private void MarkExploredDirections(ref MyNavmeshComponents.ClosedCellInfo cellInfo) { foreach (var direction in Base6Directions.EnumDirections) { var dirFlag = Base6Directions.GetDirectionFlag(direction); if (cellInfo.ExploredDirections.HasFlag(dirFlag)) { continue; } Vector3I dirVec = Base6Directions.GetIntVector(direction); MyCellCoord otherCoord = new MyCellCoord(); otherCoord.Lod = MyVoxelNavigationMesh.NAVMESH_LOD; otherCoord.CoordInLod = m_currentCell + dirVec; if (otherCoord.CoordInLod.X == -1 || otherCoord.CoordInLod.Y == -1 || otherCoord.CoordInLod.Z == -1) { continue; } ulong otherPackedCoord = otherCoord.PackId64(); if (m_triangleLists.ContainsKey(otherPackedCoord)) { m_navmeshComponents.MarkExplored(otherPackedCoord, Base6Directions.GetFlippedDirection(direction)); cellInfo.ExploredDirections |= Base6Directions.GetDirectionFlag(direction); } } m_navmeshComponents.SetExplored(m_packedCoord, cellInfo.ExploredDirections); }
private unsafe void MarkExploredDirections(ref MyNavmeshComponents.ClosedCellInfo cellInfo) { foreach (Base6Directions.Direction direction in Base6Directions.EnumDirections) { Base6Directions.DirectionFlags directionFlag = Base6Directions.GetDirectionFlag(direction); if (!cellInfo.ExploredDirections.HasFlag(directionFlag)) { Vector3I intVector = Base6Directions.GetIntVector(direction); MyCellCoord coord = new MyCellCoord { Lod = 0, CoordInLod = (Vector3I)(this.m_currentCell + intVector) }; if (((coord.CoordInLod.X != -1) && (coord.CoordInLod.Y != -1)) && (coord.CoordInLod.Z != -1)) { ulong key = coord.PackId64(); if (this.m_triangleLists.ContainsKey(key)) { this.m_navmeshComponents.MarkExplored(key, Base6Directions.GetFlippedDirection(direction)); Base6Directions.DirectionFlags *flagsPtr1 = (Base6Directions.DirectionFlags *) ref cellInfo.ExploredDirections; *((sbyte *)flagsPtr1) = *(((byte *)flagsPtr1)) | Base6Directions.GetDirectionFlag(direction); } } } } this.m_navmeshComponents.SetExplored(this.m_packedCoord, cellInfo.ExploredDirections); }
public IMyHighLevelComponent GetComponent(MyHighLevelPrimitive primitive) { ulong num; Base6Directions.DirectionFlags flags; if (!this.m_navmeshComponents.GetComponentCell(primitive.Index, out num)) { return(null); } if (!this.m_navmeshComponents.GetComponentInfo(primitive.Index, num, out flags)) { return(null); } MyCellCoord coord = new MyCellCoord(); coord.SetUnpack(num); foreach (Base6Directions.Direction direction in Base6Directions.EnumDirections) { Base6Directions.DirectionFlags directionFlag = Base6Directions.GetDirectionFlag(direction); if (!flags.HasFlag(directionFlag)) { Vector3I position = (Vector3I)(coord.CoordInLod + Base6Directions.GetIntVector(direction)); if (this.m_exploredCells.Contains(ref position)) { flags |= directionFlag; } } } return(new Component(primitive.Index, flags)); }
public unsafe void MarkExplored(ulong otherCell, Base6Directions.Direction direction) { CellInfo info = new CellInfo(); if (this.m_cellInfos.TryGetValue(otherCell, out info)) { Base6Directions.DirectionFlags *flagsPtr1 = (Base6Directions.DirectionFlags *) ref info.ExploredDirections; *((sbyte *)flagsPtr1) = *(((byte *)flagsPtr1)) | Base6Directions.GetDirectionFlag(direction); this.m_cellInfos[otherCell] = info; } }
public void DebugDraw() { if (MyFakes.DEBUG_DRAW_NAVMESH_EXPLORED_HL_CELLS) { foreach (var cell in m_exploredCells) { BoundingBoxD cellAABB; Vector3I cellCopy = cell; MyVoxelCoordSystems.GeometryCellCoordToWorldAABB(m_mesh.VoxelMapReferencePosition, ref cellCopy, out cellAABB); VRageRender.MyRenderProxy.DebugDrawAABB(cellAABB, Color.Sienna, 1.0f, 1.0f, false); } } if (MyFakes.DEBUG_DRAW_NAVMESH_FRINGE_HL_CELLS) { foreach (var packedCoord in m_navmeshComponents.GetPresentCells()) { MyCellCoord coord = new MyCellCoord(); coord.SetUnpack(packedCoord); Vector3I cellCoord = coord.CoordInLod; if (m_exploredCells.Contains(ref cellCoord)) { MyNavmeshComponents.CellInfo cellInfo = new MyNavmeshComponents.CellInfo(); if (m_navmeshComponents.TryGetCell(packedCoord, out cellInfo)) { for (int i = 0; i < cellInfo.ComponentNum; ++i) { int componentIndex = cellInfo.StartingIndex + i; var primitive = m_mesh.HighLevelGroup.GetPrimitive(componentIndex); foreach (var direction in Base6Directions.EnumDirections) { var dirFlag = Base6Directions.GetDirectionFlag(direction); if (cellInfo.ExploredDirections.HasFlag(dirFlag)) { continue; } if (m_exploredCells.Contains(cellCoord + Base6Directions.GetIntVector(direction))) { continue; } Vector3 dirVec = Base6Directions.GetVector(direction); VRageRender.MyRenderProxy.DebugDrawLine3D(primitive.WorldPosition, primitive.WorldPosition + dirVec * 3.0f, Color.Red, Color.Red, false); } } } } } } }
public void DebugDraw() { if (MyFakes.DEBUG_DRAW_NAVMESH_EXPLORED_HL_CELLS) { foreach (Vector3I vectori in this.m_exploredCells) { BoundingBoxD xd; MyVoxelCoordSystems.GeometryCellCoordToWorldAABB(this.m_mesh.VoxelMapReferencePosition, ref vectori, out xd); MyRenderProxy.DebugDrawAABB(xd, Color.Sienna, 1f, 1f, false, false, false); } } if (MyFakes.DEBUG_DRAW_NAVMESH_FRINGE_HL_CELLS) { foreach (ulong num in this.m_navmeshComponents.GetPresentCells()) { MyCellCoord coord = new MyCellCoord(); coord.SetUnpack(num); Vector3I coordInLod = coord.CoordInLod; if (this.m_exploredCells.Contains(ref coordInLod)) { MyNavmeshComponents.CellInfo cellInfo = new MyNavmeshComponents.CellInfo(); if (this.m_navmeshComponents.TryGetCell(num, out cellInfo)) { int num2 = 0; while (num2 < cellInfo.ComponentNum) { int index = cellInfo.StartingIndex + num2; MyHighLevelPrimitive primitive = this.m_mesh.HighLevelGroup.GetPrimitive(index); Base6Directions.Direction[] enumDirections = Base6Directions.EnumDirections; int num4 = 0; while (true) { if (num4 >= enumDirections.Length) { num2++; break; } Base6Directions.Direction dir = enumDirections[num4]; Base6Directions.DirectionFlags directionFlag = Base6Directions.GetDirectionFlag(dir); if (!cellInfo.ExploredDirections.HasFlag(directionFlag) && !this.m_exploredCells.Contains((Vector3I)(coordInLod + Base6Directions.GetIntVector(dir)))) { Vector3 vector = Base6Directions.GetVector(dir); MyRenderProxy.DebugDrawLine3D(primitive.WorldPosition, primitive.WorldPosition + (vector * 3f), Color.Red, Color.Red, false, false); } num4++; } } } } } } }
public void MarkExplored(ulong otherCell, Base6Directions.Direction direction) { CellInfo info = new CellInfo(); if (m_cellInfos.TryGetValue(otherCell, out info)) { info.ExploredDirections |= Base6Directions.GetDirectionFlag(direction); m_cellInfos[otherCell] = info; } else { Debug.Assert(false, "Inconsistency: Cannot find cell info to mark explored information!"); } }
public void TryClearCell(ulong packedCoord) { if (m_triangleLists.ContainsKey(packedCoord)) { ClearCachedCell(packedCoord); } RemoveExplored(packedCoord); MyNavmeshComponents.CellInfo cellInfo; if (!m_navmeshComponents.TryGetCell(packedCoord, out cellInfo)) { return; } for (int i = 0; i < cellInfo.ComponentNum; ++i) { int componentIndex = cellInfo.StartingIndex + i; m_mesh.HighLevelGroup.RemovePrimitive(componentIndex); } foreach (var direction in Base6Directions.EnumDirections) { Base6Directions.DirectionFlags dirFlag = Base6Directions.GetDirectionFlag(direction); if (cellInfo.ExploredDirections.HasFlag(dirFlag)) { Vector3I dirVec = Base6Directions.GetIntVector(direction); MyCellCoord otherCoord = new MyCellCoord(); otherCoord.SetUnpack(packedCoord); Debug.Assert(otherCoord.Lod == MyVoxelNavigationMesh.NAVMESH_LOD); otherCoord.CoordInLod = otherCoord.CoordInLod + dirVec; MyNavmeshComponents.CellInfo otherCellInfo; if (m_navmeshComponents.TryGetCell(otherCoord.PackId64(), out otherCellInfo)) { Base6Directions.DirectionFlags flippedFlag = Base6Directions.GetDirectionFlag(Base6Directions.GetFlippedDirection(direction)); m_navmeshComponents.SetExplored(otherCoord.PackId64(), otherCellInfo.ExploredDirections & ~flippedFlag); } else { Debug.Assert(false, "Could not get the oposite explored cell!"); } } } m_navmeshComponents.ClearCell(packedCoord, ref cellInfo); }
public IMyHighLevelComponent GetComponent(MyHighLevelPrimitive primitive) { ulong cellIndex; if (m_navmeshComponents.GetComponentCell(primitive.Index, out cellIndex)) { Base6Directions.DirectionFlags exploredDirections; if (m_navmeshComponents.GetComponentInfo(primitive.Index, cellIndex, out exploredDirections)) { MyCellCoord coord = new MyCellCoord(); coord.SetUnpack(cellIndex); // Look at present unexplored cells around this cell. // Their direction can be marked as explored, because there was no geometry when they were being explored foreach (var direction in Base6Directions.EnumDirections) { var directionFlag = Base6Directions.GetDirectionFlag(direction); if (exploredDirections.HasFlag(directionFlag)) { continue; } Vector3I neighbor = coord.CoordInLod + Base6Directions.GetIntVector(direction); if (m_exploredCells.Contains(ref neighbor)) { exploredDirections |= directionFlag; } } return(new Component(primitive.Index, exploredDirections)); } else { return(null); } } else { return(null); } }
public unsafe void TryClearCell(ulong packedCoord) { MyNavmeshComponents.CellInfo info; if (this.m_triangleLists.ContainsKey(packedCoord)) { this.ClearCachedCell(packedCoord); } this.RemoveExplored(packedCoord); if (this.m_navmeshComponents.TryGetCell(packedCoord, out info)) { for (int i = 0; i < info.ComponentNum; i++) { int index = info.StartingIndex + i; this.m_mesh.HighLevelGroup.RemovePrimitive(index); } foreach (Base6Directions.Direction direction in Base6Directions.EnumDirections) { Base6Directions.DirectionFlags directionFlag = Base6Directions.GetDirectionFlag(direction); if (info.ExploredDirections.HasFlag(directionFlag)) { MyNavmeshComponents.CellInfo info2; Vector3I intVector = Base6Directions.GetIntVector(direction); MyCellCoord coord = new MyCellCoord(); coord.SetUnpack(packedCoord); MyCellCoord *coordPtr1 = (MyCellCoord *)ref coord; coordPtr1->CoordInLod = (Vector3I)(coord.CoordInLod + intVector); if (this.m_navmeshComponents.TryGetCell(coord.PackId64(), out info2)) { Base6Directions.DirectionFlags flags2 = Base6Directions.GetDirectionFlag(Base6Directions.GetFlippedDirection(direction)); this.m_navmeshComponents.SetExplored(coord.PackId64(), info2.ExploredDirections & ((byte)~flags2)); } } } this.m_navmeshComponents.ClearCell(packedCoord, ref info); } }
public void ProcessCellComponents() { ProfilerShort.Begin("ProcessCellComponents"); m_triangleLists.Add(m_packedCoord, m_triangleList.GetCopy()); long timeBegin = m_mesh.GetCurrentTimestamp() + 1; long timeEnd = timeBegin; m_currentComponentRel = 0; m_currentComponent = m_navmeshComponents.OpenCell(m_packedCoord); foreach (var triIndex in m_triangleList) { // Skip already visited triangles var triangle = m_mesh.GetTriangle(triIndex); if (m_mesh.VisitedBetween(triangle, timeBegin, timeEnd)) { continue; } m_navmeshComponents.OpenComponent(); // Make sure we have place in m_currentCellConnections if (m_currentComponentRel >= m_currentCellConnections.Count) { m_currentCellConnections.Add(new List <ConnectionInfo>()); } // Find connected component from an unvisited triangle ProfilerShort.Begin("Graph traversal"); m_currentHelper = this; m_navmeshComponents.AddComponentTriangle(triangle, triangle.Center); triangle.ComponentIndex = m_navmeshComponents.OpenComponentIndex; m_mesh.PrepareTraversal(triangle, null, m_processTrianglePredicate); var primitiveEnum = m_mesh.GetEnumerator(); while (primitiveEnum.MoveNext()) { ; } primitiveEnum.Dispose(); ProfilerShort.End(); m_navmeshComponents.CloseComponent(); timeEnd = m_mesh.GetCurrentTimestamp(); m_currentComponentRel++; } MyNavmeshComponents.ClosedCellInfo cellInfo = new MyNavmeshComponents.ClosedCellInfo(); m_navmeshComponents.CloseAndCacheCell(ref cellInfo); // Add new component primitives if (cellInfo.NewCell) { for (int i = 0; i < cellInfo.ComponentNum; ++i) { m_mesh.HighLevelGroup.AddPrimitive(cellInfo.StartingIndex + i, m_navmeshComponents.GetComponentCenter(i)); } } // Connect new components with the others in the neighboring cells for (int i = 0; i < cellInfo.ComponentNum; ++i) { foreach (var connectionInfo in m_currentCellConnections[i]) { if (!cellInfo.ExploredDirections.HasFlag(Base6Directions.GetDirectionFlag(connectionInfo.Direction))) { m_mesh.HighLevelGroup.ConnectPrimitives(cellInfo.StartingIndex + i, connectionInfo.ComponentIndex); } } m_currentCellConnections[i].Clear(); } // Mark explored directions in the navmesh component helper foreach (var direction in Base6Directions.EnumDirections) { var dirFlag = Base6Directions.GetDirectionFlag(direction); if (cellInfo.ExploredDirections.HasFlag(dirFlag)) { continue; } Vector3I dirVec = Base6Directions.GetIntVector(direction); MyCellCoord otherCoord = new MyCellCoord(); otherCoord.Lod = MyVoxelNavigationMesh.NAVMESH_LOD; otherCoord.CoordInLod = m_currentCell + dirVec; if (otherCoord.CoordInLod.X == -1 || otherCoord.CoordInLod.Y == -1 || otherCoord.CoordInLod.Z == -1) { continue; } ulong otherPackedCoord = otherCoord.PackId64(); if (m_triangleLists.ContainsKey(otherPackedCoord)) { m_navmeshComponents.MarkExplored(otherPackedCoord, Base6Directions.GetFlippedDirection(direction)); cellInfo.ExploredDirections |= Base6Directions.GetDirectionFlag(direction); } } m_navmeshComponents.SetExplored(m_packedCoord, cellInfo.ExploredDirections); // Set all the components as expanded for (int i = 0; i < cellInfo.ComponentNum; ++i) { int componentIndex = cellInfo.StartingIndex + i; var component = m_mesh.HighLevelGroup.GetPrimitive(componentIndex); if (component != null) { component.IsExpanded = true; } } ProfilerShort.End(); }