mirror of
https://github.com/ppy/osu.git
synced 2025-01-12 20:22:55 +08:00
Fix storyboard vectorscale and scale cross-polluting each other (#7259)
Fix storyboard vectorscale and scale cross-polluting each other
This commit is contained in:
commit
53d6693c89
@ -176,7 +176,7 @@ namespace osu.Game.Beatmaps.Formats
|
|||||||
{
|
{
|
||||||
var startValue = float.Parse(split[4], CultureInfo.InvariantCulture);
|
var startValue = float.Parse(split[4], CultureInfo.InvariantCulture);
|
||||||
var endValue = split.Length > 5 ? float.Parse(split[5], CultureInfo.InvariantCulture) : startValue;
|
var endValue = split.Length > 5 ? float.Parse(split[5], CultureInfo.InvariantCulture) : startValue;
|
||||||
timelineGroup?.Scale.Add(easing, startTime, endTime, new Vector2(startValue), new Vector2(endValue));
|
timelineGroup?.Scale.Add(easing, startTime, endTime, startValue, endValue);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -186,7 +186,7 @@ namespace osu.Game.Beatmaps.Formats
|
|||||||
var startY = float.Parse(split[5], CultureInfo.InvariantCulture);
|
var startY = float.Parse(split[5], CultureInfo.InvariantCulture);
|
||||||
var endX = split.Length > 6 ? float.Parse(split[6], CultureInfo.InvariantCulture) : startX;
|
var endX = split.Length > 6 ? float.Parse(split[6], CultureInfo.InvariantCulture) : startX;
|
||||||
var endY = split.Length > 7 ? float.Parse(split[7], CultureInfo.InvariantCulture) : startY;
|
var endY = split.Length > 7 ? float.Parse(split[7], CultureInfo.InvariantCulture) : startY;
|
||||||
timelineGroup?.Scale.Add(easing, startTime, endTime, new Vector2(startX, startY), new Vector2(endX, endY));
|
timelineGroup?.VectorScale.Add(easing, startTime, endTime, new Vector2(startX, startY), new Vector2(endX, endY));
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -16,7 +16,8 @@ namespace osu.Game.Storyboards
|
|||||||
{
|
{
|
||||||
public CommandTimeline<float> X = new CommandTimeline<float>();
|
public CommandTimeline<float> X = new CommandTimeline<float>();
|
||||||
public CommandTimeline<float> Y = new CommandTimeline<float>();
|
public CommandTimeline<float> Y = new CommandTimeline<float>();
|
||||||
public CommandTimeline<Vector2> Scale = new CommandTimeline<Vector2>();
|
public CommandTimeline<float> Scale = new CommandTimeline<float>();
|
||||||
|
public CommandTimeline<Vector2> VectorScale = new CommandTimeline<Vector2>();
|
||||||
public CommandTimeline<float> Rotation = new CommandTimeline<float>();
|
public CommandTimeline<float> Rotation = new CommandTimeline<float>();
|
||||||
public CommandTimeline<Color4> Colour = new CommandTimeline<Color4>();
|
public CommandTimeline<Color4> Colour = new CommandTimeline<Color4>();
|
||||||
public CommandTimeline<float> Alpha = new CommandTimeline<float>();
|
public CommandTimeline<float> Alpha = new CommandTimeline<float>();
|
||||||
|
@ -8,21 +8,44 @@ 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.Textures;
|
using osu.Framework.Graphics.Textures;
|
||||||
|
using osu.Framework.MathUtils;
|
||||||
using osu.Game.Beatmaps;
|
using osu.Game.Beatmaps;
|
||||||
|
|
||||||
namespace osu.Game.Storyboards.Drawables
|
namespace osu.Game.Storyboards.Drawables
|
||||||
{
|
{
|
||||||
public class DrawableStoryboardAnimation : TextureAnimation, IFlippable
|
public class DrawableStoryboardAnimation : TextureAnimation, IFlippable, IVectorScalable
|
||||||
{
|
{
|
||||||
public StoryboardAnimation Animation { get; private set; }
|
public StoryboardAnimation Animation { get; private set; }
|
||||||
|
|
||||||
public bool FlipH { get; set; }
|
public bool FlipH { get; set; }
|
||||||
public bool FlipV { get; set; }
|
public bool FlipV { get; set; }
|
||||||
|
|
||||||
|
private Vector2 vectorScale = Vector2.One;
|
||||||
|
|
||||||
|
public Vector2 VectorScale
|
||||||
|
{
|
||||||
|
get => vectorScale;
|
||||||
|
set
|
||||||
|
{
|
||||||
|
if (Math.Abs(value.X) < Precision.FLOAT_EPSILON)
|
||||||
|
value.X = Precision.FLOAT_EPSILON;
|
||||||
|
if (Math.Abs(value.Y) < Precision.FLOAT_EPSILON)
|
||||||
|
value.Y = Precision.FLOAT_EPSILON;
|
||||||
|
|
||||||
|
if (vectorScale == value)
|
||||||
|
return;
|
||||||
|
|
||||||
|
if (!Validation.IsFinite(value)) throw new ArgumentException($@"{nameof(VectorScale)} must be finite, but is {value}.");
|
||||||
|
|
||||||
|
vectorScale = value;
|
||||||
|
Invalidate(Invalidation.MiscGeometry);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public override bool RemoveWhenNotAlive => false;
|
public override bool RemoveWhenNotAlive => false;
|
||||||
|
|
||||||
protected override Vector2 DrawScale
|
protected override Vector2 DrawScale
|
||||||
=> new Vector2(FlipH ? -base.DrawScale.X : base.DrawScale.X, FlipV ? -base.DrawScale.Y : base.DrawScale.Y);
|
=> new Vector2(FlipH ? -base.DrawScale.X : base.DrawScale.X, FlipV ? -base.DrawScale.Y : base.DrawScale.Y) * VectorScale;
|
||||||
|
|
||||||
public override Anchor Origin
|
public override Anchor Origin
|
||||||
{
|
{
|
||||||
|
@ -8,21 +8,44 @@ using osu.Framework.Bindables;
|
|||||||
using osu.Framework.Graphics;
|
using osu.Framework.Graphics;
|
||||||
using osu.Framework.Graphics.Sprites;
|
using osu.Framework.Graphics.Sprites;
|
||||||
using osu.Framework.Graphics.Textures;
|
using osu.Framework.Graphics.Textures;
|
||||||
|
using osu.Framework.MathUtils;
|
||||||
using osu.Game.Beatmaps;
|
using osu.Game.Beatmaps;
|
||||||
|
|
||||||
namespace osu.Game.Storyboards.Drawables
|
namespace osu.Game.Storyboards.Drawables
|
||||||
{
|
{
|
||||||
public class DrawableStoryboardSprite : Sprite, IFlippable
|
public class DrawableStoryboardSprite : Sprite, IFlippable, IVectorScalable
|
||||||
{
|
{
|
||||||
public StoryboardSprite Sprite { get; private set; }
|
public StoryboardSprite Sprite { get; private set; }
|
||||||
|
|
||||||
public bool FlipH { get; set; }
|
public bool FlipH { get; set; }
|
||||||
public bool FlipV { get; set; }
|
public bool FlipV { get; set; }
|
||||||
|
|
||||||
|
private Vector2 vectorScale = Vector2.One;
|
||||||
|
|
||||||
|
public Vector2 VectorScale
|
||||||
|
{
|
||||||
|
get => vectorScale;
|
||||||
|
set
|
||||||
|
{
|
||||||
|
if (Math.Abs(value.X) < Precision.FLOAT_EPSILON)
|
||||||
|
value.X = Precision.FLOAT_EPSILON;
|
||||||
|
if (Math.Abs(value.Y) < Precision.FLOAT_EPSILON)
|
||||||
|
value.Y = Precision.FLOAT_EPSILON;
|
||||||
|
|
||||||
|
if (vectorScale == value)
|
||||||
|
return;
|
||||||
|
|
||||||
|
if (!Validation.IsFinite(value)) throw new ArgumentException($@"{nameof(VectorScale)} must be finite, but is {value}.");
|
||||||
|
|
||||||
|
vectorScale = value;
|
||||||
|
Invalidate(Invalidation.MiscGeometry);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public override bool RemoveWhenNotAlive => false;
|
public override bool RemoveWhenNotAlive => false;
|
||||||
|
|
||||||
protected override Vector2 DrawScale
|
protected override Vector2 DrawScale
|
||||||
=> new Vector2(FlipH ? -base.DrawScale.X : base.DrawScale.X, FlipV ? -base.DrawScale.Y : base.DrawScale.Y);
|
=> new Vector2(FlipH ? -base.DrawScale.X : base.DrawScale.X, FlipV ? -base.DrawScale.Y : base.DrawScale.Y) * VectorScale;
|
||||||
|
|
||||||
public override Anchor Origin
|
public override Anchor Origin
|
||||||
{
|
{
|
||||||
|
@ -6,13 +6,13 @@ using osu.Framework.Graphics.Transforms;
|
|||||||
|
|
||||||
namespace osu.Game.Storyboards.Drawables
|
namespace osu.Game.Storyboards.Drawables
|
||||||
{
|
{
|
||||||
public interface IFlippable : ITransformable
|
internal interface IFlippable : ITransformable
|
||||||
{
|
{
|
||||||
bool FlipH { get; set; }
|
bool FlipH { get; set; }
|
||||||
bool FlipV { get; set; }
|
bool FlipV { get; set; }
|
||||||
}
|
}
|
||||||
|
|
||||||
public class TransformFlipH : Transform<bool, IFlippable>
|
internal class TransformFlipH : Transform<bool, IFlippable>
|
||||||
{
|
{
|
||||||
private bool valueAt(double time)
|
private bool valueAt(double time)
|
||||||
=> time < EndTime ? StartValue : EndValue;
|
=> time < EndTime ? StartValue : EndValue;
|
||||||
@ -23,7 +23,7 @@ namespace osu.Game.Storyboards.Drawables
|
|||||||
protected override void ReadIntoStartValue(IFlippable d) => StartValue = d.FlipH;
|
protected override void ReadIntoStartValue(IFlippable d) => StartValue = d.FlipH;
|
||||||
}
|
}
|
||||||
|
|
||||||
public class TransformFlipV : Transform<bool, IFlippable>
|
internal class TransformFlipV : Transform<bool, IFlippable>
|
||||||
{
|
{
|
||||||
private bool valueAt(double time)
|
private bool valueAt(double time)
|
||||||
=> time < EndTime ? StartValue : EndValue;
|
=> time < EndTime ? StartValue : EndValue;
|
||||||
@ -34,7 +34,7 @@ namespace osu.Game.Storyboards.Drawables
|
|||||||
protected override void ReadIntoStartValue(IFlippable d) => StartValue = d.FlipV;
|
protected override void ReadIntoStartValue(IFlippable d) => StartValue = d.FlipV;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static class FlippableExtensions
|
internal static class FlippableExtensions
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Adjusts <see cref="IFlippable.FlipH"/> after a delay.
|
/// Adjusts <see cref="IFlippable.FlipH"/> after a delay.
|
||||||
|
21
osu.Game/Storyboards/Drawables/IVectorScalable.cs
Normal file
21
osu.Game/Storyboards/Drawables/IVectorScalable.cs
Normal file
@ -0,0 +1,21 @@
|
|||||||
|
// 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 osu.Framework.Graphics;
|
||||||
|
using osu.Framework.Graphics.Transforms;
|
||||||
|
using osuTK;
|
||||||
|
|
||||||
|
namespace osu.Game.Storyboards.Drawables
|
||||||
|
{
|
||||||
|
internal interface IVectorScalable : ITransformable
|
||||||
|
{
|
||||||
|
Vector2 VectorScale { get; set; }
|
||||||
|
}
|
||||||
|
|
||||||
|
internal static class VectorScalableExtensions
|
||||||
|
{
|
||||||
|
public static TransformSequence<T> VectorScaleTo<T>(this T target, Vector2 newVectorScale, double duration = 0, Easing easing = Easing.None)
|
||||||
|
where T : class, IVectorScalable
|
||||||
|
=> target.TransformTo(nameof(IVectorScalable.VectorScale), newVectorScale, duration, easing);
|
||||||
|
}
|
||||||
|
}
|
@ -65,20 +65,30 @@ namespace osu.Game.Storyboards
|
|||||||
{
|
{
|
||||||
applyCommands(drawable, getCommands(g => g.X, triggeredGroups), (d, value) => d.X = value, (d, value, duration, easing) => d.MoveToX(value, duration, easing));
|
applyCommands(drawable, getCommands(g => g.X, triggeredGroups), (d, value) => d.X = value, (d, value, duration, easing) => d.MoveToX(value, duration, easing));
|
||||||
applyCommands(drawable, getCommands(g => g.Y, triggeredGroups), (d, value) => d.Y = value, (d, value, duration, easing) => d.MoveToY(value, duration, easing));
|
applyCommands(drawable, getCommands(g => g.Y, triggeredGroups), (d, value) => d.Y = value, (d, value, duration, easing) => d.MoveToY(value, duration, easing));
|
||||||
applyCommands(drawable, getCommands(g => g.Scale, triggeredGroups), (d, value) => d.Scale = value, (d, value, duration, easing) => d.ScaleTo(value, duration, easing));
|
applyCommands(drawable, getCommands(g => g.Scale, triggeredGroups), (d, value) => d.Scale = new Vector2(value), (d, value, duration, easing) => d.ScaleTo(value, duration, easing));
|
||||||
applyCommands(drawable, getCommands(g => g.Rotation, triggeredGroups), (d, value) => d.Rotation = value, (d, value, duration, easing) => d.RotateTo(value, duration, easing));
|
applyCommands(drawable, getCommands(g => g.Rotation, triggeredGroups), (d, value) => d.Rotation = value, (d, value, duration, easing) => d.RotateTo(value, duration, easing));
|
||||||
applyCommands(drawable, getCommands(g => g.Colour, triggeredGroups), (d, value) => d.Colour = value, (d, value, duration, easing) => d.FadeColour(value, duration, easing));
|
applyCommands(drawable, getCommands(g => g.Colour, triggeredGroups), (d, value) => d.Colour = value, (d, value, duration, easing) => d.FadeColour(value, duration, easing));
|
||||||
applyCommands(drawable, getCommands(g => g.Alpha, triggeredGroups), (d, value) => d.Alpha = value, (d, value, duration, easing) => d.FadeTo(value, duration, easing));
|
applyCommands(drawable, getCommands(g => g.Alpha, triggeredGroups), (d, value) => d.Alpha = value, (d, value, duration, easing) => d.FadeTo(value, duration, easing));
|
||||||
applyCommands(drawable, getCommands(g => g.BlendingParameters, triggeredGroups), (d, value) => d.Blending = value, (d, value, duration, easing) => d.TransformBlendingMode(value, duration), false);
|
applyCommands(drawable, getCommands(g => g.BlendingParameters, triggeredGroups), (d, value) => d.Blending = value, (d, value, duration, easing) => d.TransformBlendingMode(value, duration),
|
||||||
|
false);
|
||||||
|
|
||||||
|
if (drawable is IVectorScalable vectorScalable)
|
||||||
|
{
|
||||||
|
applyCommands(drawable, getCommands(g => g.VectorScale, triggeredGroups), (d, value) => vectorScalable.VectorScale = value,
|
||||||
|
(d, value, duration, easing) => vectorScalable.VectorScaleTo(value, duration, easing));
|
||||||
|
}
|
||||||
|
|
||||||
if (drawable is IFlippable flippable)
|
if (drawable is IFlippable flippable)
|
||||||
{
|
{
|
||||||
applyCommands(drawable, getCommands(g => g.FlipH, triggeredGroups), (d, value) => flippable.FlipH = value, (d, value, duration, easing) => flippable.TransformFlipH(value, duration), false);
|
applyCommands(drawable, getCommands(g => g.FlipH, triggeredGroups), (d, value) => flippable.FlipH = value, (d, value, duration, easing) => flippable.TransformFlipH(value, duration),
|
||||||
applyCommands(drawable, getCommands(g => g.FlipV, triggeredGroups), (d, value) => flippable.FlipV = value, (d, value, duration, easing) => flippable.TransformFlipV(value, duration), false);
|
false);
|
||||||
|
applyCommands(drawable, getCommands(g => g.FlipV, triggeredGroups), (d, value) => flippable.FlipV = value, (d, value, duration, easing) => flippable.TransformFlipV(value, duration),
|
||||||
|
false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void applyCommands<T>(Drawable drawable, IEnumerable<CommandTimeline<T>.TypedCommand> commands, DrawablePropertyInitializer<T> initializeProperty, DrawableTransformer<T> transform, bool alwaysInitialize = true)
|
private void applyCommands<T>(Drawable drawable, IEnumerable<CommandTimeline<T>.TypedCommand> commands, DrawablePropertyInitializer<T> initializeProperty, DrawableTransformer<T> transform,
|
||||||
|
bool alwaysInitialize = true)
|
||||||
where T : struct
|
where T : struct
|
||||||
{
|
{
|
||||||
var initialized = false;
|
var initialized = false;
|
||||||
|
Loading…
Reference in New Issue
Block a user