fix(rendering): bound portal resource lifetime
Separate logical ownership, render publication, and GPU retirement across live entities, landblocks, particles, textures, mesh arenas, portal/UI teardown, and per-frame scratch storage. Add bounded DAT/texture caches, upload budgets, three-frame fence retirement, exact-incarnation appearance reconciliation, frame pacing, and extensive lifetime conformance coverage.\n\nThe seven-destination connected route now cuts peak working/private memory roughly in half, returns Caul to 125-153 FPS locally, and produces no WER or AMD reset.\n\nCo-authored-by: OpenAI Codex <codex@openai.com>
This commit is contained in:
parent
3971997689
commit
749e8ceeb1
225 changed files with 29107 additions and 3914 deletions
|
|
@ -1,22 +1,23 @@
|
|||
namespace AcDream.App.World;
|
||||
|
||||
/// <summary>
|
||||
/// Strongly typed, storage-free view over animation components owned by a
|
||||
/// <see cref="LiveEntityRuntime"/>. This keeps feature loops type-safe without
|
||||
/// introducing a second component dictionary.
|
||||
/// Strongly typed view over animation components owned by a
|
||||
/// <see cref="LiveEntityRuntime"/>. It owns only reusable traversal scratch;
|
||||
/// canonical component identity remains in the runtime.
|
||||
/// </summary>
|
||||
public sealed class LiveEntityAnimationRuntimeView<TAnimation>
|
||||
: IEnumerable<KeyValuePair<uint, TAnimation>>
|
||||
where TAnimation : class, ILiveEntityAnimationRuntime
|
||||
{
|
||||
private readonly Func<LiveEntityRuntime?> _runtime;
|
||||
private readonly List<KeyValuePair<uint, TAnimation>> _iterationSnapshot = new();
|
||||
|
||||
public LiveEntityAnimationRuntimeView(Func<LiveEntityRuntime?> runtime) =>
|
||||
_runtime = runtime ?? throw new ArgumentNullException(nameof(runtime));
|
||||
|
||||
public int Count => _runtime()?.AnimationRuntimes.Count ?? 0;
|
||||
public int Count => _runtime()?.SpatialAnimationRuntimes.Count ?? 0;
|
||||
public IEnumerable<uint> Keys =>
|
||||
_runtime()?.AnimationRuntimes.Keys ?? Array.Empty<uint>();
|
||||
_runtime()?.SpatialAnimationRuntimes.Keys ?? Array.Empty<uint>();
|
||||
|
||||
public TAnimation this[uint localEntityId]
|
||||
{
|
||||
|
|
@ -51,16 +52,79 @@ public sealed class LiveEntityAnimationRuntimeView<TAnimation>
|
|||
&& runtime.ClearAnimationRuntime(guid);
|
||||
}
|
||||
|
||||
public IEnumerator<KeyValuePair<uint, TAnimation>> GetEnumerator()
|
||||
public Enumerator GetEnumerator()
|
||||
{
|
||||
if (_runtime() is not { } runtime)
|
||||
yield break;
|
||||
foreach (var pair in runtime.AnimationRuntimes)
|
||||
if (pair.Value is TAnimation typed)
|
||||
yield return new KeyValuePair<uint, TAnimation>(pair.Key, typed);
|
||||
_iterationSnapshot.Clear();
|
||||
LiveEntityRuntime? runtime = _runtime();
|
||||
if (runtime is not null)
|
||||
{
|
||||
foreach (var pair in runtime.SpatialAnimationRuntimes)
|
||||
{
|
||||
if (pair.Value is TAnimation typed)
|
||||
{
|
||||
_iterationSnapshot.Add(
|
||||
new KeyValuePair<uint, TAnimation>(pair.Key, typed));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return new Enumerator(runtime, _iterationSnapshot);
|
||||
}
|
||||
|
||||
IEnumerator<KeyValuePair<uint, TAnimation>> IEnumerable<KeyValuePair<uint, TAnimation>>.GetEnumerator() =>
|
||||
GetEnumerator();
|
||||
|
||||
System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator() => GetEnumerator();
|
||||
|
||||
/// <summary>
|
||||
/// Struct enumerator over a reusable frame snapshot. A runtime can rebucket
|
||||
/// or delete another entity from inside animation/physics callbacks without
|
||||
/// invalidating this traversal. Each entry is identity-checked immediately
|
||||
/// before it is yielded, so GUID reuse cannot advance the displaced owner.
|
||||
/// </summary>
|
||||
public struct Enumerator : IEnumerator<KeyValuePair<uint, TAnimation>>
|
||||
{
|
||||
private readonly LiveEntityRuntime? _runtime;
|
||||
private readonly List<KeyValuePair<uint, TAnimation>> _snapshot;
|
||||
private int _index;
|
||||
|
||||
internal Enumerator(
|
||||
LiveEntityRuntime? runtime,
|
||||
List<KeyValuePair<uint, TAnimation>> snapshot)
|
||||
{
|
||||
_runtime = runtime;
|
||||
_snapshot = snapshot;
|
||||
_index = -1;
|
||||
Current = default;
|
||||
}
|
||||
|
||||
public KeyValuePair<uint, TAnimation> Current { get; private set; }
|
||||
object System.Collections.IEnumerator.Current => Current;
|
||||
|
||||
public bool MoveNext()
|
||||
{
|
||||
while (++_index < _snapshot.Count)
|
||||
{
|
||||
KeyValuePair<uint, TAnimation> pair = _snapshot[_index];
|
||||
if (_runtime?.SpatialAnimationRuntimes.TryGetValue(
|
||||
pair.Key,
|
||||
out ILiveEntityAnimationRuntime? indexed) == true
|
||||
&& ReferenceEquals(indexed, pair.Value))
|
||||
{
|
||||
Current = pair;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
Current = default;
|
||||
return false;
|
||||
}
|
||||
|
||||
public void Dispose() { }
|
||||
|
||||
void System.Collections.IEnumerator.Reset() =>
|
||||
throw new NotSupportedException();
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>Storage-free typed view over remote-motion components.</summary>
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue