Apollo 11.0
自动驾驶开放平台
poses_interpolation.cc
浏览该文件的文档.
1/******************************************************************************
2 * Copyright 2017 The Apollo Authors. All Rights Reserved.
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 *****************************************************************************/
17
18#include <fstream>
19
20#include "cyber/common/log.h"
22
23namespace apollo {
24namespace localization {
25namespace msf {
27
28bool PosesInterpolation::Init(const std::string &input_poses_path,
29 const std::string &ref_timestamps_path,
30 const std::string &out_poses_path,
31 const std::string &extrinsic_path) {
32 this->input_poses_path_ = input_poses_path;
33 this->ref_timestamps_path_ = ref_timestamps_path;
34 this->out_poses_path_ = out_poses_path;
35 this->extrinsic_path_ = extrinsic_path;
36
37 bool success = velodyne::LoadExtrinsic(extrinsic_path_, &velodyne_extrinsic_);
38 if (!success) {
39 AERROR << "Load lidar extrinsic failed.";
40 return false;
41 }
42
43 return true;
44}
45
47 // Load input poses
49 velodyne::LoadPosesAndStds(input_poses_path_, &input_poses_, &input_stds,
50 &input_poses_timestamps_);
51
52 // Load pcd timestamp
53 LoadPCDTimestamp();
54
55 // Interpolation
56 PoseInterpolationByTime(input_poses_, input_poses_timestamps_,
57 ref_timestamps_, ref_ids_, &out_indexes_,
58 &out_timestamps_, &out_poses_);
59
60 // Write pcd poses
61 WritePCDPoses();
62}
63
64void PosesInterpolation::LoadPCDTimestamp() {
65 FILE *file = fopen(ref_timestamps_path_.c_str(), "r");
66 if (file) {
67 unsigned int index;
68 double timestamp;
69 static constexpr int kSize = 2;
70 while (fscanf(file, "%u %lf\n", &index, &timestamp) == kSize) {
71 ref_timestamps_.push_back(timestamp);
72 ref_ids_.push_back(index);
73 }
74 fclose(file);
75 } else {
76 AINFO << "Can't open file to read: " << ref_timestamps_path_;
77 }
78}
79
80void PosesInterpolation::WritePCDPoses() {
81 std::ofstream fout;
82 fout.open(out_poses_path_.c_str(), std::ofstream::out);
83
84 if (fout.is_open()) {
85 fout.setf(std::ios::fixed, std::ios::floatfield);
86 fout.precision(6);
87 for (size_t i = 0; i < out_poses_.size(); i++) {
88 double timestamp = out_timestamps_[i];
89
90 Eigen::Affine3d pose_tem = out_poses_[i] * velodyne_extrinsic_;
91 Eigen::Quaterniond quatd(pose_tem.linear());
92 Eigen::Translation3d transd(pose_tem.translation());
93 double qx = quatd.x();
94 double qy = quatd.y();
95 double qz = quatd.z();
96 double qr = quatd.w();
97
98 fout << out_indexes_[i] << " " << timestamp << " " << transd.x() << " "
99 << transd.y() << " " << transd.z() << " " << qx << " " << qy << " "
100 << qz << " " << qr << "\n";
101 }
102
103 fout.close();
104 } else {
105 AERROR << "Can't open file to write: " << out_poses_path_ << std::endl;
106 }
107} // namespace msf
108
109void PosesInterpolation::PoseInterpolationByTime(
110 const ::apollo::common::EigenAffine3dVec &in_poses,
111 const std::vector<double> &in_timestamps,
112 const std::vector<double> &ref_timestamps,
113 const std::vector<unsigned int> &ref_indexes,
114 std::vector<unsigned int> *out_indexes, std::vector<double> *out_timestamps,
116 out_indexes->clear();
117 out_timestamps->clear();
118 out_poses->clear();
119
120 unsigned int index = 0;
121 for (size_t i = 0; i < ref_timestamps.size(); i++) {
122 double ref_timestamp = ref_timestamps[i];
123 unsigned int ref_index = ref_indexes[i];
124
125 while (index < in_timestamps.size() &&
126 in_timestamps.at(index) < ref_timestamp) {
127 ++index;
128 }
129
130 if (index < in_timestamps.size()) {
131 if (index >= 1) {
132 double cur_timestamp = in_timestamps[index];
133 double pre_timestamp = in_timestamps[index - 1];
134 assert(cur_timestamp != pre_timestamp);
135
136 double t =
137 (cur_timestamp - ref_timestamp) / (cur_timestamp - pre_timestamp);
138 assert(t >= 0.0);
139 assert(t <= 1.0);
140
141 Eigen::Affine3d pre_pose = in_poses[index - 1];
142 Eigen::Affine3d cur_pose = in_poses[index];
143 Eigen::Quaterniond pre_quatd(pre_pose.linear());
144 Eigen::Translation3d pre_transd(pre_pose.translation());
145 Eigen::Quaterniond cur_quatd(cur_pose.linear());
146 Eigen::Translation3d cur_transd(cur_pose.translation());
147
148 Eigen::Quaterniond res_quatd = pre_quatd.slerp(1 - t, cur_quatd);
149
150 Eigen::Translation3d re_transd;
151 re_transd.x() = pre_transd.x() * t + cur_transd.x() * (1 - t);
152 re_transd.y() = pre_transd.y() * t + cur_transd.y() * (1 - t);
153 re_transd.z() = pre_transd.z() * t + cur_transd.z() * (1 - t);
154
155 out_poses->push_back(re_transd * res_quatd);
156 out_indexes->push_back(ref_index);
157 out_timestamps->push_back(ref_timestamp);
158 }
159 } else {
160 AWARN << "[WARN] No more poses. Exit now.";
161 break;
162 }
163 ADEBUG << "Frame_id: " << i;
164 }
165}
166
167} // namespace msf
168} // namespace localization
169} // namespace apollo
bool Init(const std::string &input_poses_path, const std::string &ref_timestamps_path, const std::string &out_poses_path, const std::string &extrinsic_path)
#define ADEBUG
Definition log.h:41
#define AERROR
Definition log.h:44
#define AINFO
Definition log.h:42
#define AWARN
Definition log.h:43
EigenVector< Eigen::Affine3d > EigenAffine3dVec
Definition eigen_defs.h:47
EigenVector< Eigen::Vector3d > EigenVector3dVec
Definition eigen_defs.h:46
bool LoadExtrinsic(const std::string &file_path, Eigen::Affine3d *extrinsic)
Load the velodyne extrinsic from a YAML file.
void LoadPosesAndStds(const std::string &file_path, ::apollo::common::EigenAffine3dVec *poses, ::apollo::common::EigenVector3dVec *stds, std::vector< double > *timestamps)
Load poses and stds their timestamps.
class register implement
Definition arena_queue.h:37
The utilities of velodyne.