mirror of
https://github.com/ppy/osu.git
synced 2024-12-14 23:52:57 +08:00
Merge branch 'master' into home-shortcut
This commit is contained in:
commit
92e7ef6ecb
25
osu.Game.Tests/Gameplay/TestSceneGameplayClockContainer.cs
Normal file
25
osu.Game.Tests/Gameplay/TestSceneGameplayClockContainer.cs
Normal file
@ -0,0 +1,25 @@
|
||||
// Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the MIT Licence.
|
||||
// See the LICENCE file in the repository root for full licence text.
|
||||
|
||||
using System;
|
||||
using NUnit.Framework;
|
||||
using osu.Game.Rulesets.Mods;
|
||||
using osu.Game.Rulesets.Osu;
|
||||
using osu.Game.Screens.Play;
|
||||
using osu.Game.Tests.Visual;
|
||||
|
||||
namespace osu.Game.Tests.Gameplay
|
||||
{
|
||||
public class TestSceneGameplayClockContainer : OsuTestScene
|
||||
{
|
||||
[Test]
|
||||
public void TestStartThenElapsedTime()
|
||||
{
|
||||
GameplayClockContainer gcc = null;
|
||||
|
||||
AddStep("create container", () => Add(gcc = new GameplayClockContainer(CreateWorkingBeatmap(new OsuRuleset().RulesetInfo), Array.Empty<Mod>(), 0)));
|
||||
AddStep("start track", () => gcc.Start());
|
||||
AddUntilStep("elapsed greater than zero", () => gcc.GameplayClock.ElapsedFrameTime > 0);
|
||||
}
|
||||
}
|
||||
}
|
@ -1,6 +1,7 @@
|
||||
// Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the MIT Licence.
|
||||
// See the LICENCE file in the repository root for full licence text.
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using System.Threading.Tasks;
|
||||
@ -10,7 +11,12 @@ using osu.Framework.Audio.Sample;
|
||||
using osu.Framework.IO.Stores;
|
||||
using osu.Framework.Testing;
|
||||
using osu.Game.Audio;
|
||||
using osu.Game.Rulesets.Mods;
|
||||
using osu.Game.Rulesets.Osu;
|
||||
using osu.Game.Screens.Play;
|
||||
using osu.Game.Skinning;
|
||||
using osu.Game.Storyboards;
|
||||
using osu.Game.Storyboards.Drawables;
|
||||
using osu.Game.Tests.Resources;
|
||||
using osu.Game.Tests.Visual;
|
||||
|
||||
@ -43,6 +49,27 @@ namespace osu.Game.Tests.Gameplay
|
||||
AddAssert("sample is non-null", () => channel != null);
|
||||
}
|
||||
|
||||
[Test]
|
||||
public void TestSamplePlaybackAtZero()
|
||||
{
|
||||
GameplayClockContainer gameplayContainer = null;
|
||||
DrawableStoryboardSample sample = null;
|
||||
|
||||
AddStep("create container", () =>
|
||||
{
|
||||
Add(gameplayContainer = new GameplayClockContainer(CreateWorkingBeatmap(new OsuRuleset().RulesetInfo), Array.Empty<Mod>(), 0));
|
||||
|
||||
gameplayContainer.Add(sample = new DrawableStoryboardSample(new StoryboardSampleInfo(string.Empty, 0, 1))
|
||||
{
|
||||
Clock = gameplayContainer.GameplayClock
|
||||
});
|
||||
});
|
||||
|
||||
AddStep("start time", () => gameplayContainer.Start());
|
||||
|
||||
AddUntilStep("sample playback succeeded", () => sample.LifetimeEnd < double.MaxValue);
|
||||
}
|
||||
|
||||
private class TestSkin : LegacySkin
|
||||
{
|
||||
public TestSkin(string resourceName, AudioManager audioManager)
|
||||
|
@ -26,6 +26,9 @@ namespace osu.Game.Rulesets.Mods
|
||||
[SettingSource("Final rate", "The final speed to ramp to")]
|
||||
public abstract BindableNumber<double> FinalRate { get; }
|
||||
|
||||
[SettingSource("Adjust pitch", "Should pitch be adjusted with speed")]
|
||||
public abstract BindableBool AdjustPitch { get; }
|
||||
|
||||
public override string SettingDescription => $"{InitialRate.Value:N2}x to {FinalRate.Value:N2}x";
|
||||
|
||||
private double finalRateTime;
|
||||
@ -43,15 +46,16 @@ namespace osu.Game.Rulesets.Mods
|
||||
protected ModTimeRamp()
|
||||
{
|
||||
// for preview purpose at song select. eventually we'll want to be able to update every frame.
|
||||
FinalRate.BindValueChanged(val => applyAdjustment(1), true);
|
||||
FinalRate.BindValueChanged(val => applyRateAdjustment(1), true);
|
||||
AdjustPitch.BindValueChanged(applyPitchAdjustment);
|
||||
}
|
||||
|
||||
public void ApplyToTrack(Track track)
|
||||
{
|
||||
this.track = track;
|
||||
track.AddAdjustment(AdjustableProperty.Frequency, SpeedChange);
|
||||
|
||||
FinalRate.TriggerChange();
|
||||
AdjustPitch.TriggerChange();
|
||||
}
|
||||
|
||||
public virtual void ApplyToBeatmap(IBeatmap beatmap)
|
||||
@ -66,14 +70,25 @@ namespace osu.Game.Rulesets.Mods
|
||||
|
||||
public virtual void Update(Playfield playfield)
|
||||
{
|
||||
applyAdjustment((track.CurrentTime - beginRampTime) / finalRateTime);
|
||||
applyRateAdjustment((track.CurrentTime - beginRampTime) / finalRateTime);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Adjust the rate along the specified ramp
|
||||
/// </summary>
|
||||
/// <param name="amount">The amount of adjustment to apply (from 0..1).</param>
|
||||
private void applyAdjustment(double amount) =>
|
||||
private void applyRateAdjustment(double amount) =>
|
||||
SpeedChange.Value = InitialRate.Value + (FinalRate.Value - InitialRate.Value) * Math.Clamp(amount, 0, 1);
|
||||
|
||||
private void applyPitchAdjustment(ValueChangedEvent<bool> adjustPitchSetting)
|
||||
{
|
||||
// remove existing old adjustment
|
||||
track.RemoveAdjustment(adjustmentForPitchSetting(adjustPitchSetting.OldValue), SpeedChange);
|
||||
|
||||
track.AddAdjustment(adjustmentForPitchSetting(adjustPitchSetting.NewValue), SpeedChange);
|
||||
}
|
||||
|
||||
private AdjustableProperty adjustmentForPitchSetting(bool adjustPitchSettingValue)
|
||||
=> adjustPitchSettingValue ? AdjustableProperty.Frequency : AdjustableProperty.Tempo;
|
||||
}
|
||||
}
|
||||
|
@ -37,6 +37,13 @@ namespace osu.Game.Rulesets.Mods
|
||||
Precision = 0.01,
|
||||
};
|
||||
|
||||
[SettingSource("Adjust pitch", "Should pitch be adjusted with speed")]
|
||||
public override BindableBool AdjustPitch { get; } = new BindableBool
|
||||
{
|
||||
Default = true,
|
||||
Value = true
|
||||
};
|
||||
|
||||
public override Type[] IncompatibleMods => base.IncompatibleMods.Append(typeof(ModWindUp)).ToArray();
|
||||
}
|
||||
}
|
||||
|
@ -37,6 +37,13 @@ namespace osu.Game.Rulesets.Mods
|
||||
Precision = 0.01,
|
||||
};
|
||||
|
||||
[SettingSource("Adjust pitch", "Should pitch be adjusted with speed")]
|
||||
public override BindableBool AdjustPitch { get; } = new BindableBool
|
||||
{
|
||||
Default = true,
|
||||
Value = true
|
||||
};
|
||||
|
||||
public override Type[] IncompatibleMods => base.IncompatibleMods.Append(typeof(ModWindDown)).ToArray();
|
||||
}
|
||||
}
|
||||
|
@ -18,6 +18,8 @@ namespace osu.Game.Scoring
|
||||
protected override IQueryable<ScoreInfo> AddIncludesForConsumption(IQueryable<ScoreInfo> query)
|
||||
=> base.AddIncludesForConsumption(query)
|
||||
.Include(s => s.Beatmap)
|
||||
.Include(s => s.Beatmap).ThenInclude(b => b.Metadata)
|
||||
.Include(s => s.Beatmap).ThenInclude(b => b.BeatmapSet).ThenInclude(s => s.Metadata)
|
||||
.Include(s => s.Ruleset);
|
||||
}
|
||||
}
|
||||
|
@ -44,8 +44,6 @@ namespace osu.Game.Screens.Edit.Compose.Components
|
||||
|
||||
private readonly BindableList<HitObject> selectedHitObjects = new BindableList<HitObject>();
|
||||
|
||||
public override bool ReceivePositionalInputAt(Vector2 screenSpacePos) => true;
|
||||
|
||||
[Resolved(canBeNull: true)]
|
||||
private IPositionSnapProvider snapProvider { get; set; }
|
||||
|
||||
|
@ -11,6 +11,7 @@ using osu.Game.Rulesets.Edit;
|
||||
using osu.Game.Rulesets.Edit.Tools;
|
||||
using osu.Game.Rulesets.Objects;
|
||||
using osu.Game.Rulesets.Objects.Drawables;
|
||||
using osuTK;
|
||||
|
||||
namespace osu.Game.Screens.Edit.Compose.Components
|
||||
{
|
||||
@ -26,6 +27,8 @@ namespace osu.Game.Screens.Edit.Compose.Components
|
||||
|
||||
private readonly Container<PlacementBlueprint> placementBlueprintContainer;
|
||||
|
||||
public override bool ReceivePositionalInputAt(Vector2 screenSpacePos) => true;
|
||||
|
||||
private InputManager inputManager;
|
||||
|
||||
private readonly IEnumerable<DrawableHitObject> drawableHitObjects;
|
||||
|
@ -251,8 +251,9 @@ namespace osu.Game.Screens.Play
|
||||
|
||||
private class HardwareCorrectionOffsetClock : FramedOffsetClock
|
||||
{
|
||||
// we always want to apply the same real-time offset, so it should be adjusted by the playback rate to achieve this.
|
||||
public override double CurrentTime => SourceTime + Offset * Rate;
|
||||
// we always want to apply the same real-time offset, so it should be adjusted by the difference in playback rate (from realtime) to achieve this.
|
||||
// base implementation already adds offset at 1.0 rate, so we only add the difference from that here.
|
||||
public override double CurrentTime => base.CurrentTime + Offset * (Rate - 1);
|
||||
|
||||
public HardwareCorrectionOffsetClock(IClock source, bool processSource = true)
|
||||
: base(source, processSource)
|
||||
|
@ -51,7 +51,7 @@ namespace osu.Game.Storyboards.Drawables
|
||||
LifetimeStart = sampleInfo.StartTime;
|
||||
LifetimeEnd = double.MaxValue;
|
||||
}
|
||||
else if (Time.Current - Time.Elapsed < sampleInfo.StartTime)
|
||||
else if (Time.Current - Time.Elapsed <= sampleInfo.StartTime)
|
||||
{
|
||||
// We've passed the start time of the sample. We only play the sample if we're within an allowable range
|
||||
// from the sample's start, to reduce layering if we've been fast-forwarded far into the future
|
||||
|
Loading…
Reference in New Issue
Block a user