11#pragma once
22#include " RaidZeroLib/api/Geometry/Point.hpp"
33#include " RaidZeroLib/api/Pathing/ParametricPath.hpp"
4- #include " RaidZeroLib/api/Units/Units.hpp"
54
65namespace rz {
7- using namespace okapi ;
86
7+ /* *
8+ * @brief Cubic Bézier parametric path segment.
9+ *
10+ * A `CubicBezier` represents a smooth parametric curve defined by four control points:
11+ * \f[
12+ * P(t) = (1-t)^3 c_0 + 3(1-t)^2 t c_1 + 3(1-t)t^2 c_2 + t^3 c_3, \quad t \in [0, 1].
13+ * \f]
14+ *
15+ * Each segment is constructed from two knots, which encode both position
16+ * and tangent direction/length at their endpoints. The constructor expands those into
17+ * the four cubic control points:
18+ * - `c₀ = start.getPoint()`
19+ * - `c₁ = start.getForwardControl()`
20+ * - `c₂ = end.getBackwardControl()`
21+ * - `c₃ = end.getPoint()`
22+ *
23+ * **Continuity:** When consecutive segments share the same end/start `Knot`,
24+ * the resulting chain is automatically C⁰ and C¹ continuous at the join.
25+ *
26+ * @see PiecewiseCubicBezier
27+ */
928class CubicBezier : public ParametricPath {
1029 public:
30+ /* *
31+ * @brief Control knot defining both position and tangent handle geometry.
32+ *
33+ * Each `Knot` specifies a point `(x, y)` in meters, an outgoing tangent
34+ * direction `theta` in radians, and a tangent handle length `magnitude` in meters.
35+ * From these, two derived “handles” are computed:
36+ * - Forward control: `point + magnitude * [cos(theta), sin(theta)]`
37+ * - Backward control: `point - magnitude * [cos(theta), sin(theta)]`
38+ *
39+ * These handles are used when constructing Bézier segments:
40+ * the *start* control point contributes its **forward** handle,
41+ * and the *end* control point contributes its **backward** handle.
42+ */
1143 class Knot {
1244 public:
13- Knot (QLength x, QLength y, QAngle theta, QLength magnitude);
45+ /* *
46+ * @brief Constructs a control knot with position, tangent angle, and handle length.
47+ *
48+ * @param x X coordinate (meters).
49+ * @param y Y coordinate (meters).
50+ * @param theta Tangent direction (radians).
51+ * @param magnitude Length of tangent handle (meters).
52+ *
53+ * @pre `magnitude > 0`.
54+ */
55+ Knot (au::QuantityD<au::Meters> x, au::QuantityD<au::Meters> y,
56+ au::QuantityD<au::Radians> theta, au::QuantityD<au::Meters> magnitude) noexcept ;
1457
15- Point getPoint () const ;
58+ // / @brief Returns the anchor position (x, y) of the control knot.
59+ Point getPoint () const noexcept ;
1660
17- Point getForwardControl () const ;
61+ // / @brief Returns the forward (outgoing) control handle in world coordinates.
62+ Point getForwardControl () const noexcept ;
1863
19- Point getBackwardControl () const ;
64+ // / @brief Returns the backward (incoming) control handle in world coordinates.
65+ Point getBackwardControl () const noexcept ;
2066
2167 private:
22- QLength x;
23- QLength y;
24- QAngle theta;
25- QLength magnitude;
68+ au::QuantityD<au::Meters> x;
69+ au::QuantityD<au::Meters> y;
70+ au::QuantityD<au::Radians> theta;
71+ au::QuantityD<au::Meters> magnitude;
2672 };
2773
28- CubicBezier (Knot start, Knot end);
74+ /* *
75+ * @brief Constructs a cubic Bézier segment between two control knots.
76+ *
77+ * The start and end control points define the endpoints and tangents.
78+ * Internally, the four Bézier control points are expanded as:
79+ * ```
80+ * c0 = start.getPoint();
81+ * c1 = start.getForwardControl();
82+ * c2 = end.getBackwardControl();
83+ * c3 = end.getPoint();
84+ * ```
85+ *
86+ * @param start Start control knot.
87+ * @param end End control knot.
88+ */
89+ CubicBezier (const Knot& start, const Knot& end) noexcept ;
2990
30- Point getPoint (double t) const override ;
91+ /* *
92+ * @brief Computes the position P(t) along the cubic Bézier.
93+ *
94+ * @param t Normalized parameter ∈ [0, 1].
95+ * @return 2D point (meters).
96+ */
97+ Point getPoint (double t) const noexcept override ;
3198
32- Point getVelocity (double t) const override ;
99+ /* *
100+ * @brief Computes the first derivative dP/dt at parameter t.
101+ *
102+ * The derivative is given by:
103+ * \f[
104+ * P'(t) = 3(1-t)^2 (c_1 - c_0) + 6(1-t)t (c_2 - c_1) + 3t^2 (c_3 - c_2)
105+ * \f]
106+ *
107+ * @param t Normalized parameter ∈ [0, 1].
108+ * @return Velocity vector (meters per unit t).
109+ */
110+ Point getVelocity (double t) const noexcept override ;
33111
34- Point getAcceleration (double t) const override ;
112+ /* *
113+ * @brief Computes the second derivative d²P/dt² at parameter t.
114+ *
115+ * The expression is:
116+ * \f[
117+ * P''(t) = 6(1-t)(c_2 - 2c_1 + c_0) + 6t(c_3 - 2c_2 + c_1)
118+ * \f]
119+ *
120+ * @param t Normalized parameter ∈ [0, 1].
121+ * @return Acceleration vector (meters per unit t²).
122+ */
123+ Point getAcceleration (double t) const noexcept override ;
35124
36125 private:
37126 Point c0;
@@ -40,4 +129,4 @@ class CubicBezier : public ParametricPath {
40129 Point c3;
41130};
42131
43- } // namespace rz
132+ } // namespace rz
0 commit comments