Skip to content

Commit

Permalink
feat(avoidance): return original lane by red traffic light
Browse files Browse the repository at this point in the history
Signed-off-by: satoshi-ota <satoshi.ota928@gmail.com>
  • Loading branch information
satoshi-ota committed Oct 26, 2023
1 parent c77ffc2 commit d132ac0
Show file tree
Hide file tree
Showing 7 changed files with 245 additions and 24 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -186,11 +186,18 @@
# avoidance distance parameters
longitudinal:
prepare_time: 2.0 # [s]
remain_buffer_distance: 30.0 # [m]
min_prepare_distance: 1.0 # [m]
min_slow_down_speed: 1.38 # [m/s]
buf_slow_down_speed: 0.56 # [m/s]
nominal_avoidance_speed: 8.33 # [m/s]
# return dead line
return_dead_line:
goal:
enable: true # [-]
buffer: 30.0 # [m]
traffic_light:
enable: true # [-]
buffer: 3.0 # [m]

# For yield maneuver
yield:
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
#include "behavior_path_planner/utils/drivable_area_expansion/parameters.hpp"
#include "motion_utils/trajectory/trajectory.hpp"

#include <lanelet2_extension/regulatory_elements/Forward.hpp>
#include <rclcpp/rclcpp.hpp>
#include <route_handler/route_handler.hpp>

Expand Down Expand Up @@ -53,6 +54,7 @@ using autoware_auto_perception_msgs::msg::PredictedObjects;
using autoware_auto_planning_msgs::msg::PathWithLaneId;
using autoware_auto_vehicle_msgs::msg::HazardLightsCommand;
using autoware_auto_vehicle_msgs::msg::TurnIndicatorsCommand;
using autoware_perception_msgs::msg::TrafficSignal;
using autoware_planning_msgs::msg::PoseWithUuidStamped;
using geometry_msgs::msg::AccelWithCovarianceStamped;
using geometry_msgs::msg::PoseStamped;
Expand All @@ -61,6 +63,7 @@ using nav_msgs::msg::Odometry;
using route_handler::RouteHandler;
using tier4_planning_msgs::msg::LateralOffset;
using PlanResult = PathWithLaneId::SharedPtr;
using lanelet::TrafficLight;
using unique_identifier_msgs::msg::UUID;

struct TrafficSignalStamped
Expand Down Expand Up @@ -161,6 +164,14 @@ struct PlannerData
mutable std::vector<double> drivable_area_expansion_prev_curvatures{};
mutable TurnSignalDecider turn_signal_decider;

std::shared_ptr<TrafficSignalStamped> getTrafficSignal(const int id) const
{
if (traffic_light_id_map.count(id) == 0) {
return {};
}
return std::make_shared<TrafficSignalStamped>(traffic_light_id_map.at(id));
}

TurnIndicatorsCommand getTurnSignal(
const PathWithLaneId & path, const TurnSignalInfo & turn_signal_info,
TurnSignalDebugData & debug_data)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -112,6 +112,14 @@ struct AvoidanceParameters
// use intersection area for avoidance
bool use_intersection_areas{false};

// consider avoidance return dead line
bool enable_dead_line_for_goal{false};
bool enable_dead_line_for_traffic_light{false};

// module try to return original path to keep this distance from edge point of the path.
double dead_line_buffer_for_goal{0.0};
double dead_line_buffer_for_traffic_light{0.0};

// max deceleration for
double max_deceleration{0.0};

Expand Down Expand Up @@ -217,9 +225,6 @@ struct AvoidanceParameters
// nominal avoidance sped
double nominal_avoidance_speed{0.0};

// module try to return original path to keep this distance from edge point of the path.
double remain_buffer_distance{0.0};

// The margin is configured so that the generated avoidance trajectory does not come near to the
// road shoulder.
double soft_road_shoulder_margin{1.0};
Expand Down Expand Up @@ -514,6 +519,10 @@ struct AvoidancePlanningData
bool found_avoidance_path{false};

double to_stop_line{std::numeric_limits<double>::max()};

double to_start_point{std::numeric_limits<double>::lowest()};

double to_return_point{std::numeric_limits<double>::max()};
};

/*
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -173,6 +173,20 @@ std::pair<PredictedObjects, PredictedObjects> separateObjectsByPath(
DrivableLanes generateExpandDrivableLanes(
const lanelet::ConstLanelet & lanelet, const std::shared_ptr<const PlannerData> & planner_data,
const std::shared_ptr<AvoidanceParameters> & parameters);

double calcDistanceToReturnDeadLine(
const lanelet::ConstLanelets & lanelets, const PathWithLaneId & path,
const std::shared_ptr<const PlannerData> & planner_data,
const std::shared_ptr<AvoidanceParameters> & parameters);

double calcDistanceToAvoidStartLine(
const lanelet::ConstLanelets & lanelets, const PathWithLaneId & path,
const std::shared_ptr<const PlannerData> & planner_data,
const std::shared_ptr<AvoidanceParameters> & parameters);

std::optional<double> calcDistanceToRedTrafficLight(
const lanelet::ConstLanelets & lanelets, const PathWithLaneId & path,
const std::shared_ptr<const PlannerData> & planner_data);
} // namespace behavior_path_planner::utils::avoidance

#endif // BEHAVIOR_PATH_PLANNER__UTILS__AVOIDANCE__UTILS_HPP_
Original file line number Diff line number Diff line change
Expand Up @@ -288,6 +288,12 @@ void AvoidanceModule::fillFundamentalData(AvoidancePlanningData & data, DebugDat
data.reference_path, 0, data.reference_path.points.size(),
calcSignedArcLength(data.reference_path.points, getEgoPosition(), 0));

data.to_return_point = utils::avoidance::calcDistanceToReturnDeadLine(
data.current_lanelets, data.reference_path_rough, planner_data_, parameters_);

data.to_start_point = utils::avoidance::calcDistanceToAvoidStartLine(
data.current_lanelets, data.reference_path_rough, planner_data_, parameters_);

// target objects for avoidance
fillAvoidanceTargetObjects(data, debug);

Expand Down Expand Up @@ -1066,18 +1072,35 @@ AvoidOutlines AvoidanceModule::generateAvoidOutline(
: 0.0;
const auto offset =
object_parameter.safety_buffer_longitudinal + additional_buffer_longitudinal;
const auto to_shift_end = o.longitudinal - offset;
const auto path_front_to_ego =
avoid_data_.arclength_from_ego.at(avoid_data_.ego_closest_path_index);

al_avoid.start_longitudinal =
std::max(o.longitudinal - offset - feasible_avoid_distance, 1e-3);
// start point (use previous linear shift length as start shift length.)
al_avoid.start_longitudinal = [&]() {
const auto nearest_avoid_distance = std::max(to_shift_end - feasible_avoid_distance, 1e-3);

if (data.to_start_point > to_shift_end) {
return nearest_avoid_distance;
}

const auto minimum_avoid_distance =
helper_.getMinAvoidanceDistance(feasible_shift_length.get() - current_ego_shift);
const auto furthest_avoid_distance = std::max(to_shift_end - minimum_avoid_distance, 1e-3);

return std::clamp(data.to_start_point, nearest_avoid_distance, furthest_avoid_distance);
}();

al_avoid.start_idx = utils::avoidance::findPathIndexFromArclength(
avoid_data_.arclength_from_ego, al_avoid.start_longitudinal + path_front_to_ego);
al_avoid.start = avoid_data_.reference_path.points.at(al_avoid.start_idx).point.pose;
al_avoid.start_shift_length = helper_.getLinearShift(al_avoid.start.position);

// end point
al_avoid.end_shift_length = feasible_shift_length.get();
al_avoid.end_longitudinal = o.longitudinal - offset;
al_avoid.end_longitudinal = to_shift_end;

// misc
al_avoid.id = getOriginalShiftLineUniqueId();
al_avoid.object = o;
al_avoid.object_on_right = utils::avoidance::isOnRight(o);
Expand All @@ -1086,18 +1109,24 @@ AvoidOutlines AvoidanceModule::generateAvoidOutline(
AvoidLine al_return;
{
const auto offset = object_parameter.safety_buffer_longitudinal + base_link2rear + o.length;
// The end_margin also has the purpose of preventing the return path from NOT being
// triggered at the end point.
const auto return_remaining_distance = std::max(
data.arclength_from_ego.back() - o.longitudinal - offset -
parameters_->remain_buffer_distance,
0.0);
const auto to_shift_start = o.longitudinal + offset;

// start point
al_return.start_shift_length = feasible_shift_length.get();
al_return.start_longitudinal = to_shift_start;

// end point
al_return.end_longitudinal = [&]() {
if (data.to_return_point > to_shift_start) {
return std::clamp(
data.to_return_point, to_shift_start, feasible_return_distance + to_shift_start);
}

return to_shift_start + feasible_return_distance;
}();
al_return.end_shift_length = 0.0;
al_return.start_longitudinal = o.longitudinal + offset;
al_return.end_longitudinal =
o.longitudinal + offset + std::min(feasible_return_distance, return_remaining_distance);

// misc
al_return.id = getOriginalShiftLineUniqueId();
al_return.object = o;
al_return.object_on_right = utils::avoidance::isOnRight(o);
Expand Down Expand Up @@ -1795,7 +1824,9 @@ AvoidLineArray AvoidanceModule::addReturnShiftLine(
return ret;
}

const auto remaining_distance = arclength_from_ego.back() - parameters_->remain_buffer_distance;
const auto remaining_distance = std::min(
arclength_from_ego.back() - parameters_->dead_line_buffer_for_goal,
avoid_data_.to_return_point);

// If the avoidance point has already been set, the return shift must be set after the point.
const auto last_sl_distance = avoid_data_.arclength_from_ego.at(last_sl.end_idx);
Expand Down Expand Up @@ -2737,6 +2768,7 @@ void AvoidanceModule::updateDebugMarker(
addObjects(data.other_objects, std::string("LessThanExecutionThreshold"));
addObjects(data.other_objects, std::string("TooNearToGoal"));
addObjects(data.other_objects, std::string("ParallelToEgoLane"));
addObjects(data.other_objects, std::string("BehindReturnPoint"));
}

// shift line pre-process
Expand Down Expand Up @@ -2860,8 +2892,8 @@ void AvoidanceModule::insertReturnDeadLine(
{
const auto & data = avoid_data_;

if (!planner_data_->route_handler->isInGoalRouteSection(data.current_lanelets.back())) {
RCLCPP_DEBUG(getLogger(), "goal is far enough.");
if (data.to_return_point > planner_data_->parameters.forward_path_length) {
RCLCPP_DEBUG(getLogger(), "return dead line is far enough.");
return;
}

Expand All @@ -2873,10 +2905,7 @@ void AvoidanceModule::insertReturnDeadLine(
}

const auto min_return_distance = helper_.getMinAvoidanceDistance(shift_length);

const auto to_goal = calcSignedArcLength(
shifted_path.path.points, getEgoPosition(), shifted_path.path.points.size() - 1);
const auto to_stop_line = to_goal - min_return_distance - parameters_->remain_buffer_distance;
const auto to_stop_line = data.to_return_point - min_return_distance;

// If we don't need to consider deceleration constraints, insert a deceleration point
// and return immediately
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -219,13 +219,23 @@ AvoidanceModuleManager::AvoidanceModuleManager(
std::string ns = "avoidance.avoidance.longitudinal.";
p.prepare_time = getOrDeclareParameter<double>(*node, ns + "prepare_time");
p.min_prepare_distance = getOrDeclareParameter<double>(*node, ns + "min_prepare_distance");
p.remain_buffer_distance = getOrDeclareParameter<double>(*node, ns + "remain_buffer_distance");
p.min_slow_down_speed = getOrDeclareParameter<double>(*node, ns + "min_slow_down_speed");
p.buf_slow_down_speed = getOrDeclareParameter<double>(*node, ns + "buf_slow_down_speed");
p.nominal_avoidance_speed =
getOrDeclareParameter<double>(*node, ns + "nominal_avoidance_speed");
}

// avoidance maneuver (return shift dead line)
{
std::string ns = "avoidance.avoidance.return_dead_line.";
p.enable_dead_line_for_goal = getOrDeclareParameter<bool>(*node, ns + "goal.enable");
p.enable_dead_line_for_traffic_light =
getOrDeclareParameter<bool>(*node, ns + "traffic_light.enable");
p.dead_line_buffer_for_goal = getOrDeclareParameter<double>(*node, ns + "goal.buffer");
p.dead_line_buffer_for_traffic_light =
getOrDeclareParameter<double>(*node, ns + "traffic_light.buffer");
}

// yield
{
std::string ns = "avoidance.yield.";
Expand Down
Loading

0 comments on commit d132ac0

Please sign in to comment.