Checkpoint 7

1. Job 通道数据结构改为 Unity.Mathematics 类型(float3/quaternion),并保留 Simulation 主数据结构不变。
2. 更新了通道边界转换函数:进入 Job 通道时转为数学类型,回写 Simulation 时转回 Vector3/Quaternion。
3. 敌人 Job 热路径去掉 Vector3/Quaternion 中间态,核心执行统一 math.* + float3/quaternion。
4. 投射物移动 Job 热路径同样统一为数学类型计算与输出。
5. 新增 Burst 开关 A/B 一致性回归测试(EditMode + PlayMode),并补了反射入口校验。
This commit is contained in:
SepComet
2026-02-23 10:29:47 +08:00
parent f0abf78128
commit e6d722ee1d
20 changed files with 2096 additions and 51 deletions
@@ -67,6 +67,12 @@ namespace Simulation.Tests.PlayMode
private static readonly MethodInfo SetUseJobSimulationMethod =
SimulationWorldType?.GetMethod("SetUseJobSimulation", PublicInstance);
private static readonly MethodInfo SetUseBurstJobsMethod =
SimulationWorldType?.GetMethod("SetUseBurstJobs", PublicInstance);
private static readonly MethodInfo ClearMethod =
SimulationWorldType?.GetMethod("Clear", PublicInstance);
private static readonly MethodInfo UseGridBucketSolverMethod =
EnemySeparationSolverProviderType?.GetMethod("UseGridBucketSolver", PublicStatic);
@@ -136,6 +142,8 @@ namespace Simulation.Tests.PlayMode
Assert.NotNull(TryGetNearestEnemyEntityIdMethod, "TryGetNearestEnemyEntityId reflection lookup failed.");
Assert.NotNull(SetUseSimulationMovementMethod, "SetUseSimulationMovement reflection lookup failed.");
Assert.NotNull(SetUseJobSimulationMethod, "SetUseJobSimulation reflection lookup failed.");
Assert.NotNull(SetUseBurstJobsMethod, "SetUseBurstJobs reflection lookup failed.");
Assert.NotNull(ClearMethod, "Clear reflection lookup failed.");
Assert.NotNull(UseGridBucketSolverMethod, "UseGridBucketSolver reflection lookup failed.");
Assert.NotNull(EnemiesProperty, "Enemies property reflection lookup failed.");
Assert.NotNull(ProjectilesProperty, "Projectiles property reflection lookup failed.");
@@ -258,6 +266,38 @@ namespace Simulation.Tests.PlayMode
yield break;
}
[UnityTest]
public IEnumerator TickEnemies_MatchesOutput_WhenBurstJobsToggled()
{
SetUseJobSimulationMethod.Invoke(_worldComponent, new object[] { true });
SetUseBurstJobsMethod.Invoke(_worldComponent, new object[] { false });
UpsertEnemy(CreateEnemy(entityId: 3251, position: Vector3.zero, speed: 2f, attackRange: 1f));
InvokeTick(deltaTime: 1f, realDeltaTime: 1f, playerPosition: new Vector3(10f, 0f, 0f));
object nonBurstEnemy = GetEnemyAt(0);
int nonBurstState = (int)GetField(nonBurstEnemy, "State");
Vector3 nonBurstPosition = (Vector3)GetField(nonBurstEnemy, "Position");
Vector3 nonBurstForward = (Vector3)GetField(nonBurstEnemy, "Forward");
ClearMethod.Invoke(_worldComponent, null);
SetUseSimulationMovementMethod.Invoke(_worldComponent, new object[] { true });
SetUseJobSimulationMethod.Invoke(_worldComponent, new object[] { true });
SetUseBurstJobsMethod.Invoke(_worldComponent, new object[] { true });
UpsertEnemy(CreateEnemy(entityId: 3251, position: Vector3.zero, speed: 2f, attackRange: 1f));
InvokeTick(deltaTime: 1f, realDeltaTime: 1f, playerPosition: new Vector3(10f, 0f, 0f));
object burstEnemy = GetEnemyAt(0);
int burstState = (int)GetField(burstEnemy, "State");
Vector3 burstPosition = (Vector3)GetField(burstEnemy, "Position");
Vector3 burstForward = (Vector3)GetField(burstEnemy, "Forward");
Assert.That(burstState, Is.EqualTo(nonBurstState));
Assert.That((burstPosition - nonBurstPosition).sqrMagnitude, Is.LessThanOrEqualTo(1e-8f));
Assert.That((burstForward - nonBurstForward).sqrMagnitude, Is.LessThanOrEqualTo(1e-8f));
yield break;
}
[UnityTest]
public IEnumerator TryGetNearestEnemyEntityId_SelectsNearestBucketCandidate_WhenJobSimulationEnabled()
{