Apollo 10.0
自动驾驶开放平台
hdmap_roi_filter.cc
浏览该文件的文档.
1/******************************************************************************
2 * Copyright 2018 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
19#include <algorithm>
20
21#include "cyber/common/file.h"
26
27namespace apollo {
28namespace perception {
29namespace lidar {
30
34
35template <typename T>
37
39 // load model config
40 std::string config_file =
41 GetConfigFile(options.config_path, options.config_file);
44 range_ = config.range();
45 cell_size_ = config.cell_size();
46 extend_dist_ = config.extend_dist();
47 no_edge_table_ = config.no_edge_table();
48 set_roi_service_ = config.set_roi_service();
49
50 // reserve mem
51 const size_t KPolygonMaxNum = 100;
52 polygons_world_.reserve(KPolygonMaxNum);
53 polygons_local_.reserve(KPolygonMaxNum);
54
55 // init bitmap
56 Eigen::Vector2d min_range(-range_, -range_);
57 Eigen::Vector2d max_range(range_, range_);
58 Eigen::Vector2d cell_size(cell_size_, cell_size_);
59 bitmap_.Init(min_range, max_range, cell_size);
60
61 // output input parameters
62 AINFO << " HDMap Roi Filter Parameters: "
63 << " range: " << range_ << " cell_size: " << cell_size_
64 << " extend_dist: " << extend_dist_
65 << " no_edge_table: " << no_edge_table_
66 << " set_roi_service: " << set_roi_service_;
67
68 return true;
69}
70
72 LidarFrame* frame) {
73 if (frame->hdmap_struct == nullptr || frame->cloud == nullptr) {
74 AERROR << " Input frame data error !";
75 return false;
76 }
77
78 // get map polygon of roi
79 auto& road_polygons = frame->hdmap_struct->road_polygons;
80 auto& junction_polygons = frame->hdmap_struct->junction_polygons;
81 size_t polygons_world_size = road_polygons.size() + junction_polygons.size();
82 if (0 == polygons_world_size) {
83 AINFO << " Polygon Empty.";
84 return false;
85 }
86
87 polygons_world_.clear();
88 polygons_world_.resize(polygons_world_size, nullptr);
89 size_t i = 0;
90 for (auto& polygon : road_polygons) {
91 polygons_world_[i++] = &polygon;
92 }
93 for (auto& polygon : junction_polygons) {
94 polygons_world_[i++] = &polygon;
95 }
96
97 // transform to local
98 base::PointFCloudPtr cloud_local = base::PointFCloudPool::Instance().Get();
99 TransformFrame(frame->cloud, frame->lidar2world_pose, polygons_world_,
100 &polygons_local_, &cloud_local);
101
102 bool ret = FilterWithPolygonMask(cloud_local, polygons_local_,
103 &(frame->roi_indices));
104
105 // set roi points label
106 if (ret) {
107 for (auto index : frame->roi_indices.indices) {
108 frame->cloud->mutable_points_label()->at(index) =
109 static_cast<uint8_t>(LidarPointLabel::ROI);
110 frame->world_cloud->mutable_points_label()->at(index) =
111 static_cast<uint8_t>(LidarPointLabel::ROI);
112 }
113 }
114
115 // set roi service
116 if (set_roi_service_) {
117 auto roi_service = SceneManager::Instance().Service("ROIService");
118 if (roi_service != nullptr) {
119 roi_service_content_.range_ = range_;
120 roi_service_content_.cell_size_ = cell_size_;
121 roi_service_content_.map_size_ = bitmap_.map_size();
122 roi_service_content_.bitmap_ = bitmap_.bitmap();
123 roi_service_content_.major_dir_ =
124 static_cast<ROIServiceContent::DirectionMajor>(bitmap_.dir_major());
125 roi_service_content_.transform_ = frame->lidar2world_pose.translation();
126 if (!ret) {
127 std::fill(roi_service_content_.bitmap_.begin(),
128 roi_service_content_.bitmap_.end(), -1);
129 }
130 roi_service->UpdateServiceContent(roi_service_content_);
131 } else {
132 AINFO << "Failed to find roi service and cannot update.";
133 }
134 }
135 return ret;
136}
137
138bool HdmapROIFilter::FilterWithPolygonMask(
139 const base::PointFCloudPtr& cloud,
140 const EigenVector<PolygonDType>& map_polygons,
141 base::PointIndices* roi_indices) {
142 std::vector<Polygon<double>> raw_polygons;
143 // convert and obtain the major direction
144 raw_polygons.resize(map_polygons.size());
145 double min_x = range_;
146 double max_x = -min_x;
147 double min_y = min_x;
148 double max_y = max_x;
149
150 for (size_t i = 0; i < map_polygons.size(); ++i) {
151 auto& raw_polygon = raw_polygons[i];
152 const auto& map_polygon = map_polygons[i];
153 raw_polygon.resize(map_polygon.size());
154 for (size_t j = 0; j < map_polygon.size(); ++j) {
155 raw_polygon[j].x() = map_polygon[j].x;
156 raw_polygon[j].y() = map_polygon[j].y;
157 min_x = std::min(raw_polygon[j].x(), min_x);
158 max_x = std::max(raw_polygon[j].x(), max_x);
159 min_y = std::min(raw_polygon[j].y(), min_y);
160 max_y = std::max(raw_polygon[j].y(), max_y);
161 }
162 }
163 min_x = std::max(min_x, -range_);
164 max_x = std::min(max_x, range_);
165 min_y = std::max(min_y, -range_);
166 max_y = std::min(max_y, range_);
167
168 DirectionMajor major_dir = DirectionMajor::XMAJOR;
169 if ((max_y - min_y) < (max_x - min_x)) {
170 major_dir = DirectionMajor::YMAJOR;
171 }
172 bitmap_.SetUp(major_dir);
173
174 return DrawPolygonsMask<double>(raw_polygons, &bitmap_, extend_dist_,
175 no_edge_table_) &&
176 Bitmap2dFilter(cloud, bitmap_, roi_indices);
177}
178
179void HdmapROIFilter::TransformFrame(
180 const base::PointFCloudPtr& cloud, const Eigen::Affine3d& vel_pose,
181 const EigenVector<PolygonDType*>& polygons_world,
182 EigenVector<PolygonDType>* polygons_local,
183 base::PointFCloudPtr* cloud_local) {
184 Eigen::Vector3d vel_location = vel_pose.translation();
185 Eigen::Matrix3d vel_rot = vel_pose.linear();
186 Eigen::Vector3d x_axis = vel_rot.row(0);
187 Eigen::Vector3d y_axis = vel_rot.row(1);
188
189 // transform polygons
190 polygons_local->clear();
191 polygons_local->resize(polygons_world.size());
192 for (size_t i = 0; i < polygons_local->size(); ++i) {
193 const auto& polygon_world = *(polygons_world[i]);
194 auto& polygon_local = (*polygons_local)[i];
195 polygon_local.resize(polygon_world.size());
196 for (size_t j = 0; j < polygon_local.size(); ++j) {
197 polygon_local[j].x = polygon_world[j].x - vel_location.x();
198 polygon_local[j].y = polygon_world[j].y - vel_location.y();
199 }
200 }
201
202 // transform cloud
203 (*cloud_local)->clear();
204 (*cloud_local)->resize(cloud->size());
205 for (size_t i = 0; i < (*cloud_local)->size(); ++i) {
206 const auto& pt = cloud->at(i);
207 auto& local_pt = (*cloud_local)->at(i);
208 Eigen::Vector3d e_pt(pt.x, pt.y, pt.z);
209 local_pt.x = static_cast<float>(x_axis.dot(e_pt));
210 local_pt.y = static_cast<float>(y_axis.dot(e_pt));
211 }
212}
213
214bool HdmapROIFilter::Bitmap2dFilter(const base::PointFCloudPtr& in_cloud,
215 const Bitmap2D& bitmap,
216 base::PointIndices* roi_indices) {
217 if (!bitmap.Check(Eigen::Vector2d(0.0, 0.0))) {
218 AWARN << " Car is not in roi!!.";
219 return false;
220 }
221 roi_indices->indices.clear();
222 roi_indices->indices.reserve(in_cloud->size());
223 for (size_t i = 0; i < in_cloud->size(); ++i) {
224 const auto& pt = in_cloud->at(i);
225 Eigen::Vector2d e_pt(pt.x, pt.y);
226 if (!bitmap.IsExists(e_pt)) {
227 continue;
228 }
229 if (bitmap.Check(e_pt)) {
230 roi_indices->indices.push_back(static_cast<int>(i));
231 }
232 }
233 return true;
234}
235
236} // namespace lidar
237} // namespace perception
238} // namespace apollo
int dir_major() const
Return the dir_major_
Definition bitmap2d.h:103
void SetUp(const DirectionMajor dir_major)
Set the dir_major_ and op_dir_major_
Definition bitmap2d.cc:92
const std::vector< uint64_t > & bitmap() const
Return the bitmap_
Definition bitmap2d.h:96
void Init(const Eigen::Vector2d &min_range, const Eigen::Vector2d &max_range, const Eigen::Vector2d &cell_size)
Init of Bitmap 2D object
Definition bitmap2d.cc:72
const Vec2ui & map_size() const
Return the map_size_
Definition bitmap2d.h:82
bool Filter(const ROIFilterOptions &options, LidarFrame *frame) override
filter point cloud outside of hdmap roi
bool Init(const ROIFilterInitOptions &options) override
Init of Hdmap ROI Filter object
std::vector< Point, Eigen::aligned_allocator< Point > > Polygon
SceneServicePtr Service(const std::string &name)
#define ACHECK(cond)
Definition log.h:80
#define AERROR
Definition log.h:44
#define AINFO
Definition log.h:42
#define AWARN
Definition log.h:43
std::vector< EigenType, Eigen::aligned_allocator< EigenType > > EigenVector
Definition eigen_defs.h:33
bool GetProtoFromFile(const std::string &file_name, google::protobuf::Message *message)
Parses the content of the file specified by the file_name as a representation of protobufs,...
Definition file.cc:132
std::shared_ptr< PointFCloud > PointFCloudPtr
typename PolygonScanCvter< T >::Polygon Polygon
Bitmap2D::DirectionMajor DirectionMajor
std::string GetConfigFile(const std::string &config_path, const std::string &config_file)
Definition util.cc:80
class register implement
Definition arena_queue.h:37
std::shared_ptr< base::AttributePointCloud< base::PointD > > world_cloud
Definition lidar_frame.h:37
std::shared_ptr< base::HdmapStruct > hdmap_struct
Definition lidar_frame.h:51
std::shared_ptr< base::AttributePointCloud< base::PointF > > cloud
Definition lidar_frame.h:35