mirror of
https://github.com/ppy/osu.git
synced 2025-02-19 22:36:07 +08:00
Merge remote-tracking branch 'refs/remotes/ppy/master' into profile-overlay-graph-new
This commit is contained in:
commit
42741895e6
@ -5,7 +5,7 @@ using osu.Game.Rulesets.Mods;
|
|||||||
|
|
||||||
namespace osu.Game.Rulesets.Catch.Mods
|
namespace osu.Game.Rulesets.Catch.Mods
|
||||||
{
|
{
|
||||||
public class CatchModEasy : ModEasy
|
public class CatchModEasy : ModEasyWithExtraLives
|
||||||
{
|
{
|
||||||
public override string Description => @"Larger fruits, more forgiving HP drain, less accuracy required, and three lives!";
|
public override string Description => @"Larger fruits, more forgiving HP drain, less accuracy required, and three lives!";
|
||||||
}
|
}
|
||||||
|
@ -5,7 +5,7 @@ using osu.Game.Rulesets.Mods;
|
|||||||
|
|
||||||
namespace osu.Game.Rulesets.Mania.Mods
|
namespace osu.Game.Rulesets.Mania.Mods
|
||||||
{
|
{
|
||||||
public class ManiaModEasy : ModEasy
|
public class ManiaModEasy : ModEasyWithExtraLives
|
||||||
{
|
{
|
||||||
public override string Description => @"More forgiving HP drain, less accuracy required, and three lives!";
|
public override string Description => @"More forgiving HP drain, less accuracy required, and three lives!";
|
||||||
}
|
}
|
||||||
|
@ -5,7 +5,7 @@ using osu.Game.Rulesets.Mods;
|
|||||||
|
|
||||||
namespace osu.Game.Rulesets.Osu.Mods
|
namespace osu.Game.Rulesets.Osu.Mods
|
||||||
{
|
{
|
||||||
public class OsuModEasy : ModEasy
|
public class OsuModEasy : ModEasyWithExtraLives
|
||||||
{
|
{
|
||||||
public override string Description => @"Larger circles, more forgiving HP drain, less accuracy required, and three lives!";
|
public override string Description => @"Larger circles, more forgiving HP drain, less accuracy required, and three lives!";
|
||||||
}
|
}
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
// Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the MIT Licence.
|
// 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.
|
// See the LICENCE file in the repository root for full licence text.
|
||||||
|
|
||||||
|
using osu.Framework.Bindables;
|
||||||
using osuTK;
|
using osuTK;
|
||||||
using osuTK.Graphics;
|
using osuTK.Graphics;
|
||||||
using osu.Framework.Extensions.Color4Extensions;
|
using osu.Framework.Extensions.Color4Extensions;
|
||||||
@ -47,6 +48,6 @@ namespace osu.Game.Rulesets.Osu.Objects.Drawables.Connections
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
public double AnimationStartTime { get; set; }
|
public Bindable<double> AnimationStartTime { get; } = new BindableDouble();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -80,7 +80,7 @@ namespace osu.Game.Rulesets.Osu.Objects.Drawables.Connections
|
|||||||
fp.Alpha = 0;
|
fp.Alpha = 0;
|
||||||
fp.Scale = new Vector2(1.5f * end.Scale);
|
fp.Scale = new Vector2(1.5f * end.Scale);
|
||||||
|
|
||||||
fp.AnimationStartTime = fadeInTime;
|
fp.AnimationStartTime.Value = fadeInTime;
|
||||||
|
|
||||||
using (fp.BeginAbsoluteSequence(fadeInTime))
|
using (fp.BeginAbsoluteSequence(fadeInTime))
|
||||||
{
|
{
|
||||||
|
@ -7,6 +7,6 @@ namespace osu.Game.Rulesets.Taiko.Mods
|
|||||||
{
|
{
|
||||||
public class TaikoModEasy : ModEasy
|
public class TaikoModEasy : ModEasy
|
||||||
{
|
{
|
||||||
public override string Description => @"Beats move slower, less accuracy required, and three lives!";
|
public override string Description => @"Beats move slower, and less accuracy required!";
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
79
osu.Game.Tests/NonVisual/Skinning/LegacySkinAnimationTest.cs
Normal file
79
osu.Game.Tests/NonVisual/Skinning/LegacySkinAnimationTest.cs
Normal file
@ -0,0 +1,79 @@
|
|||||||
|
// 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.Linq;
|
||||||
|
using NUnit.Framework;
|
||||||
|
using osu.Framework.Allocation;
|
||||||
|
using osu.Framework.Audio.Sample;
|
||||||
|
using osu.Framework.Bindables;
|
||||||
|
using osu.Framework.Graphics;
|
||||||
|
using osu.Framework.Graphics.Animations;
|
||||||
|
using osu.Framework.Graphics.OpenGL.Textures;
|
||||||
|
using osu.Framework.Graphics.Textures;
|
||||||
|
using osu.Framework.Testing;
|
||||||
|
using osu.Framework.Timing;
|
||||||
|
using osu.Game.Audio;
|
||||||
|
using osu.Game.Skinning;
|
||||||
|
using osu.Game.Tests.Visual;
|
||||||
|
|
||||||
|
namespace osu.Game.Tests.NonVisual.Skinning
|
||||||
|
{
|
||||||
|
[HeadlessTest]
|
||||||
|
public class LegacySkinAnimationTest : OsuTestScene
|
||||||
|
{
|
||||||
|
private const string animation_name = "animation";
|
||||||
|
private const int frame_count = 6;
|
||||||
|
|
||||||
|
[Cached(typeof(IAnimationTimeReference))]
|
||||||
|
private TestAnimationTimeReference animationTimeReference = new TestAnimationTimeReference();
|
||||||
|
|
||||||
|
private TextureAnimation animation;
|
||||||
|
|
||||||
|
[Test]
|
||||||
|
public void TestAnimationTimeReferenceChange()
|
||||||
|
{
|
||||||
|
ISkin skin = new TestSkin();
|
||||||
|
|
||||||
|
AddStep("get animation", () => Add(animation = (TextureAnimation)skin.GetAnimation(animation_name, true, false)));
|
||||||
|
AddAssert("frame count correct", () => animation.FrameCount == frame_count);
|
||||||
|
assertPlaybackPosition(0);
|
||||||
|
|
||||||
|
AddStep("set start time to 1000", () => animationTimeReference.AnimationStartTime.Value = 1000);
|
||||||
|
assertPlaybackPosition(-1000);
|
||||||
|
|
||||||
|
AddStep("set current time to 500", () => animationTimeReference.ManualClock.CurrentTime = 500);
|
||||||
|
assertPlaybackPosition(-500);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void assertPlaybackPosition(double expectedPosition)
|
||||||
|
=> AddAssert($"playback position is {expectedPosition}", () => animation.PlaybackPosition == expectedPosition);
|
||||||
|
|
||||||
|
private class TestSkin : ISkin
|
||||||
|
{
|
||||||
|
private static readonly string[] lookup_names = Enumerable.Range(0, frame_count).Select(frame => $"{animation_name}-{frame}").ToArray();
|
||||||
|
|
||||||
|
public Texture GetTexture(string componentName, WrapMode wrapModeS, WrapMode wrapModeT)
|
||||||
|
{
|
||||||
|
return lookup_names.Contains(componentName) ? Texture.WhitePixel : null;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Drawable GetDrawableComponent(ISkinComponent component) => throw new NotSupportedException();
|
||||||
|
public SampleChannel GetSample(ISampleInfo sampleInfo) => throw new NotSupportedException();
|
||||||
|
public IBindable<TValue> GetConfig<TLookup, TValue>(TLookup lookup) => throw new NotSupportedException();
|
||||||
|
}
|
||||||
|
|
||||||
|
private class TestAnimationTimeReference : IAnimationTimeReference
|
||||||
|
{
|
||||||
|
public ManualClock ManualClock { get; }
|
||||||
|
public IFrameBasedClock Clock { get; }
|
||||||
|
public Bindable<double> AnimationStartTime { get; } = new BindableDouble();
|
||||||
|
|
||||||
|
public TestAnimationTimeReference()
|
||||||
|
{
|
||||||
|
ManualClock = new ManualClock();
|
||||||
|
Clock = new FramedClock(ManualClock);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -318,7 +318,7 @@ namespace osu.Game.Tests.Visual.Background
|
|||||||
private class FadeAccessibleResults : ResultsScreen
|
private class FadeAccessibleResults : ResultsScreen
|
||||||
{
|
{
|
||||||
public FadeAccessibleResults(ScoreInfo score)
|
public FadeAccessibleResults(ScoreInfo score)
|
||||||
: base(score)
|
: base(score, true)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -256,7 +256,7 @@ namespace osu.Game.Tests.Visual.Ranking
|
|||||||
public HotkeyRetryOverlay RetryOverlay;
|
public HotkeyRetryOverlay RetryOverlay;
|
||||||
|
|
||||||
public TestResultsScreen(ScoreInfo score)
|
public TestResultsScreen(ScoreInfo score)
|
||||||
: base(score)
|
: base(score, true)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -326,7 +326,7 @@ namespace osu.Game.Tests.Visual.Ranking
|
|||||||
public HotkeyRetryOverlay RetryOverlay;
|
public HotkeyRetryOverlay RetryOverlay;
|
||||||
|
|
||||||
public UnrankedSoloResultsScreen(ScoreInfo score)
|
public UnrankedSoloResultsScreen(ScoreInfo score)
|
||||||
: base(score)
|
: base(score, true)
|
||||||
{
|
{
|
||||||
Score.Beatmap.OnlineBeatmapID = 0;
|
Score.Beatmap.OnlineBeatmapID = 0;
|
||||||
Score.Beatmap.Status = BeatmapSetOnlineStatus.Pending;
|
Score.Beatmap.Status = BeatmapSetOnlineStatus.Pending;
|
||||||
|
@ -420,7 +420,7 @@ namespace osu.Game
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case ScorePresentType.Results:
|
case ScorePresentType.Results:
|
||||||
screen.Push(new SoloResultsScreen(databasedScore.ScoreInfo));
|
screen.Push(new SoloResultsScreen(databasedScore.ScoreInfo, false));
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}, validScreens: new[] { typeof(PlaySongSelect) });
|
}, validScreens: new[] { typeof(PlaySongSelect) });
|
||||||
|
@ -2,17 +2,13 @@
|
|||||||
// See the LICENCE file in the repository root for full licence text.
|
// See the LICENCE file in the repository root for full licence text.
|
||||||
|
|
||||||
using System;
|
using System;
|
||||||
using Humanizer;
|
|
||||||
using osu.Framework.Bindables;
|
|
||||||
using osu.Framework.Graphics.Sprites;
|
using osu.Framework.Graphics.Sprites;
|
||||||
using osu.Game.Beatmaps;
|
using osu.Game.Beatmaps;
|
||||||
using osu.Game.Configuration;
|
|
||||||
using osu.Game.Graphics;
|
using osu.Game.Graphics;
|
||||||
using osu.Game.Rulesets.Scoring;
|
|
||||||
|
|
||||||
namespace osu.Game.Rulesets.Mods
|
namespace osu.Game.Rulesets.Mods
|
||||||
{
|
{
|
||||||
public abstract class ModEasy : Mod, IApplicableToDifficulty, IApplicableFailOverride, IApplicableToHealthProcessor
|
public abstract class ModEasy : Mod, IApplicableToDifficulty
|
||||||
{
|
{
|
||||||
public override string Name => "Easy";
|
public override string Name => "Easy";
|
||||||
public override string Acronym => "EZ";
|
public override string Acronym => "EZ";
|
||||||
@ -22,49 +18,17 @@ namespace osu.Game.Rulesets.Mods
|
|||||||
public override bool Ranked => true;
|
public override bool Ranked => true;
|
||||||
public override Type[] IncompatibleMods => new[] { typeof(ModHardRock), typeof(ModDifficultyAdjust) };
|
public override Type[] IncompatibleMods => new[] { typeof(ModHardRock), typeof(ModDifficultyAdjust) };
|
||||||
|
|
||||||
[SettingSource("Extra Lives", "Number of extra lives")]
|
public virtual void ReadFromDifficulty(BeatmapDifficulty difficulty)
|
||||||
public Bindable<int> Retries { get; } = new BindableInt(2)
|
|
||||||
{
|
|
||||||
MinValue = 0,
|
|
||||||
MaxValue = 10
|
|
||||||
};
|
|
||||||
|
|
||||||
public override string SettingDescription => Retries.IsDefault ? string.Empty : $"{"lives".ToQuantity(Retries.Value)}";
|
|
||||||
|
|
||||||
private int retries;
|
|
||||||
|
|
||||||
private BindableNumber<double> health;
|
|
||||||
|
|
||||||
public void ReadFromDifficulty(BeatmapDifficulty difficulty)
|
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
public void ApplyToDifficulty(BeatmapDifficulty difficulty)
|
public virtual void ApplyToDifficulty(BeatmapDifficulty difficulty)
|
||||||
{
|
{
|
||||||
const float ratio = 0.5f;
|
const float ratio = 0.5f;
|
||||||
difficulty.CircleSize *= ratio;
|
difficulty.CircleSize *= ratio;
|
||||||
difficulty.ApproachRate *= ratio;
|
difficulty.ApproachRate *= ratio;
|
||||||
difficulty.DrainRate *= ratio;
|
difficulty.DrainRate *= ratio;
|
||||||
difficulty.OverallDifficulty *= ratio;
|
difficulty.OverallDifficulty *= ratio;
|
||||||
|
|
||||||
retries = Retries.Value;
|
|
||||||
}
|
|
||||||
|
|
||||||
public bool PerformFail()
|
|
||||||
{
|
|
||||||
if (retries == 0) return true;
|
|
||||||
|
|
||||||
health.Value = health.MaxValue;
|
|
||||||
retries--;
|
|
||||||
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
public bool RestartOnFail => false;
|
|
||||||
|
|
||||||
public void ApplyToHealthProcessor(HealthProcessor healthProcessor)
|
|
||||||
{
|
|
||||||
health = healthProcessor.Health.GetBoundCopy();
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
50
osu.Game/Rulesets/Mods/ModEasyWithExtraLives.cs
Normal file
50
osu.Game/Rulesets/Mods/ModEasyWithExtraLives.cs
Normal file
@ -0,0 +1,50 @@
|
|||||||
|
// 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 Humanizer;
|
||||||
|
using osu.Framework.Bindables;
|
||||||
|
using osu.Game.Beatmaps;
|
||||||
|
using osu.Game.Configuration;
|
||||||
|
using osu.Game.Rulesets.Scoring;
|
||||||
|
|
||||||
|
namespace osu.Game.Rulesets.Mods
|
||||||
|
{
|
||||||
|
public abstract class ModEasyWithExtraLives : ModEasy, IApplicableFailOverride, IApplicableToHealthProcessor
|
||||||
|
{
|
||||||
|
[SettingSource("Extra Lives", "Number of extra lives")]
|
||||||
|
public Bindable<int> Retries { get; } = new BindableInt(2)
|
||||||
|
{
|
||||||
|
MinValue = 0,
|
||||||
|
MaxValue = 10
|
||||||
|
};
|
||||||
|
|
||||||
|
public override string SettingDescription => Retries.IsDefault ? string.Empty : $"{"lives".ToQuantity(Retries.Value)}";
|
||||||
|
|
||||||
|
private int retries;
|
||||||
|
|
||||||
|
private BindableNumber<double> health;
|
||||||
|
|
||||||
|
public override void ApplyToDifficulty(BeatmapDifficulty difficulty)
|
||||||
|
{
|
||||||
|
base.ApplyToDifficulty(difficulty);
|
||||||
|
retries = Retries.Value;
|
||||||
|
}
|
||||||
|
|
||||||
|
public bool PerformFail()
|
||||||
|
{
|
||||||
|
if (retries == 0) return true;
|
||||||
|
|
||||||
|
health.Value = health.MaxValue;
|
||||||
|
retries--;
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
public bool RestartOnFail => false;
|
||||||
|
|
||||||
|
public void ApplyToHealthProcessor(HealthProcessor healthProcessor)
|
||||||
|
{
|
||||||
|
health = healthProcessor.Health.GetBoundCopy();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -92,7 +92,7 @@ namespace osu.Game.Screens.Multi.Play
|
|||||||
protected override ResultsScreen CreateResults(ScoreInfo score)
|
protected override ResultsScreen CreateResults(ScoreInfo score)
|
||||||
{
|
{
|
||||||
Debug.Assert(roomId.Value != null);
|
Debug.Assert(roomId.Value != null);
|
||||||
return new TimeshiftResultsScreen(score, roomId.Value.Value, playlistItem);
|
return new TimeshiftResultsScreen(score, roomId.Value.Value, playlistItem, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected override ScoreInfo CreateScore()
|
protected override ScoreInfo CreateScore()
|
||||||
|
@ -32,7 +32,7 @@ namespace osu.Game.Screens.Multi.Ranking
|
|||||||
[Resolved]
|
[Resolved]
|
||||||
private IAPIProvider api { get; set; }
|
private IAPIProvider api { get; set; }
|
||||||
|
|
||||||
public TimeshiftResultsScreen(ScoreInfo score, int roomId, PlaylistItem playlistItem, bool allowRetry = true)
|
public TimeshiftResultsScreen(ScoreInfo score, int roomId, PlaylistItem playlistItem, bool allowRetry)
|
||||||
: base(score, allowRetry)
|
: base(score, allowRetry)
|
||||||
{
|
{
|
||||||
this.roomId = roomId;
|
this.roomId = roomId;
|
||||||
|
@ -545,7 +545,7 @@ namespace osu.Game.Screens.Play
|
|||||||
|
|
||||||
protected override bool OnScroll(ScrollEvent e) => mouseWheelDisabled.Value && !GameplayClockContainer.IsPaused.Value;
|
protected override bool OnScroll(ScrollEvent e) => mouseWheelDisabled.Value && !GameplayClockContainer.IsPaused.Value;
|
||||||
|
|
||||||
protected virtual ResultsScreen CreateResults(ScoreInfo score) => new SoloResultsScreen(score);
|
protected virtual ResultsScreen CreateResults(ScoreInfo score) => new SoloResultsScreen(score, true);
|
||||||
|
|
||||||
#region Fail Logic
|
#region Fail Logic
|
||||||
|
|
||||||
|
@ -12,7 +12,7 @@ namespace osu.Game.Screens.Play
|
|||||||
public class SpectatorResultsScreen : SoloResultsScreen
|
public class SpectatorResultsScreen : SoloResultsScreen
|
||||||
{
|
{
|
||||||
public SpectatorResultsScreen(ScoreInfo score)
|
public SpectatorResultsScreen(ScoreInfo score)
|
||||||
: base(score)
|
: base(score, false)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -58,7 +58,7 @@ namespace osu.Game.Screens.Ranking
|
|||||||
|
|
||||||
private readonly bool allowRetry;
|
private readonly bool allowRetry;
|
||||||
|
|
||||||
protected ResultsScreen(ScoreInfo score, bool allowRetry = true)
|
protected ResultsScreen(ScoreInfo score, bool allowRetry)
|
||||||
{
|
{
|
||||||
Score = score;
|
Score = score;
|
||||||
this.allowRetry = allowRetry;
|
this.allowRetry = allowRetry;
|
||||||
|
@ -18,7 +18,7 @@ namespace osu.Game.Screens.Ranking
|
|||||||
[Resolved]
|
[Resolved]
|
||||||
private RulesetStore rulesets { get; set; }
|
private RulesetStore rulesets { get; set; }
|
||||||
|
|
||||||
public SoloResultsScreen(ScoreInfo score, bool allowRetry = true)
|
public SoloResultsScreen(ScoreInfo score, bool allowRetry)
|
||||||
: base(score, allowRetry)
|
: base(score, allowRetry)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
@ -38,7 +38,7 @@ namespace osu.Game.Screens.Select
|
|||||||
}
|
}
|
||||||
|
|
||||||
protected void PresentScore(ScoreInfo score) =>
|
protected void PresentScore(ScoreInfo score) =>
|
||||||
FinaliseSelection(score.Beatmap, score.Ruleset, () => this.Push(new SoloResultsScreen(score)));
|
FinaliseSelection(score.Beatmap, score.Ruleset, () => this.Push(new SoloResultsScreen(score, false)));
|
||||||
|
|
||||||
protected override BeatmapDetailArea CreateBeatmapDetailArea() => new PlayBeatmapDetailArea();
|
protected override BeatmapDetailArea CreateBeatmapDetailArea() => new PlayBeatmapDetailArea();
|
||||||
|
|
||||||
|
@ -2,6 +2,7 @@
|
|||||||
// See the LICENCE file in the repository root for full licence text.
|
// See the LICENCE file in the repository root for full licence text.
|
||||||
|
|
||||||
using osu.Framework.Allocation;
|
using osu.Framework.Allocation;
|
||||||
|
using osu.Framework.Bindables;
|
||||||
using osu.Framework.Graphics.OpenGL.Textures;
|
using osu.Framework.Graphics.OpenGL.Textures;
|
||||||
using osu.Framework.Timing;
|
using osu.Framework.Timing;
|
||||||
|
|
||||||
@ -25,6 +26,6 @@ namespace osu.Game.Skinning
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// The time which animations should be started from, relative to <see cref="Clock"/>.
|
/// The time which animations should be started from, relative to <see cref="Clock"/>.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
double AnimationStartTime { get; }
|
Bindable<double> AnimationStartTime { get; }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -4,6 +4,7 @@
|
|||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using osu.Framework.Allocation;
|
using osu.Framework.Allocation;
|
||||||
|
using osu.Framework.Bindables;
|
||||||
using osu.Framework.Graphics;
|
using osu.Framework.Graphics;
|
||||||
using osu.Framework.Graphics.Animations;
|
using osu.Framework.Graphics.Animations;
|
||||||
using osu.Framework.Graphics.OpenGL.Textures;
|
using osu.Framework.Graphics.OpenGL.Textures;
|
||||||
@ -70,6 +71,8 @@ namespace osu.Game.Skinning
|
|||||||
[Resolved(canBeNull: true)]
|
[Resolved(canBeNull: true)]
|
||||||
private IAnimationTimeReference timeReference { get; set; }
|
private IAnimationTimeReference timeReference { get; set; }
|
||||||
|
|
||||||
|
private readonly Bindable<double> animationStartTime = new BindableDouble();
|
||||||
|
|
||||||
public SkinnableTextureAnimation(bool startAtCurrentTime = true)
|
public SkinnableTextureAnimation(bool startAtCurrentTime = true)
|
||||||
: base(startAtCurrentTime)
|
: base(startAtCurrentTime)
|
||||||
{
|
{
|
||||||
@ -82,8 +85,18 @@ namespace osu.Game.Skinning
|
|||||||
if (timeReference != null)
|
if (timeReference != null)
|
||||||
{
|
{
|
||||||
Clock = timeReference.Clock;
|
Clock = timeReference.Clock;
|
||||||
PlaybackPosition = timeReference.Clock.CurrentTime - timeReference.AnimationStartTime;
|
animationStartTime.BindTo(timeReference.AnimationStartTime);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
animationStartTime.BindValueChanged(_ => updatePlaybackPosition(), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void updatePlaybackPosition()
|
||||||
|
{
|
||||||
|
if (timeReference == null)
|
||||||
|
return;
|
||||||
|
|
||||||
|
PlaybackPosition = timeReference.Clock.CurrentTime - timeReference.AnimationStartTime.Value;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user