mrs_lib
Various reusable classes, functions and utilities for use in MRS projects
Loading...
Searching...
No Matches
publisher.impl.hpp
1#ifndef MRS_LIB_PUBLISHER_IMPL_HPP_
2#define MRS_LIB_PUBLISHER_IMPL_HPP_
3
4#include "mrs_lib/publisher.hpp"
5
6#include <chrono>
7#include <cstddef>
8#include <memory>
9#include <optional>
10#include <string_view>
11#include <utility>
12
13#include <rclcpp/create_publisher.hpp>
14#include <rclcpp/publisher.hpp>
15
16#include "mrs_lib/internal/rate_throttle.hpp"
17#include "mrs_lib/logger.hpp"
20
21
22namespace mrs_lib
23{
24
25
27 template <class MessageType>
28 class Publisher<MessageType>::Impl
29 {
30 private:
31 using RosPublisherPimpl = Pimpl<rclcpp::Publisher<MessageType>, std::shared_ptr<rclcpp::Publisher<MessageType>>>;
32
33 public:
34 Impl(const PublisherOptions& options, std::string_view topic_name)
35 : node_interfaces_(options.node_interfaces),
36 logger_(node_interfaces_),
37 unresolved_topic_name_(topic_name),
38 publisher_(rclcpp::create_publisher<MessageType>(node_interfaces_, std::string(topic_name), options.qos))
39 {
40 if (options.throttle_duration.has_value())
41 {
42 throttle_.emplace(internal::RateThrottle(options.throttle_duration.value()));
43 }
44
45 logger_.info("Created publisher on topic '{}' -> '{}'", unresolved_topic_name_, publisher_->get_topic_name());
46 }
47
48 ~Impl() = default;
49 Impl(const Impl&) = delete;
50 Impl& operator=(const Impl&) = delete;
51 Impl(Impl&&) = delete;
52 Impl& operator=(Impl&&) = delete;
53
54 template <typename Message>
55 void publish(Message&& msg)
56 {
57 bool should_publish = handle_publish_rate();
58
59 if (should_publish)
60 {
61 publisher_->publish(std::forward<Message>(msg));
62 }
63 }
64
65 [[nodiscard]] std::string get_topic_name() const
66 {
67 return publisher_->get_topic_name();
68 }
69
70 [[nodiscard]] std::string get_unresolved_topic_name() const
71 {
72 return unresolved_topic_name_;
73 }
74
75 [[nodiscard]] size_t get_subscriber_count() const
76 {
77 return publisher_->get_subscription_count();
78 }
79
80 private:
93 bool handle_publish_rate()
94 {
95 if (!throttle_.has_value())
96 {
97 // Always publish if no throttle is set.
98 return true;
99 }
100
101 auto guard = throttle_->acquire();
102 return guard->accept(node_interfaces_.get_node_clock_interface()->get_clock()->now());
103 }
104
105 PublisherNodeInterfaces node_interfaces_;
106 mrs_lib::Logger logger_;
107
108 std::string unresolved_topic_name_;
109
110 // empty if throttling is disabled, so unthrottled publishing skips the mutex and the clock read
111 std::optional<OwningMutex<internal::RateThrottle>> throttle_;
112
113 RosPublisherPimpl publisher_;
114 };
115
116
117 template <class MessageType>
118 Publisher<MessageType>::Publisher(const PublisherOptions& options, std::string_view topic_name) : impl_(std::in_place_type_t<Impl>{}, options, topic_name)
119 {
120 }
121
122 template <class MessageType>
123 void Publisher<MessageType>::publish(const MessageType& msg)
124 {
125 impl_->publish(msg);
126 }
127
128 template <class MessageType>
129 void Publisher<MessageType>::publish(std::unique_ptr<MessageType> msg)
130 {
131 impl_->publish(std::move(msg));
132 }
133
134 template <class MessageType>
135 [[nodiscard]] std::string Publisher<MessageType>::get_topic_name() const
136 {
137 return impl_->get_topic_name();
138 }
139
140 template <class MessageType>
142 {
143 return impl_->get_unresolved_topic_name();
144 }
145
146 template <class MessageType>
148 {
149 return impl_->get_subscriber_count();
150 }
151
152} // namespace mrs_lib
153
154#endif // MRS_LIB_PUBLISHER_IMPL_HPP_
Wrapper for rclcpp::Publisher.
Definition publisher.hpp:48
void publish(const MessageType &msg)
Publish a message.
Definition publisher.impl.hpp:123
std::string get_unresolved_topic_name() const
Returns the unresolved name of the topic handled by this publisher.
Definition publisher.impl.hpp:141
std::string get_topic_name() const
Returns the resolved (full) name of the topic handled by this publisher.
Definition publisher.impl.hpp:135
size_t get_subscriber_count() const
Get number of subscribers on the published topic.
Definition publisher.impl.hpp:147
Publisher(const PublisherOptions &options, std::string_view topic_name)
construct a publisher using the specified options.
Definition publisher.impl.hpp:118
All mrs_lib functions, classes, variables and definitions are contained in this namespace.
Definition attitude_converter.h:24
rclcpp::node_interfaces::NodeInterfaces< rclcpp::node_interfaces::NodeTopicsInterface, rclcpp::node_interfaces::NodeClockInterface, rclcpp::node_interfaces::NodeLoggingInterface > PublisherNodeInterfaces
ROS node interfaces required by the Publisher.
Definition publisher.hpp:25
Definition publisher.hpp:31