Apollo 10.0
自动驾驶开放平台
lslidarCH32_parser.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 *****************************************************************************/
16
18
19namespace apollo {
20namespace drivers {
21namespace lslidar {
22namespace parser {
23
25 LslidarParser(config), previous_packet_stamp_(0), gps_base_usec_(0) {}
26
28 const std::shared_ptr<LslidarScan> &scan_msg,
29 const std::shared_ptr<PointCloud> &out_msg) {
30 // allocate a point cloud with same time and frame ID as raw data
31 out_msg->mutable_header()->set_timestamp_sec(
32 scan_msg->basetime() / 1000000000.0);
33 out_msg->mutable_header()->set_module_name(
34 scan_msg->header().module_name());
35 out_msg->mutable_header()->set_frame_id(scan_msg->header().frame_id());
36 out_msg->set_height(1);
37 out_msg->set_measurement_time(scan_msg->basetime() / 1000000000.0);
38 out_msg->mutable_header()->set_sequence_num(
39 scan_msg->header().sequence_num());
40 gps_base_usec_ = scan_msg->basetime();
41
42 packets_size = scan_msg->firing_pkts_size();
43
44 for (size_t i = 0; i < packets_size; ++i) {
45 Unpack(static_cast<int>(i),
46 scan_msg->firing_pkts(static_cast<int>(i)),
47 out_msg);
48 last_time_stamp_ = out_msg->measurement_time();
49 ADEBUG << "stamp: " << std::fixed << last_time_stamp_;
50 }
51
52 if (out_msg->point().empty()) {
53 // we discard this pointcloud if empty
54 AERROR << "All points is NAN!Please check lslidar:" << config_.model();
55 }
56
57 // set default width
58 out_msg->set_width(out_msg->point_size());
59}
60
65void LslidarCH32Parser::Unpack(
66 int num,
67 const LslidarPacket &pkt,
68 std::shared_ptr<PointCloud> pc) {
69 float x, y, z;
70 uint64_t packet_end_time;
71 double z_sin_altitude = 0.0;
72 double z_cos_altitude = 0.0;
73 time_last = 0;
74 const RawPacket *raw = (const RawPacket *)pkt.data().c_str();
75
76 packet_end_time = pkt.stamp();
77
78 for (size_t point_idx = 0; point_idx < POINTS_PER_PACKET; point_idx++) {
79 firings[point_idx].vertical_line = raw->points[point_idx].vertical_line;
80 two_bytes point_amuzith;
81 point_amuzith.bytes[0] = raw->points[point_idx].azimuth_2;
82 point_amuzith.bytes[1] = raw->points[point_idx].azimuth_1;
83 firings[point_idx].azimuth
84 = static_cast<double>(point_amuzith.uint) * 0.01 * DEG_TO_RAD;
85 four_bytes point_distance;
86 point_distance.bytes[0] = raw->points[point_idx].distance_3;
87 point_distance.bytes[1] = raw->points[point_idx].distance_2;
88 point_distance.bytes[2] = raw->points[point_idx].distance_1;
89 point_distance.bytes[3] = 0;
90 firings[point_idx].distance = static_cast<double>(point_distance.uint)
91 * DISTANCE_RESOLUTION2;
92 firings[point_idx].intensity = raw->points[point_idx].intensity;
93 }
94
95 double scan_laser_altitude_degree[8];
96 if (1 == config_.degree_mode()) {
97 for (int i = 0; i < 8; i++)
98 scan_laser_altitude_degree[i] = sin_scan_laser_altitude[i];
99 } else {
100 for (int i = 0; i < 8; i++)
101 scan_laser_altitude_degree[i] = sin_scan_laser_altitude_ch32[i];
102 }
103
104 for (size_t point_idx = 0; point_idx < POINTS_PER_PACKET; point_idx++) {
105 LaserCorrection &corrections
107 .laser_corrections_[firings[point_idx].vertical_line];
108
109 if (config_.calibration())
110 firings[point_idx].distance
111 = firings[point_idx].distance + corrections.dist_correction;
112
113 if (firings[point_idx].distance > config_.max_range()
114 || firings[point_idx].distance < config_.min_range())
115 continue;
116
117 // Convert the point to xyz coordinate
118 double cos_azimuth_half = cos(firings[point_idx].azimuth * 0.5);
119 z_sin_altitude = scan_laser_altitude_degree
120 [firings[point_idx].vertical_line / 4]
121 + 2 * cos_azimuth_half
122 * sin_scan_mirror_altitude
123 [firings[point_idx].vertical_line % 4];
124 z_cos_altitude = sqrt(1 - z_sin_altitude * z_sin_altitude);
125
126 x = firings[point_idx].distance * z_cos_altitude
127 * cos(firings[point_idx].azimuth);
128 y = firings[point_idx].distance * z_cos_altitude
129 * sin(firings[point_idx].azimuth);
130 z = firings[point_idx].distance * z_sin_altitude;
131
132 // Compute the time of the point
133 uint64_t point_time
134 = packet_end_time - 1665 * (POINTS_PER_PACKET - point_idx - 1);
135 if (time_last < point_time && time_last > 0) {
136 point_time = time_last + 1665;
137 }
138 time_last = point_time;
139
140 PointXYZIT *point = pc->add_point();
141 (point_time / 1000000000.0);
142 point->set_intensity(firings[point_idx].intensity);
143
144 if (config_.calibration()) {
146 firings[point_idx].vertical_line,
147 CH32,
148 firings[point_idx].distance,
149 &corrections,
150 firings[point_idx].azimuth,
151 point);
152 } else {
153 if ((y >= config_.bottom_left_x() && y <= config_.top_right_x())
154 && (-x >= config_.bottom_left_y()
155 && -x <= config_.top_right_y())) {
156 point->set_x(nan);
157 point->set_y(nan);
158 point->set_z(nan);
159 point->set_timestamp(point_time);
160 point->set_intensity(0);
161 } else {
162 point->set_x(y);
163 point->set_y(-x);
164 point->set_z(z);
165 }
166 }
167 }
168}
169
170void LslidarCH32Parser::Order(std::shared_ptr<PointCloud> cloud) {
171 int width = 32;
172 cloud->set_width(width);
173 int height = cloud->point_size() / cloud->width();
174 cloud->set_height(height);
175
176 std::shared_ptr<PointCloud> cloud_origin = std::make_shared<PointCloud>();
177 cloud_origin->CopyFrom(*cloud);
178
179 for (int i = 0; i < width; ++i) {
180 int col = ORDER_32[i];
181
182 for (int j = 0; j < height; ++j) {
183 // make sure offset is initialized, should be init at setup() just
184 // once
185 int target_index = j * width + i;
186 int origin_index = j * width + col;
187 cloud->mutable_point(target_index)
188 ->CopyFrom(cloud_origin->point(origin_index));
189 }
190 }
191}
192
193} // namespace parser
194} // namespace lslidar
195} // namespace drivers
196} // namespace apollo
std::map< int, LaserCorrection > laser_corrections_
Definition calibration.h:72
void GeneratePointcloud(const std::shared_ptr< LslidarScan > &scan_msg, const std::shared_ptr< apollo::drivers::PointCloud > &out_msg)
Set up for data processing.
void Order(std::shared_ptr< apollo::drivers::PointCloud > cloud)
void ComputeCoords2(int Laser_ring, int Type, const float &raw_distance, LaserCorrection *corrections, const double rotation, PointXYZIT *point)
#define ADEBUG
Definition log.h:41
#define AERROR
Definition log.h:44
These classes Unpack raw Lslidar LIDAR packets into several useful formats.
#define DEG_TO_RAD
#define CH32
class register implement
Definition arena_queue.h:37
used for unpacking the first two data bytes in a block