void TraverseRoadEdge( IntersectionRoadConnection connection, NativeHashMap <IntersectionRoadConnection, bool> visited) { if (visited[connection]) { return; } var prevSampleIndex = CameraPathSamples.Length; var path = new NativeList <RigidTransform>(Allocator.Temp); while (!visited[connection]) { visited[connection] = true; AppendRoadSamples(path, connection); var roadData = RoadCenterLineDataComponents[connection.Road]; var intersectionEntity = GetIntersection(roadData, connection.Direction); if (intersectionEntity == Entity.Null) { connection.Direction = connection.InverseDirection; } else { var cornerEntity = GetCorner(connection, intersectionEntity); AppendRightTurnCornerSamples(path, cornerEntity); connection = IntersectionCornerComponents[cornerEntity].LeftRoad; } } // var culledSpline = SplineUtility.RemoveOverlappingPoints(path, Allocator.Temp, 3f); // var splineLength = SplineUtility.SplineLength(path); // var culledSpline = SplineUtility.EvenlyRemapSpline(path, (int)(splineLength / 2f), Allocator.Temp); CameraPathSamples.AddRange(path); CameraPathSampleRanges.Add(new PlacementPathSampleRange { StartIndex = prevSampleIndex, Length = path.Length }); // culledSpline.Dispose(); path.Dispose(); }
Entity GetCorner(IntersectionRoadConnection connection, Entity intersection) { var intersectionRoads = IntersectionRoadConnections[intersection].AsNativeArray(); var connectionIndex = 0; for (; connectionIndex < intersectionRoads.Length; connectionIndex++) { var intersectionRoad = intersectionRoads[connectionIndex]; if (intersectionRoad.Road == connection.Road && intersectionRoad.InverseDirection == connection.Direction) { break; } } return(IntersectionCornerEntityRefs[intersection].Reinterpret <Entity>()[connectionIndex]); }
public void Execute() { if (RoadEntities.Length == 0) { return; } var visited = new NativeHashMap <IntersectionRoadConnection, bool>(RoadEntities.Length * 2, Allocator.Temp); // Mark all road sides as unvisited for (var i = 0; i < RoadEntities.Length; i++) { var roadEntity = RoadEntities[i]; visited.Add(new IntersectionRoadConnection { Road = roadEntity, Direction = IntersectionRoadDirection.Incoming }, false); visited.Add(new IntersectionRoadConnection { Road = roadEntity, Direction = IntersectionRoadDirection.Outgoing }, false); } // Calculate dead-end road edges first with a depth-first traversal for (var i = 0; i < RoadEntities.Length; i++) { var roadEntity = RoadEntities[i]; var connection = new IntersectionRoadConnection { Road = roadEntity, Direction = IntersectionRoadDirection.Outgoing }; TraverseRoadEdge(connection, visited); connection.Direction = IntersectionRoadDirection.Incoming; TraverseRoadEdge(connection, visited); } }
void TraverseRoadEdge( IntersectionRoadConnection connection, NativeHashMap <IntersectionRoadConnection, bool> visited) { if (visited[connection]) { return; } var prevSampleIndex = PlacementPathSamples.Length; var path = new NativeList <RigidTransform>(Allocator.Temp); while (!visited[connection]) { visited[connection] = true; AppendRoadSamples(path, connection); var roadData = RoadCenterLineDataComponents[connection.Road]; var intersectionEntity = GetIntersection(roadData, connection.Direction); if (intersectionEntity == Entity.Null) { connection.Direction = connection.InverseDirection; } else { var cornerEntity = GetCorner(connection, intersectionEntity); AppendRightTurnCornerSamples(path, cornerEntity); connection = IntersectionCornerComponents[cornerEntity].LeftRoad; } } PlacementPathSamples.AddRange(path); PlacementPathSampleRanges.Add(new PlacementPathSampleRange { StartIndex = prevSampleIndex, Length = path.Length }); }
void AppendRoadSamples(NativeList <RigidTransform> samples, IntersectionRoadConnection connection) { var centerLineSamples = RoadCenterLineSamples[connection.Road] .Reinterpret <RigidTransform>().AsNativeArray(); var lateralProfileEntity = LateralProfileEntityRefs[connection.Road].Reinterpret <Entity>()[0]; var lateralProfileSamples = LateralProfileSampleBuffers[lateralProfileEntity].Reinterpret <float2>(); var lateralOffset = connection.Direction == IntersectionRoadDirection.Incoming ? lateralProfileSamples[0].x : lateralProfileSamples[lateralProfileSamples.Length - 1].x; var offset = new float3(lateralOffset, 0f, 0f); var offsetSamples = SplineUtility.OffsetSpline(centerLineSamples, offset, Allocator.Temp); if (connection.Direction == IntersectionRoadDirection.Incoming) { SplineUtility.ReverseSpline(offsetSamples); } samples.AddRange(offsetSamples); offsetSamples.Dispose(); }
void AppendRoadSamples(NativeList <RigidTransform> samples, IntersectionRoadConnection connection) { var centerLineSamples = RoadCenterLineSamples[connection.Road] .Reinterpret <RigidTransform>().AsNativeArray(); var lateralProfileEntity = LateralProfileEntityRefs[connection.Road].Reinterpret <Entity>()[0]; var lateralProfile = LateralProfileComponents[lateralProfileEntity]; var lateralOffset = connection.Direction == IntersectionRoadDirection.Incoming ? lateralProfile.LeftDrivableOffset.x + OffsetFromCurb : lateralProfile.RightDrivableOffset.x - OffsetFromCurb; var offset = new float3(lateralOffset, 0f, 0f); var offsetSamples = SplineUtility.OffsetSpline(centerLineSamples, offset, Allocator.Temp); if (connection.Direction == IntersectionRoadDirection.Incoming) { SplineUtility.ReverseSpline(offsetSamples); } samples.AddRange(offsetSamples); offsetSamples.Dispose(); }