17 #include <vtkParametricFunctionSource.h>
18 #include <vtkParametricSpline.h>
19 #include <vtkPolyData.h>
20 #include <vtkSCurveSpline.h>
21 #include <vtkSmartPointer.h>
24 #include <pcl/Vertices.h>
25 #include <pcl/common/common.h>
26 #include <vtkPolyLine.h>
30 using namespace Eigen;
34 CurveFitting::CurveFitting() {}
36 CurveFitting::~CurveFitting() { cloud->clear(); }
41 points->InsertNextPoint(p.u);
53 spline->SetXSpline(xSpline);
54 spline->SetYSpline(ySpline);
55 spline->SetZSpline(zSpline);
61 functionSource->SetParametricFunction(spline);
62 functionSource->Update();
64 vtkPolyData *
result = functionSource->GetOutput();
65 if (!
result)
return nullptr;
70 void CurveFitting::setInputcloud(PointCloudT::Ptr input_cloud) {
72 getMinMax3D(*input_cloud, point_min, point_max);
75 void CurveFitting::grid_mean_xyz(
double x_resolution,
77 vector<double> &x_mean,
78 vector<double> &y_mean,
79 vector<double> &z_mean,
80 PointCloudT::Ptr &new_cloud) {
81 if (y_resolution <= 0) {
82 y_resolution = point_max.y - point_min.y;
84 int raster_rows, raster_cols;
85 raster_rows =
ceil((point_max.x - point_min.x) / x_resolution);
86 raster_cols =
ceil((point_max.y - point_min.y) / y_resolution);
87 vector<int> idx_point;
88 vector<vector<vector<float>>> row_col;
89 vector<vector<float>> col_;
90 vector<float> vector_4;
92 col_.resize(raster_cols, vector_4);
93 row_col.resize(raster_rows, col_);
94 int point_num = cloud->size();
95 for (
int i_point = 0; i_point < point_num; i_point++) {
97 ceil((cloud->points[i_point].x - point_min.x) / x_resolution) -
100 ceil((cloud->points[i_point].y - point_min.y) / y_resolution) -
102 if (row_idx < 0) row_idx = 0;
103 if (col_idx < 0) col_idx = 0;
104 row_col[row_idx][col_idx][0] += cloud->points[i_point].x;
105 row_col[row_idx][col_idx][1] += cloud->points[i_point].y;
106 row_col[row_idx][col_idx][2] += cloud->points[i_point].z;
107 row_col[row_idx][col_idx][3] += 1;
110 for (
int i_row = 0; i_row < row_col.size(); i_row++) {
111 for (
int i_col = 0; i_col < row_col[i_row].size(); i_col++) {
112 if (row_col[i_row][i_col][3] != 0) {
114 row_col[i_row][i_col][0] / row_col[i_row][i_col][3];
116 row_col[i_row][i_col][1] / row_col[i_row][i_col][3];
118 row_col[i_row][i_col][2] / row_col[i_row][i_col][3];
119 x_mean.push_back(x_mean_tem);
120 y_mean.push_back(y_mean_tem);
121 z_mean.push_back(z_mean_tem);
122 point_mean_tem.x = x_mean_tem;
123 point_mean_tem.y = y_mean_tem;
124 point_mean_tem.z = z_mean_tem;
125 new_cloud->push_back(point_mean_tem);
131 void CurveFitting::line_fitting(vector<double>
x,
135 MatrixXd A_(2, 2), B_(2, 1),
A12(2, 1);
136 int num_point =
x.size();
137 double A01(0.0), A02(0.0), B00(0.0), B10(0.0);
138 for (
int i_point = 0; i_point < num_point; i_point++) {
139 A01 +=
x[i_point] *
x[i_point];
141 B00 +=
x[i_point] *
y[i_point];
144 A_ << A01, A02, A02, num_point;
146 A12 = A_.inverse() * B_;
151 void CurveFitting::polynomial2D_fitting(
152 vector<double>
x, vector<double>
y,
double &
a,
double &b,
double &c) {
153 MatrixXd A_(3, 3), B_(3, 1), A123(3, 1);
154 int num_point =
x.size();
155 double A01(0.0), A02(0.0),
A12(0.0), A22(0.0), B00(0.0), B10(0.0), B12(0.0);
156 for (
int i_point = 0; i_point < num_point; i_point++) {
158 A02 +=
x[i_point] *
x[i_point];
159 A12 +=
x[i_point] *
x[i_point] *
x[i_point];
160 A22 +=
x[i_point] *
x[i_point] *
x[i_point] *
x[i_point];
162 B10 +=
x[i_point] *
y[i_point];
163 B12 +=
x[i_point] *
x[i_point] *
y[i_point];
165 A_ << num_point, A01, A02, A01, A02,
A12, A02,
A12, A22;
167 A123 = A_.inverse() * B_;
173 void CurveFitting::polynomial3D_fitting(vector<double>
x,
179 int num_point =
x.size();
180 MatrixXd A_(3, 3), B_(3, 1), A123(3, 1);
181 double A01(0.0), A02(0.0),
A12(0.0), A22(0.0), B00(0.0), B10(0.0), B12(0.0);
182 for (
int i_point = 0; i_point < num_point; i_point++) {
183 double x_y = sqrt(pow(
x[i_point], 2) + pow(
y[i_point], 2));
189 B10 += x_y *
z[i_point];
190 B12 += pow(x_y, 2) *
z[i_point];
192 A_ << num_point, A01, A02, A01, A02,
A12, A02,
A12, A22;
194 A123 = A_.inverse() * B_;
195 line_fitting(
x,
y, k_line, b_line);
204 void CurveFitting::getPolynomial3D(PointCloudT::Ptr outCurve,
double step_) {
205 PointT point_min_, point_max_;
206 getMinMax3D(*cloud, point_min_, point_max_);
207 int idx_minx, idx_maxy;
208 for (
int i_point = 0; i_point < cloud->size(); i_point++) {
209 if (cloud->points[i_point].x == point_min_.x) idx_minx = i_point;
210 if (cloud->points[i_point].x == point_max_.x) idx_maxy = i_point;
213 cloud->points[idx_minx].x + k_line * cloud->points[idx_minx].y;
215 cloud->points[idx_maxy].x + k_line * cloud->points[idx_maxy].y;
217 float x_min = (m_min - b_line * k_line) / (1 + k_line * k_line);
218 float x_max = (m_max - b_line * k_line) / (1 + k_line * k_line);
220 int step_num =
ceil((x_max - x_min) / step_);
221 for (
int i_ = 0; i_ < step_num + 1; i_++) {
222 double tem_value = x_min + i_ * step_;
223 if (tem_value > x_max) {
227 point_.x = tem_value;
228 point_.y = k_line * tem_value + b_line;
229 double xxyy = sqrt(pow(point_.x, 2) + pow(point_.y, 2));
230 point_.z = c_3d + b_3d * xxyy + a_3d * pow(xxyy, 2);
231 outCurve->push_back(point_);
A 3D cloud and its associated features (color, normals, scalar fields, etc.)
std::vector< CCVector3 > & getPoints()
static ccPolyline * ConvertToPolyline(vtkPolyData *polydata, bool silent=false)
MiniVec< float, N > ceil(const MiniVec< float, N > &a)