Paparazzi UAS  v7.0_unstable
Paparazzi is a free software Unmanned Aircraft System.
gvf_parametric_2d_bezier_splines.c
Go to the documentation of this file.
1 /*
2  * Copyright (C) 2023 Alfredo Gonzalez Calvin <alfredgo@ucm.es>
3  *
4  * This file is part of paparazzi.
5  *
6  * paparazzi is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation; either version 2, or (at your option)
9  * any later version.
10  *
11  * paparazzi is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with paparazzi; see the file COPYING. If not, see
18  * <http://www.gnu.org/licenses/>.
19  */
20 
21 #include "modules/nav/common_nav.h"
24 
25 #ifndef GVF_PARAMETRIC_2D_BEZIER_SPLINES_KX
26 #define GVF_PARAMETRIC_2D_BEZIER_SPLINES_KX 2.0
27 #endif
28 
29 #ifndef GVF_PARAMETRIC_2D_BEZIER_SPLINES_KY
30 #define GVF_PARAMETRIC_2D_BEZIER_SPLINES_KY 2.0
31 #endif
32 
35  };
36 
37 // Bezier is just an array
38 void create_bezier_spline(bezier_t *bezier, float *px, float *py)
39 {
40 
41  int k, j;
42  j = 0;
43  for (k = 0; k < GVF_PARAMETRIC_2D_BEZIER_N_SEG; k++) {
44  bezier[k].p0[0] = px[j];
45  bezier[k].p0[1] = py[j];
46  bezier[k].p1[0] = px[j + 1];
47  bezier[k].p1[1] = py[j + 1];
48  bezier[k].p2[0] = px[j + 2];
49  bezier[k].p2[1] = py[j + 2];
50  bezier[k].p3[0] = px[j + 3];
51  bezier[k].p3[1] = py[j + 3];
52 
53  // This allows for C^0 continuity (last point is init point)
54  j += 3;
55  }
56 }
57 
58 void gvf_parametric_2d_bezier_splines_info(bezier_t *bezier, float *f1, float *f2, float *f1d, float *f2d, float *f1dd,
59  float *f2dd)
60 {
61  // How can we select in which bezier curve are we? Check w. spline zero: 0 <= t <= 1, spline ones: 1 <= t <= 2;
62  float t = gvf_parametric_control.w;
63  int n_seg = floorl(t);
64  float tt = t - n_seg;
65  if (n_seg < 0) {
66  n_seg = 0; // w could be < 0 in that case go to first point of first segment
67  tt = 0;
68  }
69  // Evalute the corresponding bezier curve
70  float p0x = bezier[n_seg].p0[0]; float p0y = bezier[n_seg].p0[1];
71  float p1x = bezier[n_seg].p1[0]; float p1y = bezier[n_seg].p1[1];
72  float p2x = bezier[n_seg].p2[0]; float p2y = bezier[n_seg].p2[1];
73  float p3x = bezier[n_seg].p3[0]; float p3y = bezier[n_seg].p3[1];
74 
75  // Bézier curves
76 
77  // Curve (x,y)
78  *f1 = (1 - tt) * (1 - tt) * (1 - tt) * p0x + 3 * (1 - tt) * (1 - tt) * tt * p1x + 3 *
79  (1 - tt) * tt * tt * p2x + tt * tt * tt * p3x;
80  *f2 = (1 - tt) * (1 - tt) * (1 - tt) * p0y + 3 * (1 - tt) * (1 - tt) * tt * p1y + 3 *
81  (1 - tt) * tt * tt * p2y + tt * tt * tt * p3y;
82 
83  // First derivative
84  *f1d = 3 * (1 - tt) * (1 - tt) * (p1x - p0x) + 6 * (1 - tt) * tt * (p2x - p1x) + 3 * tt * tt * (p3x - p2x);
85  *f2d = 3 * (1 - tt) * (1 - tt) * (p1y - p0y) + 6 * (1 - tt) * tt * (p2y - p1y) + 3 * tt * tt * (p3y - p2y);
86 
87  // Second derivative
88  *f1dd = 6 * (1 - tt) * (p2x - 2 * p1x + p0x) + 6 * tt * (p3x - 2 * p2x + p1x);
89  *f2dd = 6 * (1 - tt) * (p2y - 2 * p1y + p0y) + 6 * tt * (p3y - 2 * p2y + p1y);
90 
91 
92 }
gvf_parametric_con gvf_parametric_control
Guiding vector field algorithm for 2D and 3D parametric trajectories.
void gvf_parametric_2d_bezier_splines_info(bezier_t *bezier, float *f1, float *f2, float *f1d, float *f2d, float *f1dd, float *f2dd)
#define GVF_PARAMETRIC_2D_BEZIER_SPLINES_KY
gvf_par_2d_bezier_par gvf_parametric_2d_bezier_par
#define GVF_PARAMETRIC_2D_BEZIER_SPLINES_KX
void create_bezier_spline(bezier_t *bezier, float *px, float *py)
#define GVF_PARAMETRIC_2D_BEZIER_N_SEG