@@ -94,6 +94,98 @@ bool isDrivingSameLane(
94
94
95
95
return !same_ids.empty ();
96
96
}
97
+
98
+ bool existShiftSideLane (
99
+ const double start_shift_length, const double end_shift_length, const bool no_left_lanes,
100
+ const bool no_right_lanes)
101
+ {
102
+ constexpr double THRESHOLD = 0.1 ;
103
+ const auto relative_shift_length = end_shift_length - start_shift_length;
104
+
105
+ const auto avoid_shift =
106
+ std::abs (start_shift_length) < THRESHOLD && std::abs (end_shift_length) > THRESHOLD;
107
+ if (avoid_shift) {
108
+ // Left avoid. But there is no adjacent lane. No need blinker.
109
+ if (relative_shift_length > 0.0 && no_left_lanes) {
110
+ return false ;
111
+ }
112
+
113
+ // Right avoid. But there is no adjacent lane. No need blinker.
114
+ if (relative_shift_length < 0.0 && no_right_lanes) {
115
+ return false ;
116
+ }
117
+ }
118
+
119
+ const auto return_shift =
120
+ std::abs (start_shift_length) > THRESHOLD && std::abs (end_shift_length) < THRESHOLD;
121
+ if (return_shift) {
122
+ // Right return. But there is no adjacent lane. No need blinker.
123
+ if (relative_shift_length > 0.0 && no_right_lanes) {
124
+ return false ;
125
+ }
126
+
127
+ // Left return. But there is no adjacent lane. No need blinker.
128
+ if (relative_shift_length < 0.0 && no_left_lanes) {
129
+ return false ;
130
+ }
131
+ }
132
+
133
+ const auto left_middle_shift = start_shift_length > THRESHOLD && end_shift_length > THRESHOLD;
134
+ if (left_middle_shift) {
135
+ // Left avoid. But there is no adjacent lane. No need blinker.
136
+ if (relative_shift_length > 0.0 && no_left_lanes) {
137
+ return false ;
138
+ }
139
+
140
+ // Left return. But there is no adjacent lane. No need blinker.
141
+ if (relative_shift_length < 0.0 && no_left_lanes) {
142
+ return false ;
143
+ }
144
+ }
145
+
146
+ const auto right_middle_shift = start_shift_length < THRESHOLD && end_shift_length < THRESHOLD;
147
+ if (right_middle_shift) {
148
+ // Right avoid. But there is no adjacent lane. No need blinker.
149
+ if (relative_shift_length < 0.0 && no_right_lanes) {
150
+ return false ;
151
+ }
152
+
153
+ // Left avoid. But there is no adjacent lane. No need blinker.
154
+ if (relative_shift_length > 0.0 && no_right_lanes) {
155
+ return false ;
156
+ }
157
+ }
158
+
159
+ return true ;
160
+ }
161
+
162
+ bool straddleRoadBound (
163
+ const ShiftedPath & path, const ShiftLine & shift_line, const lanelet::ConstLanelets & lanes,
164
+ const vehicle_info_util::VehicleInfo & vehicle_info)
165
+ {
166
+ using boost::geometry::intersects;
167
+ using tier4_autoware_utils::pose2transform;
168
+ using tier4_autoware_utils::transformVector;
169
+
170
+ const auto footprint = vehicle_info.createFootprint ();
171
+
172
+ for (const auto & lane : lanes) {
173
+ for (size_t i = shift_line.start_idx ; i < shift_line.end_idx ; ++i) {
174
+ const auto transform = pose2transform (path.path .points .at (i).point .pose );
175
+ const auto shifted_vehicle_footprint = transformVector (footprint, transform);
176
+
177
+ if (intersects (lane.leftBound2d ().basicLineString (), shifted_vehicle_footprint)) {
178
+ return true ;
179
+ }
180
+
181
+ if (intersects (lane.rightBound2d ().basicLineString (), shifted_vehicle_footprint)) {
182
+ return true ;
183
+ }
184
+ }
185
+ }
186
+
187
+ return false ;
188
+ }
97
189
} // namespace
98
190
99
191
#ifdef USE_OLD_ARCHITECTURE
@@ -2565,55 +2657,63 @@ BehaviorModuleOutput AvoidanceModule::plan()
2565
2657
}
2566
2658
2567
2659
// generate path with shift points that have been inserted.
2568
- auto avoidance_path = generateAvoidancePath (path_shifter_);
2569
- debug_data_.output_shift = avoidance_path.shift_length ;
2660
+ ShiftedPath linear_shift_path = utils::avoidance::toShiftedPath (data.reference_path );
2661
+ ShiftedPath spline_shift_path = utils::avoidance::toShiftedPath (data.reference_path );
2662
+ const auto success_spline_path_generation =
2663
+ path_shifter_.generate (&spline_shift_path, true , SHIFT_TYPE::SPLINE);
2664
+ const auto success_linear_path_generation =
2665
+ path_shifter_.generate (&linear_shift_path, true , SHIFT_TYPE::LINEAR);
2666
+
2667
+ // set previous data
2668
+ if (success_spline_path_generation && success_linear_path_generation) {
2669
+ helper_.setPreviousLinearShiftPath (linear_shift_path);
2670
+ helper_.setPreviousSplineShiftPath (spline_shift_path);
2671
+ helper_.setPreviousReferencePath (path_shifter_.getReferencePath ());
2672
+ } else {
2673
+ spline_shift_path = helper_.getPreviousSplineShiftPath ();
2674
+ }
2570
2675
2571
2676
// modify max speed to prevent acceleration in avoidance maneuver.
2572
- modifyPathVelocityToPreventAccelerationOnAvoidance (avoidance_path );
2677
+ modifyPathVelocityToPreventAccelerationOnAvoidance (spline_shift_path );
2573
2678
2574
2679
// post processing
2575
2680
{
2576
2681
postProcess (); // remove old shift points
2577
2682
}
2578
2683
2579
- // set previous data
2580
- {
2581
- ShiftedPath linear_shift_path = utils::avoidance::toShiftedPath (data.reference_path );
2582
- path_shifter_.generate (&linear_shift_path, true , SHIFT_TYPE::LINEAR);
2583
- helper_.setPreviousLinearShiftPath (linear_shift_path);
2584
- helper_.setPreviousSplineShiftPath (avoidance_path);
2585
- helper_.setPreviousReferencePath (data.reference_path );
2586
- }
2587
-
2588
2684
BehaviorModuleOutput output;
2589
2685
2590
2686
// turn signal info
2591
- {
2687
+ if (path_shifter_.getShiftLines ().empty ()) {
2688
+ output.turn_signal_info = getPreviousModuleOutput ().turn_signal_info ;
2689
+ } else {
2592
2690
const auto original_signal = getPreviousModuleOutput ().turn_signal_info ;
2593
- const auto new_signal = calcTurnSignalInfo (avoidance_path);
2594
- const auto current_seg_idx = planner_data_->findEgoSegmentIndex (avoidance_path.path .points );
2691
+ const auto new_signal = calcTurnSignalInfo (
2692
+ linear_shift_path, path_shifter_.getShiftLines ().front (), helper_.getEgoShift (),
2693
+ avoidance_data_, planner_data_);
2694
+ const auto current_seg_idx = planner_data_->findEgoSegmentIndex (spline_shift_path.path .points );
2595
2695
output.turn_signal_info = planner_data_->turn_signal_decider .use_prior_turn_signal (
2596
- avoidance_path .path , getEgoPose (), current_seg_idx, original_signal, new_signal,
2696
+ spline_shift_path .path , getEgoPose (), current_seg_idx, original_signal, new_signal,
2597
2697
planner_data_->parameters .ego_nearest_dist_threshold ,
2598
2698
planner_data_->parameters .ego_nearest_yaw_threshold );
2599
2699
}
2600
2700
2601
2701
// sparse resampling for computational cost
2602
2702
{
2603
- avoidance_path .path =
2604
- utils::resamplePathWithSpline (avoidance_path .path , parameters_->resample_interval_for_output );
2703
+ spline_shift_path .path = utils::resamplePathWithSpline (
2704
+ spline_shift_path .path , parameters_->resample_interval_for_output );
2605
2705
}
2606
2706
2607
2707
avoidance_data_.state = updateEgoState (data);
2608
2708
2609
2709
// update output data
2610
2710
{
2611
- updateEgoBehavior (data, avoidance_path );
2711
+ updateEgoBehavior (data, spline_shift_path );
2612
2712
updateInfoMarker (avoidance_data_);
2613
2713
updateDebugMarker (avoidance_data_, path_shifter_, debug_data_);
2614
2714
}
2615
2715
2616
- output.path = std::make_shared<PathWithLaneId>(avoidance_path .path );
2716
+ output.path = std::make_shared<PathWithLaneId>(spline_shift_path .path );
2617
2717
output.reference_path = getPreviousModuleOutput ().reference_path ;
2618
2718
path_reference_ = getPreviousModuleOutput ().reference_path ;
2619
2719
@@ -2623,7 +2723,7 @@ BehaviorModuleOutput AvoidanceModule::plan()
2623
2723
// Drivable area generation.
2624
2724
generateExtendedDrivableArea (output);
2625
2725
2626
- updateRegisteredRTCStatus (avoidance_path .path );
2726
+ updateRegisteredRTCStatus (spline_shift_path .path );
2627
2727
2628
2728
return output;
2629
2729
}
@@ -3012,86 +3112,98 @@ void AvoidanceModule::initRTCStatus()
3012
3112
candidate_uuid_ = generateUUID ();
3013
3113
}
3014
3114
3015
- TurnSignalInfo AvoidanceModule::calcTurnSignalInfo (const ShiftedPath & path) const
3115
+ TurnSignalInfo AvoidanceModule::calcTurnSignalInfo (
3116
+ const ShiftedPath & path, const ShiftLine & shift_line, const double current_shift_length,
3117
+ const AvoidancePlanningData & data, const std::shared_ptr<const PlannerData> & planner_data) const
3016
3118
{
3017
- const auto shift_lines = path_shifter_.getShiftLines ();
3018
- if (shift_lines.empty ()) {
3119
+ constexpr double THRESHOLD = 0.1 ;
3120
+ const auto & p = planner_data->parameters ;
3121
+ const auto & rh = planner_data->route_handler ;
3122
+ const auto & ego_pose = planner_data->self_odometry ->pose .pose ;
3123
+ const auto & ego_speed = planner_data->self_odometry ->twist .twist .linear .x ;
3124
+
3125
+ if (shift_line.start_idx + 1 > path.shift_length .size ()) {
3126
+ RCLCPP_WARN (rclcpp::get_logger (__func__), " index inconsistency." );
3127
+ return {};
3128
+ }
3129
+
3130
+ if (shift_line.start_idx + 1 > path.path .points .size ()) {
3131
+ RCLCPP_WARN (rclcpp::get_logger (__func__), " index inconsistency." );
3019
3132
return {};
3020
3133
}
3021
3134
3022
- const auto front_shift_line = shift_lines.front ();
3023
- const size_t start_idx = front_shift_line.start_idx ;
3024
- const size_t end_idx = front_shift_line.end_idx ;
3135
+ if (shift_line.end_idx + 1 > path.shift_length .size ()) {
3136
+ RCLCPP_WARN (rclcpp::get_logger (__func__), " index inconsistency." );
3137
+ return {};
3138
+ }
3025
3139
3026
- const auto current_shift_length = helper_. getEgoShift ();
3027
- const double start_shift_length = path. shift_length . at (start_idx );
3028
- const double end_shift_length = path. shift_length . at (end_idx) ;
3029
- const double segment_shift_length = end_shift_length - start_shift_length;
3140
+ if (shift_line. end_idx + 1 > path. path . points . size ()) {
3141
+ RCLCPP_WARN ( rclcpp::get_logger (__func__), " index inconsistency. " );
3142
+ return {} ;
3143
+ }
3030
3144
3031
- const double turn_signal_shift_length_threshold =
3032
- planner_data_->parameters .turn_signal_shift_length_threshold ;
3033
- const double turn_signal_search_time = planner_data_->parameters .turn_signal_search_time ;
3034
- const double turn_signal_minimum_search_distance =
3035
- planner_data_->parameters .turn_signal_minimum_search_distance ;
3145
+ const auto start_shift_length = path.shift_length .at (shift_line.start_idx );
3146
+ const auto end_shift_length = path.shift_length .at (shift_line.end_idx );
3147
+ const auto relative_shift_length = end_shift_length - start_shift_length;
3036
3148
3037
3149
// If shift length is shorter than the threshold, it does not need to turn on blinkers
3038
- if (std::fabs (segment_shift_length ) < turn_signal_shift_length_threshold) {
3150
+ if (std::fabs (relative_shift_length ) < p. turn_signal_shift_length_threshold ) {
3039
3151
return {};
3040
3152
}
3041
3153
3042
3154
// If the vehicle does not shift anymore, we turn off the blinker
3043
- if (std::fabs (end_shift_length - current_shift_length) < 0.1 ) {
3155
+ if (std::fabs (path. shift_length . at (shift_line. end_idx ) - current_shift_length) < THRESHOLD ) {
3044
3156
return {};
3045
3157
}
3046
3158
3047
- // compute blinker start idx and end idx
3048
- const size_t blinker_start_idx = [&]() {
3049
- for (size_t idx = start_idx; idx <= end_idx; ++idx) {
3050
- const double current_shift_length = path.shift_length .at (idx);
3051
- if (current_shift_length > 0.1 ) {
3052
- return idx;
3053
- }
3054
- }
3055
- return start_idx;
3056
- }();
3057
- const size_t blinker_end_idx = end_idx;
3058
-
3059
- const auto blinker_start_pose = path.path .points .at (blinker_start_idx).point .pose ;
3060
- const auto blinker_end_pose = path.path .points .at (blinker_end_idx).point .pose ;
3159
+ const auto get_command = [](const auto & shift_length) {
3160
+ return shift_length > 0.0 ? TurnIndicatorsCommand::ENABLE_LEFT
3161
+ : TurnIndicatorsCommand::ENABLE_RIGHT;
3162
+ };
3061
3163
3062
- const double ego_vehicle_offset =
3063
- planner_data_->parameters .vehicle_info .max_longitudinal_offset_m ;
3064
3164
const auto signal_prepare_distance =
3065
- std::max (getEgoSpeed () * turn_signal_search_time, turn_signal_minimum_search_distance);
3165
+ std::max (ego_speed * p. turn_signal_search_time , p. turn_signal_minimum_search_distance );
3066
3166
const auto ego_front_to_shift_start =
3067
- calcSignedArcLength (path.path .points , getEgoPosition (), blinker_start_pose. position ) -
3068
- ego_vehicle_offset ;
3167
+ calcSignedArcLength (path.path .points , ego_pose. position , shift_line. start_idx ) -
3168
+ p. vehicle_info . max_longitudinal_offset_m ;
3069
3169
3070
3170
if (signal_prepare_distance < ego_front_to_shift_start) {
3071
3171
return {};
3072
3172
}
3073
3173
3074
- bool turn_signal_on_swerving = planner_data_->parameters .turn_signal_on_swerving ;
3174
+ const auto blinker_start_pose = path.path .points .at (shift_line.start_idx ).point .pose ;
3175
+ const auto blinker_end_pose = path.path .points .at (shift_line.end_idx ).point .pose ;
3176
+ const auto get_start_pose = [&](const auto & ego_to_shift_start) {
3177
+ return ego_to_shift_start ? ego_pose : blinker_start_pose;
3178
+ };
3075
3179
3076
3180
TurnSignalInfo turn_signal_info{};
3077
- if (turn_signal_on_swerving) {
3078
- if (segment_shift_length > 0.0 ) {
3079
- turn_signal_info.turn_signal .command = TurnIndicatorsCommand::ENABLE_LEFT;
3080
- } else {
3081
- turn_signal_info.turn_signal .command = TurnIndicatorsCommand::ENABLE_RIGHT;
3082
- }
3083
- } else {
3084
- turn_signal_info.turn_signal .command = TurnIndicatorsCommand::DISABLE;
3085
- }
3086
-
3087
- if (ego_front_to_shift_start > 0.0 ) {
3088
- turn_signal_info.desired_start_point = planner_data_->self_odometry ->pose .pose ;
3089
- } else {
3090
- turn_signal_info.desired_start_point = blinker_start_pose;
3091
- }
3181
+ turn_signal_info.desired_start_point = get_start_pose (ego_front_to_shift_start);
3092
3182
turn_signal_info.desired_end_point = blinker_end_pose;
3093
3183
turn_signal_info.required_start_point = blinker_start_pose;
3094
3184
turn_signal_info.required_end_point = blinker_end_pose;
3185
+ turn_signal_info.turn_signal .command = get_command (relative_shift_length);
3186
+
3187
+ if (!p.turn_signal_on_swerving ) {
3188
+ return turn_signal_info;
3189
+ }
3190
+
3191
+ lanelet::ConstLanelet lanelet;
3192
+ if (!rh->getClosestLaneletWithinRoute (shift_line.end , &lanelet)) {
3193
+ return {};
3194
+ }
3195
+
3196
+ const auto left_lanelets = rh->getAllLeftSharedLinestringLanelets (lanelet, true , true );
3197
+ const auto right_lanelets = rh->getAllRightSharedLinestringLanelets (lanelet, true , true );
3198
+
3199
+ if (!existShiftSideLane (
3200
+ start_shift_length, end_shift_length, left_lanelets.empty (), right_lanelets.empty ())) {
3201
+ return {};
3202
+ }
3203
+
3204
+ if (!straddleRoadBound (path, shift_line, data.current_lanelets , p.vehicle_info )) {
3205
+ return {};
3206
+ }
3095
3207
3096
3208
return turn_signal_info;
3097
3209
}
0 commit comments