Carma-platform v4.2.0
CARMA Platform is built on robot operating system (ROS) and utilizes open source software (OSS) that enables Cooperative Driving Automation (CDA) features to allow Automated Driving Systems to interact and cooperate with infrastructure and other vehicles through communication.
TrafficControl.hpp
Go to the documentation of this file.
1#pragma once
2
3/*
4 * Copyright (C) 2022 LEIDOS.
5 *
6 * Licensed under the Apache License, Version 2.0 (the "License"); you may not
7 * use this file except in compliance with the License. You may obtain a copy of
8 * the License at
9 *
10 * http://www.apache.org/licenses/LICENSE-2.0
11 *
12 * Unless required by applicable law or agreed to in writing, software
13 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
14 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
15 * License for the specific language governing permissions and limitations under
16 * the License.
17 */
18
19#include <rclcpp/rclcpp.hpp>
20#include <boost/uuid/uuid.hpp>
21#include <boost/uuid/uuid_io.hpp>
22#include <boost/uuid/uuid_generators.hpp>
23#include <lanelet2_core/LaneletMap.h>
24
25#include <autoware_lanelet2_msgs/msg/map_bin.hpp>
26
27#include <lanelet2_io/io_handlers/Serialize.h>
28#include <lanelet2_core/primitives/Point.h>
29#include <lanelet2_extension/regulatory_elements/DigitalSpeedLimit.h>
30#include <lanelet2_extension/regulatory_elements/StopRule.h>
31#include <lanelet2_extension/regulatory_elements/CarmaTrafficSignal.h>
32#include <lanelet2_extension/regulatory_elements/PassingControlLine.h>
33#include <lanelet2_extension/regulatory_elements/DigitalMinimumGap.h>
35#include <lanelet2_core/primitives/LaneletOrArea.h>
36#include <boost/archive/binary_iarchive.hpp>
37#include <boost/archive/binary_oarchive.hpp>
38#include <autoware_lanelet2_ros2_interface/utility/query.hpp>
39
40#include <carma_ros2_utils/carma_lifecycle_node.hpp>
41
42namespace carma_wm
43{
47using namespace lanelet::units::literals;
48
50{
51public:
53 TrafficControl(boost::uuids::uuid id,
54 std::vector<std::pair<lanelet::Id, lanelet::RegulatoryElementPtr>> update_list,
55 std::vector<std::pair<lanelet::Id, lanelet::RegulatoryElementPtr>> remove_list,
56 std::vector<lanelet::Lanelet> lanelet_addition):
57 id_(id), update_list_(update_list), remove_list_(remove_list), lanelet_additions_(lanelet_addition){}
58
59 boost::uuids::uuid id_; // Unique id of this geofence
60
61 // elements needed for broadcasting to the rest of map users
62 std::vector<std::pair<lanelet::Id, lanelet::RegulatoryElementPtr>> update_list_;
63 std::vector<std::pair<lanelet::Id, lanelet::RegulatoryElementPtr>> remove_list_;
64
65 // lanelets additions needed or broadcasting to the rest of map users
66 std::vector<lanelet::Lanelet> lanelet_additions_;
67
68 // traffic light id lookup
69 std::vector<std::pair<uint32_t, lanelet::Id>> traffic_light_id_lookup_;
70
71 // signalized intersection manager
73
74};
75
84void toBinMsg(std::shared_ptr<carma_wm::TrafficControl> gf_ptr, autoware_lanelet2_msgs::msg::MapBin* msg);
85
98void fromBinMsg(const autoware_lanelet2_msgs::msg::MapBin& msg, std::shared_ptr<carma_wm::TrafficControl> gf_ptr, lanelet::LaneletMapPtr lanelet_map = nullptr);
99
100} // namespace carma_wm
101
102
103// used for converting geofence into ROS msg binary
104namespace boost {
105namespace serialization {
106
107template <class Archive>
108// NOLINTNEXTLINE
109inline void save(Archive& ar, const carma_wm::TrafficControl& gf, unsigned int /*version*/)
110{
111 std::string string_id = boost::uuids::to_string(gf.id_);
112 ar << string_id;
113
114 // convert the lanelet that need to be added
115 size_t lanelet_additions_size = gf.lanelet_additions_.size();
116 ar << lanelet_additions_size;
117 for (auto llt : gf.lanelet_additions_) ar << llt;
118
119 // convert the regems that need to be removed
120 size_t remove_list_size = gf.remove_list_.size();
121 ar << remove_list_size;
122 for (auto pair : gf.remove_list_) ar << pair;
123
124 // convert id, regem pairs that need to be updated
125 size_t update_list_size = gf.update_list_.size();
126 ar << update_list_size;
127 for (auto pair : gf.update_list_) ar << pair;
128
129 // convert traffic light id lookup
130 size_t traffic_light_id_lookup_size = gf.traffic_light_id_lookup_.size();
131 ar << traffic_light_id_lookup_size;
132 for (auto pair : gf.traffic_light_id_lookup_) ar << pair;
133
134 // convert signalized intersection manager
135 ar << gf.sim_;
136}
137
138template <class Archive>
139// NOLINTNEXTLINE
140inline void load(Archive& ar, carma_wm::TrafficControl& gf, unsigned int /*version*/)
141{
142 boost::uuids::string_generator gen;
143 std::string id;
144 ar >> id;
145 gf.id_ = gen(id);
146
147 // save llts to add
148 size_t lanelet_additions_size;
149 ar >> lanelet_additions_size;
150 for (auto i = 0u; i < lanelet_additions_size; ++i)
151 {
152 lanelet::Lanelet llt;
153 ar >> llt;
154 gf.lanelet_additions_.push_back(llt);
155 }
156
157 // save regems to remove
158 size_t remove_list_size;
159 ar >> remove_list_size;
160 for (auto i = 0u; i < remove_list_size; ++i)
161 {
162 std::pair<lanelet::Id, lanelet::RegulatoryElementPtr> remove_item;
163 ar >> remove_item;
164 gf.remove_list_.push_back(remove_item);
165 }
166
167 // save parts that need to be updated
168 size_t update_list_size;
169 ar >> update_list_size;
170
171 for (auto i = 0u; i < update_list_size; ++i)
172 {
173 std::pair<lanelet::Id, lanelet::RegulatoryElementPtr> update_item;
174 ar >> update_item;
175 gf.update_list_.push_back(update_item);
176 }
177
178 // save ids
179 size_t traffic_light_id_lookup_size;
180 ar >> traffic_light_id_lookup_size;
181 for (auto i = 0u; i < traffic_light_id_lookup_size; ++i)
182 {
183 std::pair<uint32_t, lanelet::Id> traffic_light_id_pair;
184 ar >> traffic_light_id_pair;
185 gf.traffic_light_id_lookup_.push_back(traffic_light_id_pair);
186 }
187
188 // save signalized intersection manager
189 ar >> gf.sim_;
190}
191
192
193template <class Archive>
194// NOLINTNEXTLINE
195inline void save(Archive& ar, const carma_wm::SignalizedIntersectionManager& sim, unsigned int /*version*/)
196{
197 // convert traffic light id lookup
198 size_t intersection_id_to_regem_id_size = sim.intersection_id_to_regem_id_.size();
199 ar << intersection_id_to_regem_id_size;
200 for (auto pair : sim.intersection_id_to_regem_id_)
201 {
202 ar << pair;
203 }
204
205 // convert traffic light id lookup
206 size_t signal_group_to_traffic_light_id_size = sim.signal_group_to_traffic_light_id_.size();
207 ar << signal_group_to_traffic_light_id_size;
208 for (auto pair : sim.signal_group_to_traffic_light_id_)
209 {
210 ar << pair;
211 }
212
213 size_t signal_group_to_exit_lanelet_ids_size = sim.signal_group_to_exit_lanelet_ids_.size();
214 ar << signal_group_to_exit_lanelet_ids_size;
215 for (auto pair : sim.signal_group_to_exit_lanelet_ids_)
216 {
217 size_t set_size = pair.second.size();
218 ar << set_size;
219 ar << pair.first;
220 for (auto iter = pair.second.begin(); iter != pair.second.end(); iter++)
221 {
222 ar << *iter;
223 }
224 }
225
226 size_t signal_group_to_entry_lanelet_ids_size = sim.signal_group_to_entry_lanelet_ids_.size();
227 ar << signal_group_to_entry_lanelet_ids_size;
228 for (auto pair : sim.signal_group_to_entry_lanelet_ids_)
229 {
230 size_t set_size = pair.second.size();
231 ar << set_size;
232 ar << pair.first;
233 for (auto iter = pair.second.begin(); iter != pair.second.end(); iter++)
234 {
235 ar << *iter;
236 }
237 }
238}
239
240template <class Archive>
241// NOLINTNEXTLINE
242inline void load(Archive& ar, carma_wm::SignalizedIntersectionManager& sim, unsigned int /*version*/)
243{
244 // save traffic light id lookup
245 size_t intersection_id_to_regem_id_size;
246 ar >> intersection_id_to_regem_id_size;
247 for (size_t i = 0; i < intersection_id_to_regem_id_size; i ++)
248 {
249 std::pair<uint16_t, lanelet::Id> pair;
250 ar >> pair;
251 sim.intersection_id_to_regem_id_.emplace(pair);
252 }
253
254 // save traffic light id lookup
255 size_t signal_group_to_traffic_light_id_size;
256 ar >> signal_group_to_traffic_light_id_size;
257 for (size_t i = 0; i < signal_group_to_traffic_light_id_size; i ++)
258 {
259 std::pair<uint8_t, lanelet::Id> pair;
260 ar >> pair;
261 sim.signal_group_to_traffic_light_id_.emplace(pair);
262 }
263
264 size_t signal_group_to_exit_lanelet_ids_size;
265 ar >> signal_group_to_exit_lanelet_ids_size;
266 for (size_t i = 0; i < signal_group_to_exit_lanelet_ids_size; i ++)
267 {
268 size_t set_size;
269 ar >> set_size;
270 uint8_t signal_grp;
271 ar >> signal_grp;
272 for (size_t j = 0; j <set_size; j++)
273 {
274 lanelet::Id id;
275 ar >>id;
276 sim.signal_group_to_exit_lanelet_ids_[signal_grp].insert(id);
277 }
278 }
279
280 size_t signal_group_to_entry_lanelet_ids_size;
281 ar >> signal_group_to_entry_lanelet_ids_size;
282 for (size_t i = 0; i < signal_group_to_entry_lanelet_ids_size; i ++)
283 {
284 size_t set_size;
285 ar >> set_size;
286 uint8_t signal_grp;
287 ar >> signal_grp;
288 for (size_t j = 0; j <set_size; j++)
289 {
290 lanelet::Id id;
291 ar >>id;
292 sim.signal_group_to_entry_lanelet_ids_[signal_grp].insert(id);
293 }
294 }
295
296}
297
298template <typename Archive>
299void serialize(Archive& ar, std::pair<lanelet::Id, lanelet::RegulatoryElementPtr>& p, unsigned int /*version*/)
300{
301 ar& p.first;
302 ar& p.second;
303}
304
305template <typename Archive>
306void serialize(Archive& ar, std::pair<uint8_t, lanelet::Id>& p, unsigned int /*version*/)
307{
308 ar& p.first;
309 ar& p.second;
310}
311
312template <typename Archive>
313void serialize(Archive& ar, std::pair<uint16_t, lanelet::Id>& p, unsigned int /*version*/)
314{
315 ar& p.first;
316 ar& p.second;
317}
318
319template <typename Archive>
320void serialize(Archive& ar, std::pair<uint32_t, lanelet::Id>& p, unsigned int /*version*/)
321{
322 ar& p.first;
323 ar& p.second;
324}
325
326} // namespace serialization
327} // namespace boost
328
329BOOST_SERIALIZATION_SPLIT_FREE(carma_wm::TrafficControl)
330BOOST_SERIALIZATION_SPLIT_FREE(carma_wm::SignalizedIntersectionManager)
This class manages and keeps track of all signalized intersections in the map. All of the SPAT and MA...
std::unordered_map< uint8_t, std::unordered_set< lanelet::Id > > signal_group_to_entry_lanelet_ids_
std::unordered_map< uint16_t, lanelet::Id > intersection_id_to_regem_id_
std::unordered_map< uint8_t, std::unordered_set< lanelet::Id > > signal_group_to_exit_lanelet_ids_
std::unordered_map< uint8_t, lanelet::Id > signal_group_to_traffic_light_id_
std::vector< std::pair< lanelet::Id, lanelet::RegulatoryElementPtr > > update_list_
carma_wm::SignalizedIntersectionManager sim_
std::vector< std::pair< lanelet::Id, lanelet::RegulatoryElementPtr > > remove_list_
boost::uuids::uuid id_
std::vector< lanelet::Lanelet > lanelet_additions_
std::vector< std::pair< uint32_t, lanelet::Id > > traffic_light_id_lookup_
TrafficControl(boost::uuids::uuid id, std::vector< std::pair< lanelet::Id, lanelet::RegulatoryElementPtr > > update_list, std::vector< std::pair< lanelet::Id, lanelet::RegulatoryElementPtr > > remove_list, std::vector< lanelet::Lanelet > lanelet_addition)
void save(Archive &ar, const carma_wm::TrafficControl &gf, unsigned int)
void serialize(Archive &ar, std::pair< lanelet::Id, lanelet::RegulatoryElementPtr > &p, unsigned int)
void load(Archive &ar, carma_wm::TrafficControl &gf, unsigned int)
auto to_string(const UtmZone &zone) -> std::string
Definition: utm_zone.cpp:21
void fromBinMsg(const autoware_lanelet2_msgs::msg::MapBin &msg, std::shared_ptr< carma_wm::TrafficControl > gf_ptr, lanelet::LaneletMapPtr lanelet_map=nullptr)
void toBinMsg(std::shared_ptr< carma_wm::TrafficControl > gf_ptr, autoware_lanelet2_msgs::msg::MapBin *msg)