|
@@ -381,8 +381,8 @@ Error_manager Ground_region::detect(pcl::PointCloud<pcl::PointXYZ>::Ptr cloud, d
|
|
|
|
|
|
// 3.*********位姿优化,获取中心xy与角度*********
|
|
|
pcl::PointCloud<pcl::PointXYZ>::Ptr cloud_detect_z(new pcl::PointCloud<pcl::PointXYZ>);
|
|
|
- double x, y, theta, width, z_value=0.2;
|
|
|
- if(!Car_pose_detector::get_instance_references().detect_pose(cloud_filtered, cloud_detect_z, x, y, theta, width, z_value, false))
|
|
|
+ double car_pose_x, car_pose_y, car_pose_theta, car_pose_width, z_value=0.2;
|
|
|
+ if(!Car_pose_detector::get_instance_references().detect_pose(cloud_filtered, cloud_detect_z, car_pose_x, car_pose_y, car_pose_theta, car_pose_width, z_value, false))
|
|
|
{
|
|
|
return Error_manager(VELODYNE_REGION_CERES_SOLVE_ERROR, NEGLIGIBLE_ERROR, "find general car pose value failed.");
|
|
|
}
|
|
@@ -393,6 +393,10 @@ Error_manager Ground_region::detect(pcl::PointCloud<pcl::PointXYZ>::Ptr cloud, d
|
|
|
|
|
|
// 4.*********xoz优化获取底盘高度*********
|
|
|
// 重新取包含地面点的点云,用于底盘优化
|
|
|
+ double z_solver_x = car_pose_x;
|
|
|
+ double z_solver_y = car_pose_y;
|
|
|
+ double z_solver_theta = car_pose_theta;
|
|
|
+ double z_solver_width = 1.0;
|
|
|
chassis_ceres_solver t_solver;
|
|
|
pcl::PointCloud<pcl::PointXYZ>::Ptr cloud_z_solver(new pcl::PointCloud<pcl::PointXYZ>);
|
|
|
for (int i = 0; i < cloud->size(); ++i)
|
|
@@ -409,18 +413,17 @@ Error_manager Ground_region::detect(pcl::PointCloud<pcl::PointXYZ>::Ptr cloud, d
|
|
|
sor.setStddevMulThresh(3.0); //标准差倍数
|
|
|
sor.setNegative(false); //保留未滤波点(内点)
|
|
|
sor.filter(*cloud_z_solver); //保存滤波结果到cloud_filter
|
|
|
-
|
|
|
- double mid_z = 0.05, height = 0.08;
|
|
|
// 去中心,角度调正
|
|
|
- Car_pose_detector::get_instance_references().inv_trans_cloud(cloud_z_solver, x, y, theta);
|
|
|
+ Car_pose_detector::get_instance_references().inv_trans_cloud(cloud_z_solver, z_solver_x, z_solver_y, z_solver_theta);
|
|
|
|
|
|
if (cloud_z_solver->size() == 0)
|
|
|
return Error_manager(VELODYNE_REGION_EMPTY_CLOUD, NORMAL, "z solver no point");
|
|
|
|
|
|
- x = 0.0;
|
|
|
- width = 1.0;
|
|
|
+ // 给予底盘z中心与高度初值
|
|
|
+ double mid_z = 0.05, height = 0.08;
|
|
|
+ z_solver_x = 0.0;
|
|
|
// Error_manager ec = t_solver.solve(cloud_z_solver, x, mid_z, width, height);
|
|
|
- Error_manager ec = t_solver.solve_mat(cloud_z_solver, x, mid_z, width, height, false);
|
|
|
+ Error_manager ec = t_solver.solve_mat(cloud_z_solver, z_solver_x, mid_z, z_solver_width, height, false);
|
|
|
// 切除大于height高度以外点,并显示width直线
|
|
|
// 根据z值切原始点云
|
|
|
pcl::PassThrough<pcl::PointXYZ> pass;
|
|
@@ -523,6 +526,15 @@ Error_manager Ground_region::detect(pcl::PointCloud<pcl::PointXYZ>::Ptr cloud, d
|
|
|
// last_result.cy -= y;
|
|
|
// last_result.theta -= theta;
|
|
|
|
|
|
+ // 角度校验,理论上car pose检测使用车身点云,应与车轮点云识别得到的车身 x偏移(0.025)与角度(<1°)一致
|
|
|
+ double car_pose_theta_deg = 90 - car_pose_theta * 180.0 / M_PI;
|
|
|
+ if (fabs(car_pose_x - last_result.cx) > 0.025 || fabs(car_pose_theta_deg - last_result.theta) > 1)
|
|
|
+ {
|
|
|
+ char valid_info[255];
|
|
|
+ sprintf(valid_info, "validation failed for x and theta, carpose: (%.3f, %.3f), result: (%.3f, %.3f)", car_pose_x, car_pose_theta_deg, last_result.cx, last_result.theta);
|
|
|
+ return Error_manager(VELODYNE_REGION_CERES_SOLVE_ERROR, NEGLIGIBLE_ERROR, valid_info);
|
|
|
+ }
|
|
|
+
|
|
|
return SUCCESS;
|
|
|
}
|
|
|
|
|
@@ -673,7 +685,7 @@ void Ground_region::thread_measure_func()
|
|
|
else
|
|
|
{
|
|
|
m_car_wheel_information.correctness = false;
|
|
|
- LOG(ERROR) << ec.to_string();
|
|
|
+ LOG_IF(ERROR, m_region.region_id() == 4) << ec.to_string();
|
|
|
}
|
|
|
m_detect_update_time = std::chrono::system_clock::now();
|
|
|
}
|