40 bool new_run,
const Time& t, ReferenceTrajectoryInterface* sref,
const Eigen::VectorXd* prev_u,
41 double prev_u_dt, ReferenceTrajectoryInterface* xinit, ReferenceTrajectoryInterface* uinit)
43 assert(x0.size() == dynamics->getStateDimension());
44 assert(xref.getDimension() == x0.size());
45 assert(uref.getDimension() == dynamics->getInputDimension());
47 GridUpdateResult result;
61 if (!uref.isCached(
getDt(),
n, t)) uref.precompute(
getDt(),
n, t);
62 if (sref && !sref->isCached(
getDt(),
n, t)) sref->precompute(
getDt(),
n, t);
63 if (xinit && !xinit->isCached(
getDt(),
n, t)) xinit->precompute(
getDt(),
n, t);
64 if (uinit && !uinit->isCached(
getDt(),
n, t)) uinit->precompute(
getDt(),
n, t);
67 if (prev_u && prev_u->size() > 0)
82 if (xref.isStatic() && !xinit)
88 initializeSequences(x0, xref.getReferenceCached(
n - 1), xinit ? *xinit : xref, uinit ? *uinit : uref, nlp_fun);
101 _x_seq.front().values() = x0;
103 for (
int i = 0; i <
_xf_fixed.size(); ++i)
112 if (new_run || result.updated())
115 result.edges_updated = nlp_fun.update(
getN(), t.toSec(), xref, uref, sref,
hasSingleDt(), x0, {
getDt()},
122 if (result.updated())
128 result.edges_updated =
true;
135 NlpFunctions& nlp_fun)
144 nlp_fun.checkAndInitializeBoundDimensions(x0.size(), uref.getDimension());
151 int num_intervals = n_init - 1;
154 Eigen::VectorXd dir = xf - x0;
155 double dist = dir.norm();
156 if (dist != 0) dir /= dist;
157 double step = dist / num_intervals;
159 for (
int k = 0; k < num_intervals; ++k)
162 _x_seq.emplace_back(x0 + (
double)k * step * dir, nlp_fun.x_lb, nlp_fun.x_ub);
164 _u_seq.emplace_back(uref.getReferenceCached(k), nlp_fun.u_lb, nlp_fun.u_ub);
170 _x_seq.front().setFixed(
true);
175 assert(
_x_seq.size() > 0);
182 ReferenceTrajectoryInterface& uref, NlpFunctions& nlp_fun)
197 nlp_fun.checkAndInitializeBoundDimensions(x0.size(), uref.getDimension());
204 int num_intervals = n_init - 1;
206 _x_seq.emplace_back(x0, nlp_fun.x_lb, nlp_fun.x_ub);
207 _u_seq.emplace_back(uref.getReferenceCached(0), nlp_fun.u_lb, nlp_fun.u_ub);
208 for (
int k = 1; k < num_intervals; ++k)
211 _x_seq.emplace_back(xref.getReferenceCached(k), nlp_fun.x_lb, nlp_fun.x_ub);
213 _u_seq.emplace_back(uref.getReferenceCached(k), nlp_fun.u_lb, nlp_fun.u_ub);
219 _x_seq.front().setFixed(
true);
224 assert(
_x_seq.size() > 1);
234 if (num_shift <= 0)
return;
236 if (num_shift >
getN() - 2)
247 for (
int i = 0; i <
getN() - num_shift; ++i)
249 int idx = i + num_shift;
250 if (idx ==
getN() - 1)
262 int idx =
getN() - num_shift;
268 for (
int i = 0; i < num_shift; ++i, ++idx)
274 if (i == num_shift - 1)
293 double first_dist = (x0 -
_x_seq.front().values()).norm();
294 if (
std::abs(first_dist) < 1e-12)
return 0;
300 int num_interv =
getN() - 1;
302 double dist_cache = first_dist;
304 int num_keep_interv = 1;
305 int lookahead =
std::min(num_interv - num_keep_interv, 20);
309 for (
int i = 1; i <= lookahead; ++i)
311 dist = (x0 -
_x_seq[i].values()).norm();
312 if (dist < dist_cache)
329 u0 =
_u_seq.front().values();
357 PRINT_ERROR_NAMED(
"Dimensions mismatch between xf_fixed and xf. Setting xf_fixed to false.");
367 if (vtx.getDimension() == nlp_fun.
x_lb.size())
368 vtx.setLowerBounds(nlp_fun.
x_lb);
370 PRINT_ERROR_NAMED(
"Cannot update lower state bounds due to dimensions mismatch");
372 if (vtx.getDimension() == nlp_fun.
x_ub.size())
373 vtx.setUpperBounds(nlp_fun.
u_ub);
375 PRINT_ERROR_NAMED(
"Cannot update upper state bounds due to dimensions mismatch");
380 if (vtx.getDimension() == nlp_fun.
u_lb.size())
381 vtx.setLowerBounds(nlp_fun.
u_lb);
383 PRINT_ERROR_NAMED(
"Cannot update lower control input bounds due to dimensions mismatch");
385 if (vtx.getDimension() == nlp_fun.
u_ub.size())
386 vtx.setUpperBounds(nlp_fun.
u_ub);
388 PRINT_ERROR_NAMED(
"Cannot update upper control input bounds due to dimensions mismatch");
401 if (
n == n_new)
return;
405 PRINT_ERROR_NAMED(
"We currently need _nlp_fun to be valid in order to retrieve bounds");
418 int num_interv =
n - 1;
420 double dt_old =
getDt();
422 double dt_new = dt_old * double(
n - 1) / double(n_new - 1);
426 double t_old_p1 = dt_old;
428 for (
int idx_new = 1; idx_new < n_new - 1; ++idx_new)
432 t_new = dt_new * double(idx_new);
433 while (t_new >
double(idx_old) * dt_old && idx_old <
n)
437 t_old_p1 = double(idx_old) * dt_old;
439 const Eigen::VectorXd& x_prev = x_seq_old.col(idx_old - 1);
440 const Eigen::VectorXd& x_cur = (idx_old <
n - 1) ? x_seq_old.col(idx_old) :
_xf.
values();
442 if (idx_new < num_interv)
445 _x_seq[idx_new].values() = x_prev + (t_new - (t_old_p1 - dt_old)) / dt_old * (x_cur - x_prev);
449 _u_seq[idx_new].values() = u_seq_old.col(idx_old - 1);
507 vertices.push_back(&
_xf);
508 vertices.push_back(&
_dt);
520 for (
int i = 0; i <
n - 1; ++i)
531 if (x_sequence) x_sequence->clear();
532 if (u_sequence) u_sequence->clear();
544 for (int i = 0; i < _x_seq.size(); ++i)
546 x_sequence->add(t, _x_seq[i].values());
548 if (t > t_max) break;
550 if (t <= t_max) x_sequence->add(t, _xf.values());
556 for (int i = 0; i < _u_seq.size(); ++i)
558 u_sequence->add(t, _u_seq[i].values());
560 if (t > t_max) break;
562 // duplicate last u to have the sampe time stamps as x_sequence
563 if (t <= t_max) u_sequence->add(t, _u_seq.back().values());