path_display.cpp
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2008, Willow Garage, Inc.
3  * 2020, Locus Robotics
4  * All rights reserved.
5  *
6  * Redistribution and use in source and binary forms, with or without
7  * modification, are permitted provided that the following conditions are met:
8  *
9  * * Redistributions of source code must retain the above copyright
10  * notice, this list of conditions and the following disclaimer.
11  * * Redistributions in binary form must reproduce the above copyright
12  * notice, this list of conditions and the following disclaimer in the
13  * documentation and/or other materials provided with the distribution.
14  * * Neither the name of the Willow Garage, Inc. or Locus Robotics nor the names of its
15  * contributors may be used to endorse or promote products derived from
16  * this software without specific prior written permission.
17  *
18  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
19  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
20  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
21  * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
22  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
23  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
24  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
25  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
26  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
27  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
28  * POSSIBILITY OF SUCH DAMAGE.
29  */
30 
34 
35 #include <OgreSceneNode.h>
36 #include <OgreSceneManager.h>
37 #include <OgreMatrix4.h>
38 
39 #include <algorithm>
40 #include <vector>
41 
42 namespace robot_nav_rviz_plugins
43 {
45 {
46  style_property_ = new rviz::EnumProperty("Line Style", "Lines",
47  "The rendering operation to use to draw the grid lines.", this, SLOT(updateStyle()));
48  style_property_->addOption("Lines", static_cast<int>(LineStyle::LINES));
49  style_property_->addOption("Billboards", static_cast<int>(LineStyle::BILLBOARDS));
50 
51  line_width_property_ = new rviz::FloatProperty("Line Width", 0.03, "The width, in meters, of each path line. "
52  "Only works with the 'Billboards' style.", this, SLOT(updateLineWidth()), this);
55 
56  color_property_ = new rviz::ColorProperty("Color", QColor(41, 170, 226), "Color to draw the path.", this);
57  alpha_property_ = new rviz::FloatProperty("Alpha", 1.0, "Amount of transparency to apply to the path.", this);
58 
59  buffer_length_property_ = new rviz::IntProperty("Buffer Length", 1, "Number of paths to display.", this,
60  SLOT(updateBufferLength()));
62 
63  offset_property_ = new rviz::VectorProperty("Offset", Ogre::Vector3::ZERO,
64  "Allows you to offset the path from the origin of the reference frame. In meters.", this, SLOT(updateOffset()));
65 
66  pose_style_property_ = new rviz::EnumProperty("Pose Style", "None", "Shape to display the pose as.", this,
67  SLOT(updatePoseStyle()));
68  pose_style_property_->addOption("None", static_cast<int>(PoseStyle::NONE));
69  pose_style_property_->addOption("Axes", static_cast<int>(PoseStyle::AXES));
70  pose_style_property_->addOption("Arrows", static_cast<int>(PoseStyle::ARROWS));
71 
72  pose_axes_length_property_ = new rviz::FloatProperty("Length", 0.3, "Length of the axes.", this,
73  SLOT(updatePoseAxisGeometry()));
74  pose_axes_radius_property_ = new rviz::FloatProperty("Radius", 0.03, "Radius of the axes.", this,
75  SLOT(updatePoseAxisGeometry()));
76  pose_arrow_color_property_ = new rviz::ColorProperty("Pose Color", QColor(41, 170, 226), "Color to draw the poses.",
77  this, SLOT(updatePoseArrowColor()));
78  pose_arrow_shaft_length_property_ = new rviz::FloatProperty("Shaft Length", 0.1, "Length of the arrow shaft.",
79  this, SLOT(updatePoseArrowGeometry()));
80  pose_arrow_head_length_property_ = new rviz::FloatProperty("Head Length", 0.2, "Length of the arrow head.",
81  this, SLOT(updatePoseArrowGeometry()));
82  pose_arrow_shaft_diameter_property_ = new rviz::FloatProperty("Shaft Diameter", 0.1, "Diameter of the arrow shaft.",
83  this, SLOT(updatePoseArrowGeometry()));
84  pose_arrow_head_diameter_property_ = new rviz::FloatProperty("Head Diameter", 0.3, "Diameter of the arrow head.",
85  this, SLOT(updatePoseArrowGeometry()));
93 }
94 
96 {
98 }
99 
101 {
104 }
105 
107 {
108  MFDClass::reset();
110 }
111 
112 void PathDisplay::allocateAxesVector(std::vector<rviz::Axes*>& axes_vect, int num)
113 {
114  unsigned int num_u = static_cast<unsigned int>(num);
115  if (num_u > axes_vect.size())
116  {
117  for (size_t i = axes_vect.size(); i < num_u; i++)
118  {
122  axes_vect.push_back(axes);
123  }
124  }
125  else if (num_u < axes_vect.size())
126  {
127  for (int i = axes_vect.size() - 1; num <= i; i--)
128  {
129  delete axes_vect[i];
130  }
131  axes_vect.resize(num);
132  }
133 }
134 
135 void PathDisplay::allocateArrowVector(std::vector<rviz::Arrow*>& arrow_vect, int num)
136 {
137  unsigned int num_u = static_cast<unsigned int>(num);
138  if (num_u > arrow_vect.size())
139  {
140  for (size_t i = arrow_vect.size(); i < num_u; i++)
141  {
143  arrow_vect.push_back(arrow);
144  }
145  }
146  else if (num_u < arrow_vect.size())
147  {
148  for (int i = arrow_vect.size() - 1; num <= i; i--)
149  {
150  delete arrow_vect[i];
151  }
152  arrow_vect.resize(num);
153  }
154 }
155 
157 {
158  switch (getLineStyle())
159  {
160  case LineStyle::LINES:
161  default:
163  break;
164 
167  break;
168  }
169 
171 }
172 
174 {
175  float line_width = line_width_property_->getFloat();
176 
178  {
179  for (rviz::BillboardLine* billboard_line : billboard_lines_)
180  {
181  if (billboard_line) billboard_line->setLineWidth(line_width);
182  }
183  }
185 }
186 
188 {
189  scene_node_->setPosition(offset_property_->getVector());
191 }
192 
194 {
195  switch (getPoseStyle())
196  {
197  case PoseStyle::AXES:
205  break;
206  case PoseStyle::ARROWS:
214  break;
215  default:
223  }
225 }
226 
228 {
229  for (auto& axes_vect : axes_chain_)
230  {
231  for (auto& axes : axes_vect)
232  {
235  }
236  }
238 }
239 
241 {
242  Ogre::ColourValue color = pose_arrow_color_property_->getOgreColor();
243 
244  for (auto& arrow_vect : arrow_chain_)
245  {
246  for (auto& arrow : arrow_vect)
247  {
248  arrow->setColor(color);
249  }
250  }
252 }
253 
255 {
256  for (auto& arrow_vect : arrow_chain_)
257  {
258  for (auto& arrow : arrow_vect)
259  {
264  }
265  }
267 }
268 
270 {
271  // Destroy all simple lines, if any
272  for (auto& manual_object : manual_objects_)
273  {
274  if (manual_object)
275  {
276  manual_object->clear();
277  scene_manager_->destroyManualObject(manual_object);
278  manual_object = NULL; // ensure it doesn't get destroyed again
279  }
280  }
281 
282  // Destroy all billboards, if any
283  for (auto& billboard_line : billboard_lines_)
284  {
285  if (billboard_line)
286  {
287  delete billboard_line; // also destroys the corresponding scene node
288  billboard_line = NULL; // ensure it doesn't get destroyed again
289  }
290  }
291 
292  // Destroy Pose Vectors
293  for (auto& axes_vect : axes_chain_)
294  {
295  allocateAxesVector(axes_vect, 0);
296  }
297  axes_chain_.resize(0);
298 
299  for (auto& arrow_vect : arrow_chain_)
300  {
301  allocateArrowVector(arrow_vect, 0);
302  }
303  arrow_chain_.resize(0);
304 }
305 
307 {
308  // Delete old path objects
309  destroyObjects();
310 
311  // Read options
312  int buffer_length = buffer_length_property_->getInt();
313 
314  // Create new path objects
315  switch (getLineStyle())
316  {
317  case LineStyle::LINES: // simple lines with fixed width of 1px
318  manual_objects_.resize(buffer_length);
319  for (size_t i = 0; i < manual_objects_.size(); i++)
320  {
321  manual_objects_[i] = scene_manager_->createManualObject();
322  manual_objects_[i]->setDynamic(true);
323  scene_node_->attachObject(manual_objects_[i]);
324  }
325  break;
326 
327  case LineStyle::BILLBOARDS: // billboards with configurable width
328  billboard_lines_.resize(buffer_length);
329  for (size_t i = 0; i < billboard_lines_.size(); i++)
330  {
332  }
333  break;
334  }
335  axes_chain_.resize(buffer_length);
336  arrow_chain_.resize(buffer_length);
337 }
338 
339 void PathDisplay::processMessage(const nav_2d_msgs::Path2D::ConstPtr& msg)
340 {
341  // Calculate index of oldest element in cyclic buffer
342  size_t bufferIndex = messages_received_ % buffer_length_property_->getInt();
343 
344  LineStyle style = getLineStyle();
345  PoseStyle pose_style = getPoseStyle();
346  Ogre::ManualObject* manual_object = NULL;
347  rviz::BillboardLine* billboard_line = NULL;
348 
349  // Delete oldest element
350  switch (style)
351  {
352  case LineStyle::LINES:
353  manual_object = manual_objects_[bufferIndex];
354  manual_object->clear();
355  break;
356 
358  billboard_line = billboard_lines_[bufferIndex];
359  billboard_line->clear();
360  break;
361  }
362 
363  std::vector<rviz::Arrow*>& arrow_vect = arrow_chain_[bufferIndex];
364  std::vector<rviz::Axes*>& axes_vect = axes_chain_[bufferIndex];
365 
366  // Check if path contains invalid coordinate values
367  if (!validateFloats(*msg))
368  {
369  setStatus(rviz::StatusProperty::Error, "Topic", "Message contained invalid floating point values (nans or infs)");
370  return;
371  }
372 
373  // Lookup transform into fixed frame
374  Ogre::Vector3 position;
375  Ogre::Quaternion orientation;
376  if (!context_->getFrameManager()->getTransform(msg->header, position, orientation))
377  {
378  ROS_DEBUG("Error transforming from frame '%s' to frame '%s'",
379  msg->header.frame_id.c_str(), qPrintable(fixed_frame_));
380  }
381 
382  Ogre::Matrix4 transform(orientation);
383  transform.setTrans(position);
384 
385  // scene_node_->setPosition(position);
386  // scene_node_->setOrientation(orientation);
387 
388  Ogre::ColourValue color = color_property_->getOgreColor();
389  color.a = alpha_property_->getFloat();
390  Ogre::ColourValue arrow_color = pose_arrow_color_property_->getOgreColor();
391 
392  uint32_t num_points = msg->poses.size();
393  switch (style)
394  {
395  case LineStyle::LINES:
396  manual_object->estimateVertexCount(num_points);
397  manual_object->begin("BaseWhiteNoLighting", Ogre::RenderOperation::OT_LINE_STRIP);
398  break;
399 
401  billboard_line->setNumLines(1);
402  billboard_line->setMaxPointsPerLine(num_points);
403  billboard_line->setLineWidth(line_width_property_->getFloat());
404  break;
405  }
406  switch (pose_style)
407  {
408  case PoseStyle::NONE:
409  break;
410  case PoseStyle::AXES:
411  allocateAxesVector(axes_vect, num_points);
412  break;
413  case PoseStyle::ARROWS:
414  allocateArrowVector(arrow_vect, num_points);
415  break;
416  }
417 
418  for (uint32_t i = 0; i < num_points; ++i)
419  {
420  geometry_msgs::Pose pose = nav_2d_utils::pose2DToPose(msg->poses[i]);
421 
422  Ogre::Vector3 xpos = transform * Ogre::Vector3(pose.position.x,
423  pose.position.y,
424  pose.position.z);
425  const geometry_msgs::Quaternion& quat = pose.orientation;
426  Ogre::Quaternion xquat = orientation * Ogre::Quaternion(quat.w, quat.x, quat.y, quat.z);
427 
428  switch (style)
429  {
430  case LineStyle::LINES:
431  manual_object->position(xpos.x, xpos.y, xpos.z);
432  manual_object->colour(color);
433  break;
435  billboard_line->addPoint(xpos, color);
436  break;
437  }
438  switch (pose_style)
439  {
440  case PoseStyle::NONE:
441  break;
442 
443  case PoseStyle::AXES:
444  axes_vect[i]->setPosition(xpos);
445  axes_vect[i]->setOrientation(xquat);
446  break;
447 
448  case PoseStyle::ARROWS:
449  arrow_vect[i]->setColor(arrow_color);
450  arrow_vect[i]->set(pose_arrow_shaft_length_property_->getFloat(),
454  arrow_vect[i]->setPosition(xpos);
455  arrow_vect[i]->setDirection(xquat * Ogre::Vector3(1, 0, 0));
456  break;
457  }
458  }
459 
460  if (style == LineStyle::LINES)
461  manual_object->end();
462 
464 }
465 
466 } // namespace robot_nav_rviz_plugins
467 
rviz::BillboardLine::clear
void clear()
rviz::BillboardLine
rviz::IntProperty::setMin
void setMin(int min)
rviz::BillboardLine::setLineWidth
void setLineWidth(float width)
rviz::MessageFilterDisplay::reset
void reset() override
validate_floats.h
robot_nav_rviz_plugins::PathDisplay::destroyObjects
void destroyObjects()
Definition: path_display.cpp:269
robot_nav_rviz_plugins::PathDisplay::updatePoseArrowColor
void updatePoseArrowColor()
Definition: path_display.cpp:240
rviz::DisplayContext::queueRender
virtual void queueRender()=0
robot_nav_rviz_plugins::PathDisplay::allocateArrowVector
void allocateArrowVector(std::vector< rviz::Arrow * > &arrow_vect, int num)
Definition: path_display.cpp:135
NULL
#define NULL
robot_nav_rviz_plugins::PathDisplay::PoseStyle::NONE
@ NONE
robot_nav_rviz_plugins::PathDisplay::pose_arrow_color_property_
rviz::ColorProperty * pose_arrow_color_property_
Definition: path_display.h:103
robot_nav_rviz_plugins
Several reusable pieces for displaying polygons.
Definition: nav_grid_display.h:60
robot_nav_rviz_plugins::PathDisplay::processMessage
void processMessage(const nav_2d_msgs::Path2D::ConstPtr &msg) override
Definition: path_display.cpp:339
rviz::Arrow
rviz::StatusProperty::Error
Error
robot_nav_rviz_plugins::PathDisplay::updateStyle
void updateStyle()
Definition: path_display.cpp:156
robot_nav_rviz_plugins::validateFloats
bool validateFloats(const nav_grid::NavGridInfo &info)
Definition: validate_floats.h:49
rviz::Property::show
void show()
robot_nav_rviz_plugins::PathDisplay::axes_chain_
std::vector< std::vector< rviz::Axes * > > axes_chain_
Definition: path_display.h:89
robot_nav_rviz_plugins::PathDisplay::style_property_
rviz::EnumProperty * style_property_
Definition: path_display.h:92
robot_nav_rviz_plugins::PathDisplay::allocateAxesVector
void allocateAxesVector(std::vector< rviz::Axes * > &axes_vect, int num)
Definition: path_display.cpp:112
robot_nav_rviz_plugins::PathDisplay::updatePoseArrowGeometry
void updatePoseArrowGeometry()
Definition: path_display.cpp:254
robot_nav_rviz_plugins::PathDisplay::~PathDisplay
virtual ~PathDisplay()
Definition: path_display.cpp:95
robot_nav_rviz_plugins::PathDisplay::pose_axes_radius_property_
rviz::FloatProperty * pose_axes_radius_property_
Definition: path_display.h:102
robot_nav_rviz_plugins::PathDisplay::updateLineWidth
void updateLineWidth()
Definition: path_display.cpp:173
robot_nav_rviz_plugins::PathDisplay::updateBufferLength
void updateBufferLength()
Definition: path_display.cpp:306
rviz::Display::fixed_frame_
QString fixed_frame_
path_display.h
rviz::BillboardLine::setMaxPointsPerLine
void setMaxPointsPerLine(uint32_t max)
robot_nav_rviz_plugins::PathDisplay::PathDisplay
PathDisplay()
Definition: path_display.cpp:44
robot_nav_rviz_plugins::PathDisplay
Displays a nav_2d_msgs::Path2D message in Rviz.
Definition: path_display.h:54
rviz::FloatProperty::setMin
void setMin(float min)
rviz::ColorProperty
rviz::Display
rviz::EnumProperty
rviz::FloatProperty
robot_nav_rviz_plugins::PathDisplay::PoseStyle::ARROWS
@ ARROWS
robot_nav_rviz_plugins::PathDisplay::buffer_length_property_
rviz::IntProperty * buffer_length_property_
Definition: path_display.h:96
rviz::Property::hide
void hide()
rviz::Display::setStatus
virtual void setStatus(StatusProperty::Level level, const QString &name, const QString &text)
robot_nav_rviz_plugins::PathDisplay::reset
void reset() override
Definition: path_display.cpp:106
robot_nav_rviz_plugins::PathDisplay::updatePoseAxisGeometry
void updatePoseAxisGeometry()
Definition: path_display.cpp:227
robot_nav_rviz_plugins::PathDisplay::LineStyle::BILLBOARDS
@ BILLBOARDS
PLUGINLIB_EXPORT_CLASS
#define PLUGINLIB_EXPORT_CLASS(class_type, base_class_type)
robot_nav_rviz_plugins::PathDisplay::line_width_property_
rviz::FloatProperty * line_width_property_
Definition: path_display.h:95
robot_nav_rviz_plugins::PathDisplay::PoseStyle
PoseStyle
Definition: path_display.h:79
rviz::FloatProperty::getFloat
virtual float getFloat() const
rviz::EnumProperty::addOption
virtual void addOption(const QString &option, int value=0)
robot_nav_rviz_plugins::PathDisplay::updateOffset
void updateOffset()
Definition: path_display.cpp:187
ROS_DEBUG
#define ROS_DEBUG(...)
rviz::Display::scene_node_
Ogre::SceneNode * scene_node_
robot_nav_rviz_plugins::PathDisplay::billboard_lines_
std::vector< rviz::BillboardLine * > billboard_lines_
Definition: path_display.h:88
robot_nav_rviz_plugins::PathDisplay::pose_arrow_shaft_length_property_
rviz::FloatProperty * pose_arrow_shaft_length_property_
Definition: path_display.h:104
rviz::Display::scene_manager_
Ogre::SceneManager * scene_manager_
robot_nav_rviz_plugins::PathDisplay::pose_axes_length_property_
rviz::FloatProperty * pose_axes_length_property_
Definition: path_display.h:101
robot_nav_rviz_plugins::PathDisplay::pose_arrow_shaft_diameter_property_
rviz::FloatProperty * pose_arrow_shaft_diameter_property_
Definition: path_display.h:106
rviz::BillboardLine::setNumLines
void setNumLines(uint32_t num)
robot_nav_rviz_plugins::PathDisplay::pose_arrow_head_diameter_property_
rviz::FloatProperty * pose_arrow_head_diameter_property_
Definition: path_display.h:107
robot_nav_rviz_plugins::PathDisplay::pose_style_property_
rviz::EnumProperty * pose_style_property_
Definition: path_display.h:100
robot_nav_rviz_plugins::PathDisplay::arrow_chain_
std::vector< std::vector< rviz::Arrow * > > arrow_chain_
Definition: path_display.h:90
rviz::DisplayContext::getFrameManager
virtual FrameManager * getFrameManager() const=0
rviz::MessageFilterDisplay< nav_2d_msgs::Path2D >::messages_received_
uint32_t messages_received_
rviz::Axes
rviz::MessageFilterDisplay::onInitialize
void onInitialize() override
robot_nav_rviz_plugins::PathDisplay::pose_arrow_head_length_property_
rviz::FloatProperty * pose_arrow_head_length_property_
Definition: path_display.h:105
rviz::FrameManager::getTransform
bool getTransform(const Header &header, Ogre::Vector3 &position, Ogre::Quaternion &orientation)
rviz::Display::context_
DisplayContext * context_
robot_nav_rviz_plugins::PathDisplay::LineStyle::LINES
@ LINES
robot_nav_rviz_plugins::PathDisplay::alpha_property_
rviz::FloatProperty * alpha_property_
Definition: path_display.h:94
class_list_macros.hpp
robot_nav_rviz_plugins::PathDisplay::onInitialize
void onInitialize() override
Definition: path_display.cpp:100
rviz::IntProperty::getInt
virtual int getInt() const
conversions.h
rviz::VectorProperty
robot_nav_rviz_plugins::PathDisplay::updatePoseStyle
void updatePoseStyle()
Definition: path_display.cpp:193
rviz::VectorProperty::getVector
virtual Ogre::Vector3 getVector() const
nav_2d_utils::pose2DToPose
geometry_msgs::Pose pose2DToPose(const geometry_msgs::Pose2D &pose2d)
robot_nav_rviz_plugins::PathDisplay::PoseStyle::AXES
@ AXES
robot_nav_rviz_plugins::PathDisplay::getPoseStyle
PoseStyle getPoseStyle() const
Definition: path_display.h:81
robot_nav_rviz_plugins::PathDisplay::offset_property_
rviz::VectorProperty * offset_property_
Definition: path_display.h:97
robot_nav_rviz_plugins::PathDisplay::color_property_
rviz::ColorProperty * color_property_
Definition: path_display.h:93
rviz::ColorProperty::getOgreColor
Ogre::ColourValue getOgreColor() const
robot_nav_rviz_plugins::PathDisplay::manual_objects_
std::vector< Ogre::ManualObject * > manual_objects_
Definition: path_display.h:87
robot_nav_rviz_plugins::PathDisplay::LineStyle
LineStyle
Definition: path_display.h:78
robot_nav_rviz_plugins::PathDisplay::getLineStyle
LineStyle getLineStyle() const
Definition: path_display.h:80
rviz::BillboardLine::addPoint
void addPoint(const Ogre::Vector3 &point)
rviz::IntProperty


robot_nav_rviz_plugins
Author(s):
autogenerated on Sun May 18 2025 02:47:50