From 75ea1388c53c9aea47b31499425d503f1004e421 Mon Sep 17 00:00:00 2001 From: AnnulusGames Date: Sat, 7 Dec 2024 14:31:54 +0900 Subject: [PATCH 1/2] Change: calculate random numbers using a hash value derived from the seed and time. --- .../Adapters/FixedStringMotionAdapters.cs | 15 +++----- .../Runtime/Adapters/ShakeMotionAdapters.cs | 31 +++------------- .../Runtime/Internal/MotionHelper.cs | 3 +- .../Runtime/Internal/MotionStorage.cs | 6 +++- .../Runtime/Internal/RandomHelper.cs | 36 +++++++++++++++++++ .../Runtime/Internal/RandomHelper.cs.meta | 2 ++ .../Runtime/Internal/SharedRandom.cs | 20 ----------- .../Runtime/Internal/SharedRandom.cs.meta | 11 ------ .../Runtime/MotionBuilderExtensions.cs | 4 +-- .../Runtime/MotionEvaluationContext.cs | 5 +++ .../LitMotion/Runtime/Options/ShakeOptions.cs | 6 ++-- .../Runtime/Options/StringOptions.cs | 6 ++-- 12 files changed, 67 insertions(+), 78 deletions(-) create mode 100644 src/LitMotion/Assets/LitMotion/Runtime/Internal/RandomHelper.cs create mode 100644 src/LitMotion/Assets/LitMotion/Runtime/Internal/RandomHelper.cs.meta delete mode 100644 src/LitMotion/Assets/LitMotion/Runtime/Internal/SharedRandom.cs delete mode 100644 src/LitMotion/Assets/LitMotion/Runtime/Internal/SharedRandom.cs.meta diff --git a/src/LitMotion/Assets/LitMotion/Runtime/Adapters/FixedStringMotionAdapters.cs b/src/LitMotion/Assets/LitMotion/Runtime/Adapters/FixedStringMotionAdapters.cs index e9b9fa00..27623b1b 100644 --- a/src/LitMotion/Assets/LitMotion/Runtime/Adapters/FixedStringMotionAdapters.cs +++ b/src/LitMotion/Assets/LitMotion/Runtime/Adapters/FixedStringMotionAdapters.cs @@ -18,8 +18,7 @@ public FixedString32Bytes Evaluate(ref FixedString32Bytes startValue, ref FixedS var start = startValue; var end = endValue; var customScrambleChars = options.CustomScrambleChars; - ref var randomState = ref options.RandomState; - if (randomState.state == 0) randomState = ref SharedRandom.Random; + var randomState = RandomHelper.Create(options.RandomSeed, context.Time); FixedStringHelper.Interpolate(ref start, ref end, context.Progress, options.ScrambleMode, options.RichTextEnabled, ref randomState, ref customScrambleChars, out var result); return result; } @@ -32,8 +31,7 @@ public FixedString64Bytes Evaluate(ref FixedString64Bytes startValue, ref FixedS var start = startValue; var end = endValue; var customScrambleChars = options.CustomScrambleChars; - ref var randomState = ref options.RandomState; - if (randomState.state == 0) randomState = ref SharedRandom.Random; + var randomState = RandomHelper.Create(options.RandomSeed, context.Time); FixedStringHelper.Interpolate(ref start, ref end, context.Progress, options.ScrambleMode, options.RichTextEnabled, ref randomState, ref customScrambleChars, out var result); return result; } @@ -46,8 +44,7 @@ public FixedString128Bytes Evaluate(ref FixedString128Bytes startValue, ref Fixe var start = startValue; var end = endValue; var customScrambleChars = options.CustomScrambleChars; - ref var randomState = ref options.RandomState; - if (randomState.state == 0) randomState = ref SharedRandom.Random; + var randomState = RandomHelper.Create(options.RandomSeed, context.Time); FixedStringHelper.Interpolate(ref start, ref end, context.Progress, options.ScrambleMode, options.RichTextEnabled, ref randomState, ref customScrambleChars, out var result); return result; } @@ -60,8 +57,7 @@ public FixedString512Bytes Evaluate(ref FixedString512Bytes startValue, ref Fixe var start = startValue; var end = endValue; var customScrambleChars = options.CustomScrambleChars; - ref var randomState = ref options.RandomState; - if (randomState.state == 0) randomState = ref SharedRandom.Random; + var randomState = RandomHelper.Create(options.RandomSeed, context.Time); FixedStringHelper.Interpolate(ref start, ref end, context.Progress, options.ScrambleMode, options.RichTextEnabled, ref randomState, ref customScrambleChars, out var result); return result; } @@ -74,8 +70,7 @@ public FixedString4096Bytes Evaluate(ref FixedString4096Bytes startValue, ref Fi var start = startValue; var end = endValue; var customScrambleChars = options.CustomScrambleChars; - ref var randomState = ref options.RandomState; - if (randomState.state == 0) randomState = ref SharedRandom.Random; + var randomState = RandomHelper.Create(options.RandomSeed, context.Time); FixedStringHelper.Interpolate(ref start, ref end, context.Progress, options.ScrambleMode, options.RichTextEnabled, ref randomState, ref customScrambleChars, out var result); return result; } diff --git a/src/LitMotion/Assets/LitMotion/Runtime/Adapters/ShakeMotionAdapters.cs b/src/LitMotion/Assets/LitMotion/Runtime/Adapters/ShakeMotionAdapters.cs index 06394aa3..3c878f9c 100644 --- a/src/LitMotion/Assets/LitMotion/Runtime/Adapters/ShakeMotionAdapters.cs +++ b/src/LitMotion/Assets/LitMotion/Runtime/Adapters/ShakeMotionAdapters.cs @@ -2,6 +2,7 @@ using UnityEngine; using LitMotion; using LitMotion.Adapters; +using Unity.Mathematics; [assembly: RegisterGenericJobType(typeof(MotionUpdateJob))] [assembly: RegisterGenericJobType(typeof(MotionUpdateJob))] @@ -16,15 +17,7 @@ namespace LitMotion.Adapters public float Evaluate(ref float startValue, ref float endValue, ref ShakeOptions options, in MotionEvaluationContext context) { VibrationHelper.EvaluateStrength(endValue, options.Frequency, options.DampingRatio, context.Progress, out var s); - float multipliar; - if (options.RandomState.state == 0) - { - multipliar = SharedRandom.Random.NextFloat(-1f, 1f); - } - else - { - multipliar = options.RandomState.NextFloat(-1f, 1f); - } + var multipliar = RandomHelper.NextFloat(options.RandomSeed, context.Time, -1f, 1f); return startValue + s * multipliar; } } @@ -34,15 +27,7 @@ public float Evaluate(ref float startValue, ref float endValue, ref ShakeOptions public Vector2 Evaluate(ref Vector2 startValue, ref Vector2 endValue, ref ShakeOptions options, in MotionEvaluationContext context) { VibrationHelper.EvaluateStrength(endValue, options.Frequency, options.DampingRatio, context.Progress, out var s); - Vector2 multipliar; - if (options.RandomState.state == 0) - { - multipliar = new Vector2(SharedRandom.Random.NextFloat(-1f, 1f), SharedRandom.Random.NextFloat(-1f, 1f)); - } - else - { - multipliar = new Vector2(options.RandomState.NextFloat(-1f, 1f), options.RandomState.NextFloat(-1f, 1f)); - } + var multipliar = RandomHelper.NextFloat2(options.RandomSeed, context.Time, new float2(-1f, -1f), new float2(1f, 1f)); return startValue + new Vector2(s.x * multipliar.x, s.y * multipliar.y); } } @@ -52,15 +37,7 @@ public Vector2 Evaluate(ref Vector2 startValue, ref Vector2 endValue, ref ShakeO public Vector3 Evaluate(ref Vector3 startValue, ref Vector3 endValue, ref ShakeOptions options, in MotionEvaluationContext context) { VibrationHelper.EvaluateStrength(endValue, options.Frequency, options.DampingRatio, context.Progress, out var s); - Vector3 multipliar; - if (options.RandomState.state == 0) - { - multipliar = new Vector3(SharedRandom.Random.NextFloat(-1f, 1f), SharedRandom.Random.NextFloat(-1f, 1f), SharedRandom.Random.NextFloat(-1f, 1f)); - } - else - { - multipliar = new Vector3(options.RandomState.NextFloat(-1f, 1f), options.RandomState.NextFloat(-1f, 1f), options.RandomState.NextFloat(-1f, 1f)); - } + var multipliar = RandomHelper.NextFloat3(options.RandomSeed, context.Time, new float3(-1f, -1f, -1f), new float3(1f, 1f, 1f)); return startValue + new Vector3(s.x * multipliar.x, s.y * multipliar.y, s.z * multipliar.z); } } diff --git a/src/LitMotion/Assets/LitMotion/Runtime/Internal/MotionHelper.cs b/src/LitMotion/Assets/LitMotion/Runtime/Internal/MotionHelper.cs index ea8192ad..d01739c3 100644 --- a/src/LitMotion/Assets/LitMotion/Runtime/Internal/MotionHelper.cs +++ b/src/LitMotion/Assets/LitMotion/Runtime/Internal/MotionHelper.cs @@ -133,7 +133,8 @@ public static void Update(MotionDataStartValue, ref ptr->EndValue, ref ptr->Options, context); diff --git a/src/LitMotion/Assets/LitMotion/Runtime/Internal/MotionStorage.cs b/src/LitMotion/Assets/LitMotion/Runtime/Internal/MotionStorage.cs index dffb4014..52671944 100644 --- a/src/LitMotion/Assets/LitMotion/Runtime/Internal/MotionStorage.cs +++ b/src/LitMotion/Assets/LitMotion/Runtime/Internal/MotionStorage.cs @@ -327,7 +327,11 @@ int TryCompleteCore(MotionHandle handle) ref unmanagedData.StartValue, ref unmanagedData.EndValue, ref unmanagedData.Options, - new() { Progress = easedEndProgress } + new() + { + Progress = easedEndProgress, + Time = unmanagedData.Core.Time, + } ); managedData.UpdateUnsafe(endValue); diff --git a/src/LitMotion/Assets/LitMotion/Runtime/Internal/RandomHelper.cs b/src/LitMotion/Assets/LitMotion/Runtime/Internal/RandomHelper.cs new file mode 100644 index 00000000..c82642af --- /dev/null +++ b/src/LitMotion/Assets/LitMotion/Runtime/Internal/RandomHelper.cs @@ -0,0 +1,36 @@ +using Unity.Mathematics; +using UnityEngine; + +namespace LitMotion +{ + internal static class RandomHelper + { + public static float NextFloat(uint seed, double time, float min, float max) + { + return Create(seed, time).NextFloat(min, max); + } + + public static float2 NextFloat2(uint seed, double time, in float2 min, in float2 max) + { + return Create(seed, time).NextFloat2(min, max); + } + + public static float3 NextFloat3(uint seed, double time, in float3 min, in float3 max) + { + return Create(seed, time).NextFloat3(min, max); + } + + static uint GetHash(uint seed, double time) + { + var hash = new Hash128(); + hash.Append(ref seed); + hash.Append(ref time); + return (uint)hash.GetHashCode(); + } + + public static Unity.Mathematics.Random Create(uint seed, double time) + { + return new Unity.Mathematics.Random(GetHash(seed, time)); + } + } +} \ No newline at end of file diff --git a/src/LitMotion/Assets/LitMotion/Runtime/Internal/RandomHelper.cs.meta b/src/LitMotion/Assets/LitMotion/Runtime/Internal/RandomHelper.cs.meta new file mode 100644 index 00000000..2e763f1d --- /dev/null +++ b/src/LitMotion/Assets/LitMotion/Runtime/Internal/RandomHelper.cs.meta @@ -0,0 +1,2 @@ +fileFormatVersion: 2 +guid: 48c0aa60f5a06434a94c2b4892b7bcd2 \ No newline at end of file diff --git a/src/LitMotion/Assets/LitMotion/Runtime/Internal/SharedRandom.cs b/src/LitMotion/Assets/LitMotion/Runtime/Internal/SharedRandom.cs deleted file mode 100644 index 9c4f8650..00000000 --- a/src/LitMotion/Assets/LitMotion/Runtime/Internal/SharedRandom.cs +++ /dev/null @@ -1,20 +0,0 @@ -using Unity.Burst; -using Unity.Mathematics; - -namespace LitMotion -{ - static class SharedRandom - { - readonly struct Key { } - static readonly SharedStatic sharedStatic = SharedStatic.GetOrCreate(); - - public static ref Random Random - { - get - { - if (sharedStatic.Data.state == 0) sharedStatic.Data.InitState(); - return ref sharedStatic.Data; - } - } - } -} \ No newline at end of file diff --git a/src/LitMotion/Assets/LitMotion/Runtime/Internal/SharedRandom.cs.meta b/src/LitMotion/Assets/LitMotion/Runtime/Internal/SharedRandom.cs.meta deleted file mode 100644 index 51d9718a..00000000 --- a/src/LitMotion/Assets/LitMotion/Runtime/Internal/SharedRandom.cs.meta +++ /dev/null @@ -1,11 +0,0 @@ -fileFormatVersion: 2 -guid: 52577232f18cf4e13955b15d9b77f797 -MonoImporter: - externalObjects: {} - serializedVersion: 2 - defaultReferences: [] - executionOrder: 0 - icon: {instanceID: 0} - userData: - assetBundleName: - assetBundleVariant: diff --git a/src/LitMotion/Assets/LitMotion/Runtime/MotionBuilderExtensions.cs b/src/LitMotion/Assets/LitMotion/Runtime/MotionBuilderExtensions.cs index 984e827d..b56113c2 100644 --- a/src/LitMotion/Assets/LitMotion/Runtime/MotionBuilderExtensions.cs +++ b/src/LitMotion/Assets/LitMotion/Runtime/MotionBuilderExtensions.cs @@ -127,7 +127,7 @@ public static MotionBuilder WithRandomSeed { var options = builder.buffer.Options; - options.RandomState = new Unity.Mathematics.Random(seed); + options.RandomSeed = seed; builder.buffer.Options = options; return builder; } @@ -163,7 +163,7 @@ public static MotionBuilder WithRandomSeed { var options = builder.buffer.Options; - options.RandomState = new Unity.Mathematics.Random(seed); + options.RandomSeed = seed; builder.buffer.Options = options; return builder; } diff --git a/src/LitMotion/Assets/LitMotion/Runtime/MotionEvaluationContext.cs b/src/LitMotion/Assets/LitMotion/Runtime/MotionEvaluationContext.cs index d4cd44da..fe1ed479 100644 --- a/src/LitMotion/Assets/LitMotion/Runtime/MotionEvaluationContext.cs +++ b/src/LitMotion/Assets/LitMotion/Runtime/MotionEvaluationContext.cs @@ -9,5 +9,10 @@ public struct MotionEvaluationContext /// Progress (0-1) /// public float Progress; + + /// + /// Current motion time + /// + public double Time; } } \ No newline at end of file diff --git a/src/LitMotion/Assets/LitMotion/Runtime/Options/ShakeOptions.cs b/src/LitMotion/Assets/LitMotion/Runtime/Options/ShakeOptions.cs index ba337cee..7aa98fa3 100644 --- a/src/LitMotion/Assets/LitMotion/Runtime/Options/ShakeOptions.cs +++ b/src/LitMotion/Assets/LitMotion/Runtime/Options/ShakeOptions.cs @@ -10,7 +10,7 @@ public struct ShakeOptions : IEquatable, IMotionOptions { public int Frequency; public float DampingRatio; - public Unity.Mathematics.Random RandomState; + public uint RandomSeed; public static ShakeOptions Default { @@ -28,7 +28,7 @@ public readonly bool Equals(ShakeOptions other) { return other.Frequency == Frequency && other.DampingRatio == DampingRatio && - other.RandomState.state == RandomState.state; + other.RandomSeed == RandomSeed; } public override readonly bool Equals(object obj) @@ -39,7 +39,7 @@ public override readonly bool Equals(object obj) public override readonly int GetHashCode() { - return HashCode.Combine(Frequency, DampingRatio, RandomState); + return HashCode.Combine(Frequency, DampingRatio, RandomSeed); } } } \ No newline at end of file diff --git a/src/LitMotion/Assets/LitMotion/Runtime/Options/StringOptions.cs b/src/LitMotion/Assets/LitMotion/Runtime/Options/StringOptions.cs index 82bf63ff..d197c1d4 100644 --- a/src/LitMotion/Assets/LitMotion/Runtime/Options/StringOptions.cs +++ b/src/LitMotion/Assets/LitMotion/Runtime/Options/StringOptions.cs @@ -43,14 +43,14 @@ public struct StringOptions : IMotionOptions, IEquatable public ScrambleMode ScrambleMode; public bool RichTextEnabled; public FixedString64Bytes CustomScrambleChars; - public Unity.Mathematics.Random RandomState; + public uint RandomSeed; public readonly bool Equals(StringOptions other) { return other.ScrambleMode == ScrambleMode && other.RichTextEnabled == RichTextEnabled && other.CustomScrambleChars == CustomScrambleChars && - other.RandomState.state == RandomState.state; + other.RandomSeed == RandomSeed; } public override readonly bool Equals(object obj) @@ -61,7 +61,7 @@ public override readonly bool Equals(object obj) public override readonly int GetHashCode() { - return HashCode.Combine(ScrambleMode, RichTextEnabled, CustomScrambleChars, RandomState); + return HashCode.Combine(ScrambleMode, RichTextEnabled, CustomScrambleChars, RandomSeed); } } } \ No newline at end of file From d5c8f462f1baf0f6909fb7391dad7eff598c7760 Mon Sep 17 00:00:00 2001 From: AnnulusGames Date: Sat, 7 Dec 2024 14:40:00 +0900 Subject: [PATCH 2/2] Fix: context time not passed --- .../Assets/LitMotion/Runtime/Internal/MotionStorage.cs | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/LitMotion/Assets/LitMotion/Runtime/Internal/MotionStorage.cs b/src/LitMotion/Assets/LitMotion/Runtime/Internal/MotionStorage.cs index 52671944..713be9ca 100644 --- a/src/LitMotion/Assets/LitMotion/Runtime/Internal/MotionStorage.cs +++ b/src/LitMotion/Assets/LitMotion/Runtime/Internal/MotionStorage.cs @@ -127,7 +127,8 @@ public unsafe MotionHandle Create(ref MotionBuilder { Ease.CustomAnimationCurve => buffer.AnimationCurve.Evaluate(0f), _ => EaseUtility.Evaluate(0f, dataRef.Core.Ease) - } + }, + Time = dataRef.Core.Time, } )); }