@@ -415,17 +415,21 @@ bool withinRoadLanelet(
415
415
}
416
416
417
417
boost::optional<CrosswalkEdgePoints> isReachableCrosswalkEdgePoints (
418
- const TrackedObject & object, const CrosswalkEdgePoints & edge_points ,
419
- const lanelet::LaneletMapPtr & lanelet_map_ptr , const double time_horizon ,
420
- const double min_object_vel)
418
+ const TrackedObject & object, const lanelet::ConstLanelet & target_crosswalk ,
419
+ const CrosswalkEdgePoints & edge_points , const lanelet::LaneletMapPtr & lanelet_map_ptr ,
420
+ const double time_horizon, const double min_object_vel)
421
421
{
422
422
using Point = boost::geometry::model::d2::point_xy<double >;
423
- using Line = boost::geometry::model::linestring<Point >;
424
423
425
424
const auto & obj_pos = object.kinematics .pose_with_covariance .pose .position ;
426
425
const auto & obj_vel = object.kinematics .twist_with_covariance .twist .linear ;
427
426
const auto yaw = tier4_autoware_utils::getRPY (object.kinematics .pose_with_covariance .pose ).z ;
428
427
428
+ lanelet::BasicPoint2d obj_pos_as_lanelet (obj_pos.x , obj_pos.y );
429
+ if (boost::geometry::within (obj_pos_as_lanelet, target_crosswalk.polygon2d ().basicPolygon ())) {
430
+ return {};
431
+ }
432
+
429
433
const auto & p1 = edge_points.front_center_point ;
430
434
const auto & p2 = edge_points.back_center_point ;
431
435
@@ -442,62 +446,66 @@ boost::optional<CrosswalkEdgePoints> isReachableCrosswalkEdgePoints(
442
446
const auto estimated_velocity = std::hypot (obj_vel.x , obj_vel.y );
443
447
const auto is_stop_object = estimated_velocity < stop_velocity_th;
444
448
const auto velocity = std::max (min_object_vel, estimated_velocity);
445
-
446
- lanelet::BasicPoint2d search_point (obj_pos.x , obj_pos.y );
447
- // nearest lanelet
448
449
const auto surrounding_lanelets = lanelet::geometry::findNearest (
449
- lanelet_map_ptr->laneletLayer , search_point , time_horizon * velocity);
450
+ lanelet_map_ptr->laneletLayer , obj_pos_as_lanelet , time_horizon * velocity);
450
451
451
- bool first_intersect_load = false ;
452
- bool second_intersect_load = false ;
453
- std::vector<Point > intersects_first;
454
- std::vector<Point > intersects_second;
455
- for (const auto & lanelet : surrounding_lanelets) {
456
- if (withinLanelet (object, lanelet.second )) {
457
- return {};
458
- }
452
+ const auto isAcrossAnyRoad = [&surrounding_lanelets](const Point & p_src, const Point & p_dst) {
453
+ const auto withinAnyCrosswalk = [&surrounding_lanelets](const Point & p) {
454
+ for (const auto & lanelet : surrounding_lanelets) {
455
+ const lanelet::Attribute attr = lanelet.second .attribute (lanelet::AttributeName::Subtype);
456
+ if (
457
+ (attr.value () == lanelet::AttributeValueString::Crosswalk ||
458
+ attr.value () == lanelet::AttributeValueString::Walkway) &&
459
+ boost::geometry::within (p, lanelet.second .polygon2d ().basicPolygon ())) {
460
+ return true ;
461
+ }
462
+ }
463
+ return false ;
464
+ };
459
465
460
- lanelet::Attribute attr = lanelet.second .attribute (lanelet::AttributeName::Subtype);
461
- if (attr.value () != " road" ) {
462
- continue ;
463
- }
466
+ const auto isExist = [](const Point & p, const std::vector<Point > & points) {
467
+ for (const auto & existingPoint : points) {
468
+ if (boost::geometry::distance (p, existingPoint) < 1e-1 ) {
469
+ return true ;
470
+ }
471
+ }
472
+ return false ;
473
+ };
464
474
465
- {
466
- const Line object_to_entry_point{
467
- {obj_pos.x , obj_pos.y }, {ret.front_center_point .x (), ret.front_center_point .y ()}};
468
- std::vector<Point > tmp_intersects;
469
- boost::geometry::intersection (
470
- object_to_entry_point, lanelet.second .polygon2d ().basicPolygon (), tmp_intersects);
471
- for (const auto & p : tmp_intersects) {
472
- intersects_first.push_back (p);
475
+ std::vector<Point > points_of_intersect;
476
+ const boost::geometry::model::linestring<Point > line{p_src, p_dst};
477
+ for (const auto & lanelet : surrounding_lanelets) {
478
+ const lanelet::Attribute attr = lanelet.second .attribute (lanelet::AttributeName::Subtype);
479
+ if (attr.value () != lanelet::AttributeValueString::Road) {
480
+ continue ;
473
481
}
474
- }
475
482
476
- {
477
- const Line object_to_entry_point{
478
- {obj_pos.x , obj_pos.y }, {ret.back_center_point .x (), ret.back_center_point .y ()}};
479
483
std::vector<Point > tmp_intersects;
480
484
boost::geometry::intersection (
481
- object_to_entry_point , lanelet.second .polygon2d ().basicPolygon (), tmp_intersects);
485
+ line , lanelet.second .polygon2d ().basicPolygon (), tmp_intersects);
482
486
for (const auto & p : tmp_intersects) {
483
- intersects_second.push_back (p);
487
+ if (isExist (p, points_of_intersect) || withinAnyCrosswalk (p)) {
488
+ continue ;
489
+ }
490
+ points_of_intersect.push_back (p);
491
+ if (points_of_intersect.size () >= 2 ) {
492
+ return true ;
493
+ }
484
494
}
485
495
}
486
- }
487
-
488
- if (1 < intersects_first.size ()) {
489
- first_intersect_load = true ;
490
- }
496
+ return false ;
497
+ };
491
498
492
- if (1 < intersects_second.size ()) {
493
- second_intersect_load = true ;
494
- }
499
+ const bool first_intersects_road = isAcrossAnyRoad (
500
+ {obj_pos.x , obj_pos.y }, {ret.front_center_point .x (), ret.front_center_point .y ()});
501
+ const bool second_intersects_road =
502
+ isAcrossAnyRoad ({obj_pos.x , obj_pos.y }, {ret.back_center_point .x (), ret.back_center_point .y ()});
495
503
496
- if (first_intersect_load && second_intersect_load ) {
504
+ if (first_intersects_road && second_intersects_road ) {
497
505
return {};
498
506
}
499
507
500
- if (first_intersect_load && !second_intersect_load ) {
508
+ if (first_intersects_road && !second_intersects_road ) {
501
509
ret.swap ();
502
510
}
503
511
@@ -1197,48 +1205,45 @@ PredictedObject MapBasedPredictionNode::getPredictedObjectAsCrosswalkUser(
1197
1205
predicted_object.kinematics .predicted_paths .push_back (predicted_path);
1198
1206
}
1199
1207
}
1208
+ }
1209
+ // try to find the edge points for all crosswalks and generate path to the crosswalk edge
1210
+ for (const auto & crosswalk : crosswalks_) {
1211
+ const auto edge_points = getCrosswalkEdgePoints (crosswalk);
1212
+
1213
+ const auto reachable_first = hasPotentialToReach (
1214
+ object, edge_points.front_center_point , edge_points.front_right_point ,
1215
+ edge_points.front_left_point , prediction_time_horizon_, min_crosswalk_user_velocity_,
1216
+ max_crosswalk_user_delta_yaw_threshold_for_lanelet_);
1217
+ const auto reachable_second = hasPotentialToReach (
1218
+ object, edge_points.back_center_point , edge_points.back_right_point ,
1219
+ edge_points.back_left_point , prediction_time_horizon_, min_crosswalk_user_velocity_,
1220
+ max_crosswalk_user_delta_yaw_threshold_for_lanelet_);
1221
+
1222
+ if (!reachable_first && !reachable_second) {
1223
+ continue ;
1224
+ }
1200
1225
1201
- // If the object is not crossing the crosswalk, not in the road lanelets, try to find the edge
1202
- // points for all crosswalks and generate path to the crosswalk edge
1203
- } else {
1204
- for (const auto & crosswalk : crosswalks_) {
1205
- const auto edge_points = getCrosswalkEdgePoints (crosswalk);
1206
-
1207
- const auto reachable_first = hasPotentialToReach (
1208
- object, edge_points.front_center_point , edge_points.front_right_point ,
1209
- edge_points.front_left_point , prediction_time_horizon_, min_crosswalk_user_velocity_,
1210
- max_crosswalk_user_delta_yaw_threshold_for_lanelet_);
1211
- const auto reachable_second = hasPotentialToReach (
1212
- object, edge_points.back_center_point , edge_points.back_right_point ,
1213
- edge_points.back_left_point , prediction_time_horizon_, min_crosswalk_user_velocity_,
1214
- max_crosswalk_user_delta_yaw_threshold_for_lanelet_);
1215
-
1216
- if (!reachable_first && !reachable_second) {
1217
- continue ;
1218
- }
1219
-
1220
- const auto reachable_crosswalk = isReachableCrosswalkEdgePoints (
1221
- object, edge_points, lanelet_map_ptr_, prediction_time_horizon_,
1222
- min_crosswalk_user_velocity_);
1223
-
1224
- if (!reachable_crosswalk) {
1225
- continue ;
1226
- }
1226
+ const auto reachable_crosswalk = isReachableCrosswalkEdgePoints (
1227
+ object, crosswalk, edge_points, lanelet_map_ptr_, prediction_time_horizon_,
1228
+ min_crosswalk_user_velocity_);
1227
1229
1228
- PredictedPath predicted_path =
1229
- path_generator_-> generatePathForCrosswalkUser (object, reachable_crosswalk. get ()) ;
1230
- predicted_path. confidence = 1.0 ;
1230
+ if (!reachable_crosswalk) {
1231
+ continue ;
1232
+ }
1231
1233
1232
- if (predicted_path.path .empty ()) {
1233
- continue ;
1234
- }
1235
- // If the predicted path to the crosswalk is crossing the fence, don't use it
1236
- if (doesPathCrossAnyFence (predicted_path)) {
1237
- continue ;
1238
- }
1234
+ PredictedPath predicted_path =
1235
+ path_generator_->generatePathForCrosswalkUser (object, reachable_crosswalk.get ());
1236
+ predicted_path.confidence = 1.0 ;
1239
1237
1240
- predicted_object.kinematics .predicted_paths .push_back (predicted_path);
1238
+ if (predicted_path.path .empty ()) {
1239
+ continue ;
1241
1240
}
1241
+ // If the predicted path to the crosswalk is crossing the fence, don't use it
1242
+ if (doesPathCrossAnyFence (predicted_path)) {
1243
+ continue ;
1244
+ }
1245
+
1246
+ predicted_object.kinematics .predicted_paths .push_back (predicted_path);
1242
1247
}
1243
1248
1244
1249
const auto n_path = predicted_object.kinematics .predicted_paths .size ();
0 commit comments