@@ -167,51 +167,41 @@ def trim(self, start : float, end : float) -> Path:
167167
168168 def fit_curve_radius (self , vehicle_position : List [float ], n_points : int ) -> float :
169169 """
170- Fits a circular curve to n upcoming points from the vehicle's current position
171- and returns the radius of that curve.
170+ Calculates the curve radius over the next 3 intervals and returns the largest.
172171
173172 Args:
174173 vehicle_position: Current position of the vehicle [x, y, ...]
175- n_points: Number of upcoming points to consider for curve fitting
176-
174+ n_points: Number of points to sample ahead. Must be >= 5 to allow 3 intervals.
175+
177176 Returns:
178- float: Radius of the fitted circular curve. Returns float('inf') for
179- straight lines or when insufficient points are available.
177+ float: Min radius among 3 consecutive 3-point intervals. Returns float('inf') if not enough data.
180178 """
181- # Find the closest point on the path to the vehicle position
182179 _ , closest_point_idx_float = self .closest_point (vehicle_position )
183-
184- # I use ceil here because we want to be looking forward to the next set of points
185180 closest_point_idx = int (math .ceil (closest_point_idx_float ))
186181
187- # Get indices for n upcoming points
188- start_idx = closest_point_idx
189- end_idx = min (start_idx + n_points , len (self .points ) - 1 )
190-
191- # If we don't have enough points for fitting, return infinite radius (straight line)
192- if end_idx - start_idx < 2 :
193- return float ('inf' )
194-
182+ # Require at least 5 points to form 3 overlapping triplets
183+ total_needed = max (n_points , 5 )
184+ end_idx = min (closest_point_idx + total_needed , len (self .points ))
195185
196- # Extract upcoming points for fitting
197- points_to_fit = self . points [ start_idx : end_idx + 1 ]
198-
199- # Ensure we have at least 3 points for circle fitting
200- if len ( points_to_fit ) < 3 :
201- return float ( 'inf' )
202-
203- # For now, we'll focus on 2D paths
204- # If points are higher dimensional, we'll use only x,y coordinates
205- points_2d = [[ p [ 0 ], p [ 1 ]] for p in points_to_fit ]
206-
207- # Fit circle to points using least squares method
208- try :
209- # Center of circle (h, k) and radius r
210- h , k , r = self . _fit_circle_to_points ( points_2d )
211- return r
212- except :
213- # If fitting fails (e.g., collinear points), return infinite radius
214- return float ('inf ' )
186+ if end_idx - closest_point_idx < 5 :
187+ return float ( '0' )
188+
189+ # Get the next chunk of points
190+ points_to_check = self . points [ closest_point_idx : end_idx ]
191+
192+ # Convert to 2D
193+ points_2d = [[ p [ 0 ], p [ 1 ]] for p in points_to_check ]
194+
195+ radii = []
196+ for i in range ( len ( points_2d ) - 2 ): # Slide a window of 3
197+ triplet = points_2d [ i : i + 3 ]
198+ try :
199+ _ , _ , r = self . _fit_circle_to_points ( triplet )
200+ radii . append ( r )
201+ except :
202+ radii . append ( float ( 'inf' )) # Treat failed fits as straight line
203+
204+ return min ( radii ) if radii else float ('0 ' )
215205
216206 def _fit_circle_to_points (self , points : List [List [float ]]) -> Tuple [float , float , float ]:
217207 """
0 commit comments