refactor(animation): extract live PartArray presenter
Move final live part composition, exact-incarnation schedule handoff, MotionDone binding, and presentation diagnostics out of GameWindow while preserving the retail frame order. Reject stale schedule and completion ABA at the new owner boundary. Co-Authored-By: OpenAI Codex <codex@openai.com>
This commit is contained in:
parent
9760ff5a8d
commit
f004ac5562
14 changed files with 963 additions and 438 deletions
63
src/AcDream.App/Rendering/LiveEntityAnimationState.cs
Normal file
63
src/AcDream.App/Rendering/LiveEntityAnimationState.cs
Normal file
|
|
@ -0,0 +1,63 @@
|
|||
using System.Numerics;
|
||||
using AcDream.App.World;
|
||||
using AcDream.Core.Physics;
|
||||
using AcDream.Core.Physics.Motion;
|
||||
using AcDream.Core.World;
|
||||
using DatReaderWriter.DBObjs;
|
||||
using DatReaderWriter.Types;
|
||||
|
||||
namespace AcDream.App.Rendering;
|
||||
|
||||
/// <summary>
|
||||
/// Incarnation-owned live <c>CPartArray</c> presentation state. Time, root
|
||||
/// motion, and hooks remain owned by <see cref="LiveEntityAnimationScheduler"/>;
|
||||
/// this component retains the final part-presentation channels only.
|
||||
/// </summary>
|
||||
internal sealed class LiveEntityAnimationState : ILiveEntityAnimationRuntime
|
||||
{
|
||||
public required WorldEntity Entity;
|
||||
WorldEntity ILiveEntityAnimationRuntime.Entity => Entity;
|
||||
uint ILiveEntityAnimationRuntime.CurrentMotion => Sequencer?.CurrentMotion ?? 0u;
|
||||
|
||||
public required Setup Setup;
|
||||
public required Animation Animation;
|
||||
public required int LowFrame;
|
||||
public required int HighFrame;
|
||||
public required float Framerate;
|
||||
public required float Scale;
|
||||
public required IReadOnlyList<LiveAnimationPartTemplate> PartTemplate;
|
||||
public required IReadOnlyList<bool> PartAvailability;
|
||||
public float CurrFrame;
|
||||
public AnimationSequencer? Sequencer;
|
||||
|
||||
public IReadOnlyList<PartTransform>? PreparedSequenceFrames;
|
||||
public bool SequenceAdvancedBeforeAnimationPass;
|
||||
public readonly Frame RootMotionScratch = new();
|
||||
public readonly MotionDeltaFrame RootMotionDeltaScratch = new();
|
||||
|
||||
/// <summary>Reusable compact drawable channel, consumed before draw.</summary>
|
||||
public readonly List<MeshRef> MeshRefsScratch = new();
|
||||
/// <summary>Reusable indexed rigid/effect channel.</summary>
|
||||
public readonly List<Matrix4x4> EffectPartPosesScratch = new();
|
||||
/// <summary>
|
||||
/// Indexed visible transforms retained separately from the rigid channel
|
||||
/// because Setup DefaultScale affects geometry but not attachments.
|
||||
/// </summary>
|
||||
public readonly List<Matrix4x4> VisualPartPosesScratch = new();
|
||||
public bool PresentationPosesInitialized;
|
||||
|
||||
public double LastSequenceDiagnosticTime;
|
||||
public double LastPartDiagnosticTime;
|
||||
|
||||
public void InvalidatePresentationPoses()
|
||||
{
|
||||
PresentationPosesInitialized = false;
|
||||
VisualPartPosesScratch.Clear();
|
||||
EffectPartPosesScratch.Clear();
|
||||
}
|
||||
}
|
||||
|
||||
internal readonly record struct LiveAnimationPartTemplate(
|
||||
uint GfxObjId,
|
||||
IReadOnlyDictionary<uint, uint>? SurfaceOverrides,
|
||||
bool IsDrawable);
|
||||
Loading…
Add table
Add a link
Reference in a new issue