40template <
class Distance,
class Input>
75 constexpr bool IsFinished(
const units::second_t& t)
const {
140 : m_constraints(constraints) {}
158 const State& goal)
const {
159 auto direction = ShouldFlipInput(current, goal) ? -1 : 1;
160 auto u = direction * m_constraints.
maxInput;
167 }
else if (t < timing.inflectionTime) {
168 return {ComputeDistanceFromTime(t, u, current),
169 ComputeVelocityFromTime(t, u, current)};
170 }
else if (t < timing.totalTime) {
171 return {ComputeDistanceFromTime(t - timing.totalTime, -u, goal),
172 ComputeVelocityFromTime(t - timing.totalTime, -u, goal)};
187 const State& goal)
const {
188 auto direction = ShouldFlipInput(current, goal) ? -1 : 1;
189 auto u = direction * m_constraints.
maxInput;
202 const State& goal)
const {
205 return timing.totalTime;
217 const State& goal)
const {
218 auto direction = ShouldFlipInput(current, goal) ? -1 : 1;
219 auto u = direction * m_constraints.
maxInput;
241 if (current == goal) {
245 auto inflectionVelocity = SolveForInflectionVelocity(u, current, goal);
246 auto inflectionPosition =
247 ComputeDistanceFromVelocity(inflectionVelocity, -u, goal);
249 return {inflectionPosition, inflectionVelocity};
264 const State& inflectionPoint,
270 units::second_t inflectionT_forward;
285 inflectionPoint.velocity) < epsilon) {
286 auto solvableV = inflectionPoint.velocity;
287 units::second_t t_to_solvable_v;
291 t_to_solvable_v = 0_s;
292 x_at_solvable_v = current.position;
295 solvableV += u_dir * epsilon;
297 solvableV -= u_dir * epsilon;
301 ComputeTimeFromVelocity(solvableV, u, current.velocity);
302 x_at_solvable_v = ComputeDistanceFromVelocity(solvableV, u, current);
305 inflectionT_forward =
306 t_to_solvable_v + u_dir *
307 (inflectionPoint.position - x_at_solvable_v) /
310 inflectionT_forward = ComputeTimeFromVelocity(inflectionPoint.velocity, u,
314 auto inflectionT_backward =
315 ComputeTimeFromVelocity(inflectionPoint.velocity, -u, goal.velocity);
317 return {inflectionT_forward, inflectionT_forward - inflectionT_backward};
330 constexpr Distance_t ComputeDistanceFromTime(
const units::second_t& time,
332 const State& initial)
const {
333 auto A = m_constraints.
A;
334 auto B = m_constraints.
B;
337 return initial.position +
353 constexpr Velocity_t ComputeVelocityFromTime(
const units::second_t& time,
355 const State& initial)
const {
356 auto A = m_constraints.
A;
357 auto B = m_constraints.
B;
374 constexpr units::second_t ComputeTimeFromVelocity(
377 auto A = m_constraints.
A;
378 auto B = m_constraints.
B;
381 return units::math::log((A * velocity + B * u) / (A * initial + B * u)) / A;
396 const State& initial)
const {
397 auto A = m_constraints.
A;
398 auto B = m_constraints.
B;
401 return initial.position + (velocity - initial.velocity) / A -
404 (A * initial.velocity + B * u));
418 const State& current,
419 const State& goal)
const {
420 auto A = m_constraints.
A;
421 auto B = m_constraints.
B;
426 auto position_delta = goal.position - current.position;
427 auto velocity_delta = goal.velocity - current.velocity;
429 auto scalar = (A * current.velocity + B * u) * (A * goal.velocity - B * u);
430 auto power = -A / B / u * (A * position_delta - velocity_delta);
435 if (-1e-9 < c.value() && c.value() < 0) {
453 constexpr bool ShouldFlipInput(
const State& current,
454 const State& goal)
const {
457 auto v0 = current.velocity;
458 auto xf = goal.position;
459 auto vf = goal.velocity;
461 auto x_forward = ComputeDistanceFromVelocity(vf, u, current);
462 auto x_reverse = ComputeDistanceFromVelocity(vf, -u, current);
465 return xf < x_reverse;
469 return xf < x_forward;
474 auto c = xf >= x_forward;
475 auto d = xf >= x_reverse;
477 return (a && !d) || (
b && !c) || (!c && !d);
480 Constraints m_constraints;
Profile constraints.
Definition ExponentialProfile.h:83
Input_t maxInput
Maximum unsigned input voltage.
Definition ExponentialProfile.h:113
A_t A
The State-Space 1x1 system matrix.
Definition ExponentialProfile.h:116
constexpr Velocity_t MaxVelocity() const
Computes the max achievable velocity for an Exponential Profile.
Definition ExponentialProfile.h:110
constexpr Constraints(Input_t maxInput, A_t A, B_t B)
Constructs constraints for an ExponentialProfile.
Definition ExponentialProfile.h:92
constexpr Constraints(Input_t maxInput, kV_t kV, kA_t kA)
Constructs constraints for an ExponentialProfile from characteristics.
Definition ExponentialProfile.h:102
B_t B
The State-Space 1x1 input matrix.
Definition ExponentialProfile.h:119
Profile timing.
Definition ExponentialProfile.h:61
constexpr bool IsFinished(const units::second_t &t) const
Decides if the profile is finished by time t.
Definition ExponentialProfile.h:75
units::second_t totalTime
Total profile time.
Definition ExponentialProfile.h:67
units::second_t inflectionTime
Profile inflection time.
Definition ExponentialProfile.h:64
Profile state.
Definition ExponentialProfile.h:123
constexpr bool operator==(const State &) const =default
Distance_t position
The position at this state.
Definition ExponentialProfile.h:126
Velocity_t velocity
The velocity at this state.
Definition ExponentialProfile.h:129
A Exponential-shaped velocity profile.
Definition ExponentialProfile.h:41
constexpr units::second_t TimeLeftUntil(const State ¤t, const State &goal) const
Calculates the time it will take for this profile to reach the goal state.
Definition ExponentialProfile.h:201
constexpr ExponentialProfile(Constraints constraints)
Constructs a ExponentialProfile.
Definition ExponentialProfile.h:139
units::compound_unit< Input, units::inverse< Velocity > > KV
Definition ExponentialProfile.h:53
units::compound_unit< Input, units::inverse< Acceleration > > KA
Definition ExponentialProfile.h:55
units::unit_t< Distance > Distance_t
Definition ExponentialProfile.h:43
units::unit_t< Velocity > Velocity_t
Definition ExponentialProfile.h:46
units::compound_unit< Distance, units::inverse< units::seconds > > Velocity
Definition ExponentialProfile.h:44
constexpr ExponentialProfile & operator=(ExponentialProfile &&)=default
constexpr ExponentialProfile(const ExponentialProfile &)=default
units::unit_t< Input > Input_t
Definition ExponentialProfile.h:49
constexpr State CalculateInflectionPoint(const State ¤t, const State &goal) const
Calculates the point after which the fastest way to reach the goal state is to apply input in the opp...
Definition ExponentialProfile.h:186
constexpr ExponentialProfile(ExponentialProfile &&)=default
units::compound_unit< Velocity, units::inverse< units::seconds > > Acceleration
Definition ExponentialProfile.h:47
constexpr ProfileTiming CalculateProfileTiming(const State ¤t, const State &goal) const
Calculates the time it will take for this profile to reach the inflection point, and the time it will...
Definition ExponentialProfile.h:216
constexpr State Calculate(const units::second_t &t, const State ¤t, const State &goal) const
Calculates the position and velocity for the profile at a time t where the current state is at time t...
Definition ExponentialProfile.h:157
constexpr ExponentialProfile & operator=(const ExponentialProfile &)=default
constexpr UnitType abs(const UnitType x) noexcept
Compute absolute value.
Definition math.h:726
constexpr auto sqrt(const UnitType &value) noexcept -> unit_t< square_root< typename units::traits::unit_t_traits< UnitType >::unit_type >, typename units::traits::unit_t_traits< UnitType >::underlying_type, linear_scale >
computes the square root of value
Definition math.h:485
constexpr dimensionless::scalar_t log(const ScalarUnit x) noexcept
Compute natural logarithm.
Definition math.h:351
constexpr dimensionless::scalar_t exp(const ScalarUnit x) noexcept
Compute exponential function.
Definition math.h:334
typename units::detail::compound_impl< U, Us... >::type compound_unit
Represents a unit type made up from other units.
Definition base.h:1438
unit< std::ratio< 1 >, units::category::scalar_unit > scalar
Definition base.h:2514