fix(physics): traverse prepared indoor portal topology
This commit is contained in:
parent
b12d94047c
commit
4d095be286
9 changed files with 400 additions and 5 deletions
|
|
@ -16,6 +16,7 @@ public class CellTransitFindTransitCellsSphereTests
|
|||
Root = new CellBSPNode
|
||||
{
|
||||
// Local x >= 0 is inside this synthetic cell.
|
||||
Type = DatReaderWriter.Enums.BSPNodeType.BPIn,
|
||||
SplittingPlane = new Plane(new Vector3(1f, 0f, 0f), 0f),
|
||||
PosNode = leaf,
|
||||
}
|
||||
|
|
@ -28,6 +29,7 @@ public class CellTransitFindTransitCellsSphereTests
|
|||
// Portal poly at local x=2.5 (right wall), normal +X.
|
||||
var portalPolyA = new ResolvedPolygon
|
||||
{
|
||||
Id = 10,
|
||||
Vertices = new[]
|
||||
{
|
||||
new Vector3(2.5f, -2.5f, 0f),
|
||||
|
|
@ -54,6 +56,24 @@ public class CellTransitFindTransitCellsSphereTests
|
|||
};
|
||||
}
|
||||
|
||||
private static CellPhysics PrepareCell(CellPhysics graphCell, uint sourceId)
|
||||
{
|
||||
FlatCellCollisionAsset prepared =
|
||||
FlatCollisionAssetBuilder.FlattenCell(graphCell);
|
||||
return new CellPhysics
|
||||
{
|
||||
SourceId = sourceId,
|
||||
WorldTransform = graphCell.WorldTransform,
|
||||
InverseWorldTransform = graphCell.InverseWorldTransform,
|
||||
Resolved = new Dictionary<ushort, ResolvedPolygon>(),
|
||||
FlatPhysicsBsp = prepared.Structure.PhysicsBsp,
|
||||
FlatContainmentBsp = prepared.Structure.ContainmentBsp,
|
||||
FlatPortalPolygons = prepared.Structure.PortalPolygons,
|
||||
FlatTopology = prepared.Topology,
|
||||
Portals = graphCell.Portals,
|
||||
};
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void SphereInsideCellA_NearPortal_AddsCellB()
|
||||
{
|
||||
|
|
@ -216,4 +236,73 @@ public class CellTransitFindTransitCellsSphereTests
|
|||
|
||||
Assert.True(exitOutside);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void PreparedExitPortal_UsesIndexedPlaneWithoutGraphDictionary()
|
||||
{
|
||||
const uint cellId = 0xA9B40100u;
|
||||
CellPhysics graphCell = MakeCellWithPortalAtRightWall(
|
||||
Matrix4x4.Identity,
|
||||
otherCellId: 0xFFFF,
|
||||
flags: 0);
|
||||
CellPhysics preparedCell = PrepareCell(graphCell, cellId);
|
||||
var cache = PhysicsDataCache.CreateProduction();
|
||||
cache.RegisterCellStructForTest(cellId, preparedCell);
|
||||
|
||||
var candidates = new HashSet<uint>();
|
||||
CellTransit.FindTransitCellsSphere(
|
||||
cache,
|
||||
preparedCell,
|
||||
cellId,
|
||||
new Vector3(2.0f, 0f, 2.5f),
|
||||
sphereRadius: 0.5f,
|
||||
candidates,
|
||||
out bool exitOutside);
|
||||
|
||||
Assert.Null(preparedCell.PortalPolygons);
|
||||
Assert.True(exitOutside);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void PreparedLoadedNeighbor_UsesFlatContainmentWithoutGraphObjects()
|
||||
{
|
||||
const uint cellAId = 0xA9B40100u;
|
||||
const uint cellBId = 0xA9B40101u;
|
||||
CellPhysics graphCellA = MakeCellWithPortalAtRightWall(
|
||||
Matrix4x4.Identity,
|
||||
otherCellId: 0x0101,
|
||||
flags: 2);
|
||||
|
||||
var cellBTransform = Matrix4x4.CreateTranslation(
|
||||
new Vector3(5f, 0f, 0f));
|
||||
Matrix4x4.Invert(cellBTransform, out Matrix4x4 cellBInverse);
|
||||
var graphCellB = new CellPhysics
|
||||
{
|
||||
WorldTransform = cellBTransform,
|
||||
InverseWorldTransform = cellBInverse,
|
||||
Resolved = new Dictionary<ushort, ResolvedPolygon>(),
|
||||
CellBSP = SinglePlaneCellBsp(),
|
||||
};
|
||||
|
||||
CellPhysics preparedCellA = PrepareCell(graphCellA, cellAId);
|
||||
CellPhysics preparedCellB = PrepareCell(graphCellB, cellBId);
|
||||
var cache = PhysicsDataCache.CreateProduction();
|
||||
cache.RegisterCellStructForTest(cellAId, preparedCellA);
|
||||
cache.RegisterCellStructForTest(cellBId, preparedCellB);
|
||||
|
||||
var candidates = new HashSet<uint>();
|
||||
CellTransit.FindTransitCellsSphere(
|
||||
cache,
|
||||
preparedCellA,
|
||||
cellAId,
|
||||
new Vector3(4.75f, 0f, 2.5f),
|
||||
sphereRadius: 0.5f,
|
||||
candidates,
|
||||
out bool exitOutside);
|
||||
|
||||
Assert.Null(preparedCellA.PortalPolygons);
|
||||
Assert.Null(preparedCellB.CellBSP);
|
||||
Assert.Contains(cellBId, candidates);
|
||||
Assert.False(exitOutside);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue