private bool drawSpeedLimitHandles(ushort segmentId, bool viewOnly) { if (!LoadingExtension.IsPathManagerCompatible) { return(false); } if (viewOnly && !Options.speedLimitsOverlay) { return(false); } // draw speedlimits over mean middle points of lane beziers if (!segmentCenterByDir.ContainsKey(segmentId)) { segmentCenterByDir.Add(segmentId, new Dictionary <NetInfo.Direction, Vector3>()); TrafficManagerTool.CalculateSegmentCenterByDir(segmentId, segmentCenterByDir[segmentId]); } bool hovered = false; foreach (KeyValuePair <NetInfo.Direction, Vector3> e in segmentCenterByDir[segmentId]) { Vector3 signPos = e.Value; var screenPos = Camera.main.WorldToScreenPoint(signPos); screenPos.y = Screen.height - screenPos.y; if (screenPos.z < 0) { return(false); } var camPos = Singleton <SimulationManager> .instance.m_simulationView.m_position; var diff = signPos - camPos; if (diff.magnitude > TrafficManagerTool.PriorityCloseLod) { return(false); // do not draw if too distant } ItemClass connectionClass = Singleton <NetManager> .instance.m_segments.m_buffer[segmentId].Info.GetConnectionClass(); if (!(connectionClass.m_service == ItemClass.Service.Road || (connectionClass.m_service == ItemClass.Service.PublicTransport && connectionClass.m_subService == ItemClass.SubService.PublicTransportTrain))) { return(false); } var zoom = 1.0f / diff.magnitude * 100f * MainTool.GetBaseZoom(); var size = speedLimitSignSize * zoom; var guiColor = GUI.color; var boundingBox = new Rect(screenPos.x - size / 2, screenPos.y - size / 2, size, size); bool hoveredHandle = !viewOnly && TrafficManagerTool.IsMouseOver(boundingBox); if (hoveredHandle) { // mouse hovering over sign hovered = true; guiColor.a = 0.8f; } else { guiColor.a = 0.5f; } GUI.color = guiColor; try { GUI.DrawTexture(boundingBox, TrafficLightToolTextureResources.SpeedLimitTextures[SpeedLimitManager.GetCustomSpeedLimit(segmentId, e.Key)]); } catch (Exception ex) { Log.Error("segment " + segmentId + " limit: " + SpeedLimitManager.GetCustomSpeedLimit(segmentId, e.Key) + ", ex: " + ex.ToString()); } if (hoveredHandle && Input.GetMouseButton(0)) { // change the speed limit to the selected one ushort speedLimitToSet = SpeedLimitManager.AvailableSpeedLimits[curSpeedLimitIndex]; //Log._Debug($"Setting speed limit of segment {segmentId}, dir {e.Key.ToString()} to {speedLimitToSet}"); SpeedLimitManager.SetSpeedLimit(segmentId, e.Key, speedLimitToSet); // TODO use SegmentTraverser if (Input.GetKey(KeyCode.LeftShift) || Input.GetKey(KeyCode.RightShift)) { NetInfo selectedSegmentInfo = Singleton <NetManager> .instance.m_segments.m_buffer[segmentId].Info; List <object[]> selectedSortedLanes = TrafficManagerTool.GetSortedVehicleLanes(segmentId, selectedSegmentInfo, null); LinkedList <ushort> nodesToProcess = new LinkedList <ushort>(); HashSet <ushort> processedNodes = new HashSet <ushort>(); HashSet <ushort> processedSegments = new HashSet <ushort>(); processedSegments.Add(SelectedSegmentId); ushort selectedStartNodeId = Singleton <NetManager> .instance.m_segments.m_buffer[segmentId].m_startNode; ushort selectedEndNodeId = Singleton <NetManager> .instance.m_segments.m_buffer[segmentId].m_endNode; if (selectedStartNodeId != 0) { nodesToProcess.AddFirst(selectedStartNodeId); } if (selectedEndNodeId != 0) { nodesToProcess.AddFirst(selectedEndNodeId); } while (nodesToProcess.First != null) { ushort nodeId = nodesToProcess.First.Value; nodesToProcess.RemoveFirst(); processedNodes.Add(nodeId); if (Singleton <NetManager> .instance.m_nodes.m_buffer[nodeId].CountSegments() > 2) { continue; // junction. stop. } // explore segments at node for (var s = 0; s < 8; s++) { var otherSegmentId = Singleton <NetManager> .instance.m_nodes.m_buffer[nodeId].GetSegment(s); if (otherSegmentId <= 0 || processedSegments.Contains(otherSegmentId)) { continue; } processedSegments.Add(otherSegmentId); NetInfo segmentInfo = Singleton <NetManager> .instance.m_segments.m_buffer[otherSegmentId].Info; List <object[]> sortedLanes = TrafficManagerTool.GetSortedVehicleLanes(otherSegmentId, segmentInfo, null); if (sortedLanes.Count == selectedSortedLanes.Count) { // number of lanes matches selected segment for (int i = 0; i < sortedLanes.Count; ++i) { object[] selectedLaneData = selectedSortedLanes[i]; object[] laneData = sortedLanes[i]; uint selectedLaneId = (uint)selectedLaneData[0]; uint selectedLaneIndex = (uint)selectedLaneData[2]; NetInfo.Lane selectedLaneInfo = segmentInfo.m_lanes[selectedLaneIndex]; uint laneId = (uint)laneData[0]; uint laneIndex = (uint)laneData[2]; NetInfo.Lane laneInfo = segmentInfo.m_lanes[laneIndex]; if (laneInfo.m_finalDirection == e.Key) { SpeedLimitManager.SetSpeedLimit(otherSegmentId, laneInfo.m_finalDirection, speedLimitToSet); } // apply restrictions of selected segment & lane //VehicleRestrictionsManager.SetAllowedVehicleTypes(otherSegmentId, segmentInfo, laneIndex, laneInfo, laneId, VehicleRestrictionsManager.GetAllowedVehicleTypes(SelectedSegmentId, selectedSegmentInfo, selectedLaneIndex, selectedLaneInfo)); } // add nodes to explore ushort startNodeId = Singleton <NetManager> .instance.m_segments.m_buffer[otherSegmentId].m_startNode; ushort endNodeId = Singleton <NetManager> .instance.m_segments.m_buffer[otherSegmentId].m_endNode; if (startNodeId != 0 && !processedNodes.Contains(startNodeId)) { nodesToProcess.AddFirst(startNodeId); } if (endNodeId != 0 && !processedNodes.Contains(endNodeId)) { nodesToProcess.AddFirst(endNodeId); } } } } } //mouseClickProcessed = true; } guiColor.a = 1f; GUI.color = guiColor; } return(hovered); }
/// <summary> /// Displays lane ids over lanes /// </summary> private void _guiLanes(ushort segmentId, ref NetSegment segment, ref NetInfo segmentInfo) { GUIStyle _counterStyle = new GUIStyle(); Vector3 centerPos = segment.m_bounds.center; var screenPos = Camera.main.WorldToScreenPoint(centerPos); screenPos.y = Screen.height - screenPos.y - 200; if (screenPos.z < 0) { return; } var camPos = Singleton <SimulationManager> .instance.m_simulationView.m_position; var diff = centerPos - camPos; if (diff.magnitude > DebugCloseLod) { return; // do not draw if too distant } var zoom = 1.0f / diff.magnitude * 150f; _counterStyle.fontSize = (int)(11f * zoom); _counterStyle.normal.textColor = new Color(1f, 1f, 0f); uint totalDensity = 0u; uint curLaneId = segment.m_lanes; for (int i = 0; i < segmentInfo.m_lanes.Length; ++i) { if (curLaneId == 0) { break; } if (CustomRoadAI.currentLaneDensities[segmentId] != null && i < CustomRoadAI.currentLaneDensities[segmentId].Length) { totalDensity += CustomRoadAI.currentLaneDensities[segmentId][i]; } curLaneId = Singleton <NetManager> .instance.m_lanes.m_buffer[curLaneId].m_nextLane; } curLaneId = segment.m_lanes; String labelStr = ""; for (int i = 0; i < segmentInfo.m_lanes.Length; ++i) { if (curLaneId == 0) { break; } NetInfo.Lane laneInfo = segmentInfo.m_lanes[i]; labelStr += "Lane idx " + i + ", id " + curLaneId; #if DEBUG labelStr += ", flags: " + ((NetLane.Flags)Singleton <NetManager> .instance.m_lanes.m_buffer[curLaneId].m_flags).ToString() + ", limit: " + SpeedLimitManager.GetCustomSpeedLimit(curLaneId) + " km/h, dir: " + laneInfo.m_direction + ", final: " + laneInfo.m_finalDirection + ", pos: " + String.Format("{0:0.##}", laneInfo.m_position) + ", sim. idx: " + laneInfo.m_similarLaneIndex + " for " + laneInfo.m_vehicleType + "/" + laneInfo.m_laneType; #endif /*if (CustomRoadAI.InStartupPhase) * labelStr += ", in start-up phase"; * else*/ labelStr += ", avg. speed: " + (CustomRoadAI.laneMeanSpeeds[segmentId] != null && i < CustomRoadAI.laneMeanSpeeds[segmentId].Length ? "" + CustomRoadAI.laneMeanSpeeds[segmentId][i] : "?") + " %"; labelStr += ", rel. density: " + (CustomRoadAI.laneMeanRelDensities[segmentId] != null && i < CustomRoadAI.laneMeanRelDensities[segmentId].Length ? "" + CustomRoadAI.laneMeanRelDensities[segmentId][i] : "?") + " %"; #if ABSDENSITY labelStr += ", abs. density: " + (CustomRoadAI.laneMeanAbsDensities[segmentId] != null && i < CustomRoadAI.laneMeanAbsDensities[segmentId].Length ? "" + CustomRoadAI.laneMeanAbsDensities[segmentId][i] : "?") + " %"; #endif #if DEBUG labelStr += " (" + (CustomRoadAI.currentLaneDensities[segmentId] != null && i < CustomRoadAI.currentLaneDensities[segmentId].Length ? "" + CustomRoadAI.currentLaneDensities[segmentId][i] : "?") + "/" + totalDensity + ")"; #endif labelStr += "\n"; curLaneId = Singleton <NetManager> .instance.m_lanes.m_buffer[curLaneId].m_nextLane; } Vector2 dim = _counterStyle.CalcSize(new GUIContent(labelStr)); Rect labelRect = new Rect(screenPos.x - dim.x / 2f, screenPos.y, dim.x, dim.y); GUI.Label(labelRect, labelStr, _counterStyle); }
private bool drawSpeedLimitHandles(ushort segmentId, bool viewOnly) { if (!LoadingExtension.IsPathManagerCompatible) { return(false); } if (viewOnly && !Options.speedLimitsOverlay) { return(false); } // draw speedlimits over mean middle points of lane beziers if (!segmentCenterByDir.ContainsKey(segmentId)) { segmentCenterByDir.Add(segmentId, new Dictionary <NetInfo.Direction, Vector3>()); TrafficManagerTool.CalculateSegmentCenterByDir(segmentId, segmentCenterByDir[segmentId]); } bool hovered = false; foreach (KeyValuePair <NetInfo.Direction, Vector3> e in segmentCenterByDir[segmentId]) { Vector3 signPos = e.Value; var screenPos = Camera.main.WorldToScreenPoint(signPos); screenPos.y = Screen.height - screenPos.y; if (screenPos.z < 0) { return(false); } var camPos = Singleton <SimulationManager> .instance.m_simulationView.m_position; var diff = signPos - camPos; if (diff.magnitude > TrafficManagerTool.PriorityCloseLod) { return(false); // do not draw if too distant } ItemClass connectionClass = Singleton <NetManager> .instance.m_segments.m_buffer[segmentId].Info.GetConnectionClass(); if (!(connectionClass.m_service == ItemClass.Service.Road || (connectionClass.m_service == ItemClass.Service.PublicTransport && connectionClass.m_subService == ItemClass.SubService.PublicTransportTrain))) { return(false); } var zoom = 1.0f / diff.magnitude * 100f * MainTool.GetBaseZoom(); var size = speedLimitSignSize * zoom; var guiColor = GUI.color; var boundingBox = new Rect(screenPos.x - size / 2, screenPos.y - size / 2, size, size); bool hoveredHandle = !viewOnly && TrafficManagerTool.IsMouseOver(boundingBox); if (hoveredHandle) { // mouse hovering over sign hovered = true; guiColor.a = 0.8f; } else { guiColor.a = 0.5f; } GUI.color = guiColor; try { GUI.DrawTexture(boundingBox, TrafficLightToolTextureResources.SpeedLimitTextures[SpeedLimitManager.GetCustomSpeedLimit(segmentId, e.Key)]); } catch (Exception ex) { Log.Error("segment " + segmentId + " limit: " + SpeedLimitManager.GetCustomSpeedLimit(segmentId, e.Key) + ", ex: " + ex.ToString()); } if (hoveredHandle && Input.GetMouseButton(0)) { // change the speed limit to the selected one ushort speedLimitToSet = SpeedLimitManager.AvailableSpeedLimits[curSpeedLimitIndex]; //Log._Debug($"Setting speed limit of segment {segmentId}, dir {e.Key.ToString()} to {speedLimitToSet}"); SpeedLimitManager.SetSpeedLimit(segmentId, e.Key, speedLimitToSet); //mouseClickProcessed = true; } guiColor.a = 1f; GUI.color = guiColor; } return(hovered); }