Skip to content
Merged
Show file tree
Hide file tree
Changes from 33 commits
Commits
Show all changes
35 commits
Select commit Hold shift + click to select a range
999b019
[tmp] debug accel limits
adivardi Sep 1, 2025
f801ca1
[tmp] more debug prints
adivardi Sep 2, 2025
6369739
[mppi] fix division by zero
adivardi Sep 2, 2025
907068a
[mppi] apply savitskyGolayFilter before control constraints
adivardi Sep 2, 2025
d28860d
[tmp] comment out some prints
adivardi Sep 4, 2025
24ddf03
[tmp] rearrange accel check
adivardi Sep 4, 2025
7009019
[tmp] comment out more prints
adivardi Sep 9, 2025
52a4315
Revert "Unclamp noise velocity. (#5266)"
adivardi Sep 22, 2025
13195ed
[mppi] color trajectories by cost
adivardi Oct 6, 2025
a3f4b4b
[clean] pub unconstrained optimal trajectory
adivardi Oct 6, 2025
89a2fcb
Reapply "Unclamp noise velocity. (#5266)"
adivardi Sep 26, 2025
76ae5a5
[mppi] implement control cost from paper
adivardi Oct 7, 2025
f5bc281
Revert "[mppi] implement control cost from paper"
adivardi Oct 7, 2025
d48ff16
constrain u_virt_0,1 to force acceleration constraints
adivardi Oct 8, 2025
34049ed
[tmp] only constrain before publish
adivardi Oct 8, 2025
b78c774
[tmp] use unconstrained u_virt for warm start
adivardi Oct 9, 2025
c4afab0
[mppi] constrain velocity & curvature in predict
adivardi Oct 9, 2025
afa6acd
[mppi] clean up: constrain velocity & curvature in predict
adivardi Oct 9, 2025
1f85072
[tmp] only constrain control_seq(0,1) in applyControlSequenceConstraints
adivardi Oct 9, 2025
2f2b546
Revert "[tmp] only constrain control_seq(0,1) in applyControlSequence…
adivardi Oct 9, 2025
fa91535
Undo "[tmp] use unconstrained u_virt for warm start"
adivardi Oct 9, 2025
f8e8f6d
Reapply constrain u_virt_0,1 to force acceleration constraints
adivardi Oct 9, 2025
d3eb7aa
[tmp] debugging changes to be removed
adivardi Oct 9, 2025
8b6bcf7
[tmp] undo changes to predict & applyControlSequenceConstraints
adivardi Oct 13, 2025
bf606a3
[tmp] use prev u_pub for accel constraints
adivardi Oct 13, 2025
2482d08
[tmp] constrain before publish w.r.t to prev u_pub
adivardi Oct 13, 2025
05f2891
Revert PR 5266 again :)
adivardi Oct 13, 2025
4f411b4
[mppi] clean ackermann constraints
adivardi Oct 17, 2025
e36d936
[mppi] publish u0 instead of u1
adivardi Oct 17, 2025
af63f9d
constrain turning radius in predict
adivardi Oct 17, 2025
aadf3c2
Revert "[clean] pub unconstrained optimal trajectory"
adivardi Oct 23, 2025
6a172a0
Clean fix division by zero (from PR 5636)
adivardi Oct 22, 2025
1822d1b
Revert "[mppi] constrain velocity & curvature in predict"
adivardi Oct 23, 2025
2ee9e06
remove all the commented out code
adivardi Oct 23, 2025
3e42f4b
remove debugging prints & code
adivardi Oct 23, 2025
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ struct Trajectories
Eigen::ArrayXXf x;
Eigen::ArrayXXf y;
Eigen::ArrayXXf yaws;
Eigen::ArrayXf costs;

/**
* @brief Reset state data
Expand Down
47 changes: 36 additions & 11 deletions nav2_mppi_controller/include/nav2_mppi_controller/motion_models.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -89,13 +89,41 @@ class MotionModel
0).select(state.vx.col(i - 1) + max_delta_vx,
state.vx.col(i - 1) - min_delta_vx);

state.vx.col(i) = state.cvx.col(i - 1)
state.cvx.col(i - 1) = state.cvx.col(i - 1)
.cwiseMax(lower_bound_vx)
.cwiseMin(upper_bound_vx);
state.vx.col(i) = state.cvx.col(i - 1);

state.wz.col(i) = state.cwz.col(i - 1)
// state.u(i) = state.cu(i-1)
// => we start from current robot speed (state.u(0)) and then apply u_virt (state.cu(i-1))
// but we also need to constrain u_virt before applying it based on static limits (max vel & curvature) to compute
// u_app
// then state.u(i) = u_app(i-1)
// ==> x_k = F(x_k-1, u_app_k-1) = F(x_k-1, g(u_virt_k-1))

// u_app(0) should be limited on acceleration relative to either feedback (state.u(0)) as done now
// TODO 3 or ideally based on last published command

// state.vx.col(i) = state.cvx.col(i - 1)
// .cwiseMax(lower_bound_vx)
// .cwiseMin(upper_bound_vx);

state.cwz.col(i - 1) = state.cwz.col(i - 1)
.cwiseMax(state.wz.col(i - 1) - max_delta_wz)
.cwiseMin(state.wz.col(i - 1) + max_delta_wz);
state.wz.col(i) = state.cwz.col(i - 1);

// state.wz.col(i) = state.cwz.col(i - 1)
// .cwiseMax(state.wz.col(i - 1) - max_delta_wz)
// .cwiseMin(state.wz.col(i - 1) + max_delta_wz);

// constrain u_virt 0 & 1 to make sure accelerations are limited at the first step (state.vx(0) is from feedback)
// also constrain u_virt_1 as this is published as command
// if (i <= 2)
// {
// state.cvx.col(i - 1) = state.vx.col(i);
// state.cwz.col(i - 1) = state.wz.col(i);
// }

if (is_holo) {
auto lower_bound_vy = (state.vy.col(i - 1) >
Expand All @@ -105,9 +133,10 @@ class MotionModel
0).select(state.vy.col(i - 1) + max_delta_vy,
state.vy.col(i - 1) - min_delta_vy);

state.vy.col(i) = state.cvy.col(i - 1)
state.cvy.col(i - 1) = state.cvy.col(i - 1)
.cwiseMax(lower_bound_vy)
.cwiseMin(upper_bound_vy);
state.vy.col(i) = state.cvy.col(i - 1);
}
}
}
Expand Down Expand Up @@ -161,14 +190,10 @@ class AckermannMotionModel : public MotionModel
*/
void applyConstraints(models::ControlSequence & control_sequence) override
{
const auto vx_ptr = control_sequence.vx.data();
auto wz_ptr = control_sequence.wz.data();
int steps = control_sequence.vx.size();
for(int i = 0; i < steps; i++) {
float wz_constrained = fabs(*(vx_ptr + i) / min_turning_r_);
float & wz_curr = *(wz_ptr + i);
wz_curr = utils::clamp(-1 * wz_constrained, wz_constrained, wz_curr);
}
const auto wz_constrained = control_sequence.vx.abs() / min_turning_r_;
control_sequence.wz = control_sequence.wz
.max((-wz_constrained))
.min(wz_constrained);
}

/**
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -145,6 +145,8 @@ class Optimizer
*/
void optimize();

void computeControlSequenceAccel(const models::ControlSequence& control_sequence);

/**
* @brief Prepare state information on new request for trajectory rollouts
* @param robot_pose Pose of the robot at given time
Expand Down Expand Up @@ -190,13 +192,13 @@ class Optimizer
* @brief Update velocities in state
* @param state fill state with velocities on each step
*/
void updateStateVelocities(models::State & state) const;
void updateStateVelocities(models::State & state);

/**
* @brief Update initial velocity in state
* @param state fill state
*/
void updateInitialStateVelocities(models::State & state) const;
void updateInitialStateVelocities(models::State & state);

/**
* @brief predict velocities in state using model
Expand Down Expand Up @@ -280,6 +282,9 @@ class Optimizer
models::Path path_;
geometry_msgs::msg::Pose goal_;
Eigen::ArrayXf costs_;
geometry_msgs::msg::TwistStamped prev_control_twist_;
models::ControlSequence prev_control_sequence_;
Eigen::Array3f initial_velocities_;

CriticData critics_data_ = {
state_, generated_trajectories_, path_, goal_,
Expand Down
18 changes: 18 additions & 0 deletions nav2_mppi_controller/include/nav2_mppi_controller/tools/utils.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -563,6 +563,16 @@ inline void savitskyGolayFilter(
};

// Filter trajectories

// std::cout << "**** SGF:\n";
// std::cout << "wz before: " << control_sequence.wz(Eigen::seq(0, 9)).transpose() << "\n";
// std::cout << "control_history ";
// for (const auto& e : control_history)
// {
// // std::cout << e.wz << " , ";
// }
// std::cout << std::endl;

const models::ControlSequence initial_control_sequence = control_sequence;
applyFilterOverAxis(
control_sequence.vx, initial_control_sequence.vx, control_history[0].vx,
Expand All @@ -574,6 +584,14 @@ inline void savitskyGolayFilter(
control_sequence.wz, initial_control_sequence.wz, control_history[0].wz,
control_history[1].wz, control_history[2].wz, control_history[3].wz);

// std::cout << "after wz: " << control_sequence.wz(Eigen::seq(0, 9)).transpose() << "\n";
// std::cout << "control_history ";
// for (const auto& e : control_history)
// {
// // std::cout << e.wz << " , ";
// }
// std::cout << std::endl;

// Update control history
unsigned int offset = settings.shift_control_sequence ? 1 : 0;
control_history[0] = control_history[1];
Expand Down
5 changes: 5 additions & 0 deletions nav2_mppi_controller/src/critic_manager.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -67,6 +67,11 @@ std::string CriticManager::getFullName(const std::string & name)
void CriticManager::evalTrajectoriesScores(
CriticData & data) const
{
// std::cout << "evalTrajectoriesScores:" << std::endl;
// std::cout << "data.state.vx: " << data.state.vx(Eigen::seq(0, 9), 0).transpose() << "\n";
// std::cout << "data.state.cvx: " << data.state.cvx(Eigen::seq(0, 9), 0).transpose() << "\n";
// std::cout << "data.trajectories.x: " << data.trajectories.x(Eigen::seq(0, 9), 0).transpose() << "\n";

for (const auto & critic : critics_) {
if (data.fail_flag) {
break;
Expand Down
10 changes: 8 additions & 2 deletions nav2_mppi_controller/src/critics/constraint_critic.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -82,8 +82,12 @@ void ConstraintCritic::score(CriticData & data)
if (acker != nullptr) {
auto & vx = data.state.vx;
auto & wz = data.state.wz;
float min_turning_rad = acker->getMinTurningRadius();
auto out_of_turning_rad_motion = (min_turning_rad - (vx.abs() / wz.abs())).max(0.0f);
const float min_turning_rad = acker->getMinTurningRadius();

const float epsilon = 1e-6f;
auto wz_safe = wz.abs().max(epsilon); // Replace small wz values to avoid division by 0
auto out_of_turning_rad_motion = (min_turning_rad - (vx.abs() / wz_safe)).max(0.0f);

if (power_ > 1u) {
data.costs += ((((vx - max_vel_).max(0.0f) + (min_vel_ - vx).max(0.0f) +
out_of_turning_rad_motion) * data.model_dt).rowwise().sum().eval() *
Expand All @@ -92,6 +96,8 @@ void ConstraintCritic::score(CriticData & data)
data.costs += ((((vx - max_vel_).max(0.0f) + (min_vel_ - vx).max(0.0f) +
out_of_turning_rad_motion) * data.model_dt).rowwise().sum().eval() * weight_).eval();
}
// std::cout << "constraint_critic costs after: " << data.costs(Eigen::seq(0, 9)).transpose() << std::endl;

return;
}
}
Expand Down
Loading
Loading