diff --git a/system/ui/lib/shader_polygon.py b/system/ui/lib/shader_polygon.py index 8dc0d9d8cb..d0c2570d35 100644 --- a/system/ui/lib/shader_polygon.py +++ b/system/ui/lib/shader_polygon.py @@ -15,7 +15,7 @@ uniform int pointCount; uniform vec4 fillColor; uniform vec2 resolution; -uniform bool useGradient; +uniform int useGradient; uniform vec2 gradientStart; uniform vec2 gradientEnd; uniform vec4 gradientColors[8]; @@ -23,24 +23,30 @@ uniform float gradientStops[8]; uniform int gradientColorCount; vec4 getGradientColor(vec2 pos) { - vec2 gradientDir = gradientEnd - gradientStart; - float gradientLength = length(gradientDir); + vec2 gradientDir = gradientEnd - gradientStart; + float gradientLength = length(gradientDir); - if (gradientLength < 0.001) return gradientColors[0]; + if (gradientLength < 0.001) return gradientColors[0]; - vec2 normalizedDir = gradientDir / gradientLength; - vec2 pointVec = pos - gradientStart; - float projection = dot(pointVec, normalizedDir); - float t = clamp(projection / gradientLength, 0.0, 1.0); + float t = clamp(dot(pos - gradientStart, gradientDir) / (gradientLength * gradientLength), 0.0, 1.0); - for (int i = 0; i < gradientColorCount - 1; i++) { - if (t >= gradientStops[i] && t <= gradientStops[i+1]) { - float segmentT = (t - gradientStops[i]) / (gradientStops[i+1] - gradientStops[i]); - return mix(gradientColors[i], gradientColors[i+1], segmentT); + // Binary search for better performance with many stops + int left = 0; + int right = gradientColorCount - 1; + + while (left < right - 1) { + int mid = (left + right) / 2; + if (t <= gradientStops[mid]) { + right = mid; + } else { + left = mid; + } } - } - return gradientColors[gradientColorCount-1]; + if (left == right) return gradientColors[left]; + + float segmentT = (t - gradientStops[left]) / (gradientStops[right] - gradientStops[left]); + return mix(gradientColors[left], gradientColors[right], segmentT); } float distanceToEdge(vec2 p) { @@ -265,11 +271,7 @@ def draw_polygon(points: np.ndarray, color=None, gradient=None): rl.set_shader_value(state.shader, state.locations['resolution'], resolution_ptr, rl.ShaderUniformDataType.SHADER_UNIFORM_VEC2) # Set points - points_ptr = rl.ffi.new("float[]", len(transformed_points) * 2) - flat_points = transformed_points.flatten() - if not flat_points.flags['C_CONTIGUOUS']: - flat_points = np.ascontiguousarray(flat_points) - + flat_points = np.ascontiguousarray(transformed_points.flatten().astype(np.float32)) points_ptr = rl.ffi.cast("float *", flat_points.ctypes.data) rl.set_shader_value_v( state.shader, state.locations['points'], points_ptr, rl.ShaderUniformDataType.SHADER_UNIFORM_VEC2, len(transformed_points) diff --git a/system/ui/onroad/model_renderer.py b/system/ui/onroad/model_renderer.py index 29c750136e..d47454eea7 100644 --- a/system/ui/onroad/model_renderer.py +++ b/system/ui/onroad/model_renderer.py @@ -31,14 +31,14 @@ class ModelRenderer: self._experimental_mode = False self._blend_factor = 1.0 self._prev_allow_throttle = True - self._lane_line_probs = [0.0] * 4 - self._road_edge_stds = [0.0] * 2 + self._lane_line_probs = np.zeros(4, dtype=np.float32) + self._road_edge_stds = np.zeros(2, dtype=np.float32) self._path_offset_z = 1.22 # Initialize empty polygon vertices - self._track_vertices = [] - self._lane_line_vertices = [[] for _ in range(4)] - self._road_edge_vertices = [[] for _ in range(2)] + self._track_vertices = np.empty((0, 2), dtype=np.float32) + self._lane_line_vertices = [np.empty((0, 2), dtype=np.float32) for _ in range(4)] + self._road_edge_vertices = [np.empty((0, 2), dtype=np.float32) for _ in range(2)] self._lead_vertices = [None, None] # Transform matrix (3x3 for car space to screen space) @@ -216,7 +216,7 @@ class ModelRenderer: segment_colors.append(color) if len(segment_colors) < 2: - self.draw_complex_polygon(self._track_vertices, rl.Color(255, 255, 255, 30)) + draw_polygon(self._track_vertices, rl.Color(255, 255, 255, 30)) return # Create gradient specification @@ -342,6 +342,9 @@ class ModelRenderer: left_points.append(left) right_points.append(right) + if not left_points or not right_points: + return np.empty((0, 2), dtype=np.float32) + return np.array(left_points + right_points[::-1], dtype=np.float32) @staticmethod