30 #include <boost/make_shared.hpp> 34 #include <OgreSceneNode.h> 35 #include <OgreSceneManager.h> 36 #include <OgreMaterialManager.h> 37 #include <OgreResourceGroupManager.h> 38 #include <OgreSubEntity.h> 40 #include <OgreRenderWindow.h> 60 , pose_changed_(false)
61 , time_since_last_feedback_(0)
63 , pose_update_requested_(false)
65 , show_visual_aids_(false)
79 boost::recursive_mutex::scoped_lock lock(
mutex_);
80 Ogre::Vector3 position(message.pose.position.x, message.pose.position.y, message.pose.position.z);
81 Ogre::Quaternion orientation(message.pose.orientation.w, message.pose.orientation.x,
82 message.pose.orientation.y, message.pose.orientation.z);
84 if (orientation.w == 0 && orientation.x == 0 && orientation.y == 0 && orientation.z == 0)
99 boost::recursive_mutex::scoped_lock lock(
mutex_);
102 name_ = message.name;
105 if (message.controls.empty())
117 position_ = Ogre::Vector3(message.pose.position.x, message.pose.position.y, message.pose.position.z);
129 has_menu_ = !message.menu_entries.empty();
148 std::set<std::string> old_names_to_delete;
149 M_ControlPtr::const_iterator ci;
152 old_names_to_delete.insert((*ci).first);
156 for (
unsigned i = 0; i < message.controls.size(); i++)
158 const visualization_msgs::InteractiveMarkerControl& control_message = message.controls[i];
159 M_ControlPtr::iterator search_iter =
controls_.find(control_message.name);
166 control = (*search_iter).second;
172 controls_[control_message.name] = control;
175 control->processMessage(control_message);
179 old_names_to_delete.erase(control_message.name);
183 std::set<std::string>::iterator si;
184 for (si = old_names_to_delete.begin(); si != old_names_to_delete.end(); si++)
192 if (!message.description.empty())
200 menu_.reset(
new QMenu());
205 for (
unsigned m = 0; m < message.menu_entries.size(); m++)
207 const visualization_msgs::MenuEntry& entry = message.menu_entries[m];
211 if (entry.parent_id == 0)
218 std::map<uint32_t, MenuNode>::iterator parent_it =
menu_entries_.find(entry.parent_id);
221 ROS_ERROR(
"interactive marker menu entry %u found before its parent id %u. Ignoring.",
222 entry.id, entry.parent_id);
226 (*parent_it).second.child_ids.push_back(entry.id);
235 std::ostringstream
s;
251 for (
size_t id_index = 0; id_index < ids.size(); id_index++)
253 uint32_t
id = ids[id_index];
254 std::map<uint32_t, MenuNode>::iterator node_it =
menu_entries_.find(
id);
256 "interactive marker menu entry %u not found during populateMenu().", id);
259 if (node.child_ids.empty())
264 menu->addAction(action);
269 QMenu* sub_menu = menu->addMenu(
makeMenuString(node.entry.title));
278 if (entry.find(
"[x]") == 0)
280 menu_entry = QChar(0x2611) + QString::fromStdString(entry.substr(3));
282 else if (entry.find(
"[ ]") == 0)
284 menu_entry = QChar(0x2610) + QString::fromStdString(entry.substr(3));
288 menu_entry = QChar(0x3000) + QString::fromStdString(entry);
296 boost::recursive_mutex::scoped_lock lock(
mutex_);
297 Ogre::Vector3 reference_position;
298 Ogre::Quaternion reference_orientation;
317 #pragma GCC diagnostic push 318 #pragma GCC diagnostic ignored "-Wdeprecated-declarations" 325 #pragma GCC diagnostic pop 329 std::ostringstream
s;
330 s <<
"Error getting time of latest transform between " <<
reference_frame_ <<
" and " 331 << fixed_frame <<
": " << error <<
" (error code: " << retval <<
")";
340 reference_orientation))
359 boost::recursive_mutex::scoped_lock lock(
mutex_);
366 M_ControlPtr::iterator it;
369 (*it).second->update();
385 visualization_msgs::InteractiveMarkerFeedback feedback;
386 feedback.event_type = visualization_msgs::InteractiveMarkerFeedback::KEEP_ALIVE;
394 boost::recursive_mutex::scoped_lock lock(
mutex_);
395 visualization_msgs::InteractiveMarkerFeedback feedback;
396 feedback.event_type = visualization_msgs::InteractiveMarkerFeedback::POSE_UPDATE;
404 boost::recursive_mutex::scoped_lock lock(
mutex_);
414 setPose(position, orientation,
"");
419 Ogre::Quaternion orientation,
420 const std::string& control_name)
422 boost::recursive_mutex::scoped_lock lock(
mutex_);
431 M_ControlPtr::iterator it;
444 boost::recursive_mutex::scoped_lock lock(
mutex_);
453 boost::recursive_mutex::scoped_lock lock(
mutex_);
459 boost::recursive_mutex::scoped_lock lock(
mutex_);
460 M_ControlPtr::iterator it;
463 (*it).second->setShowVisualAids(show);
470 boost::recursive_mutex::scoped_lock lock(
mutex_);
476 boost::recursive_mutex::scoped_lock lock(
mutex_);
482 boost::recursive_mutex::scoped_lock lock(
mutex_);
489 boost::recursive_mutex::scoped_lock lock(
mutex_);
500 const Ogre::Vector3& cursor_pos,
501 const Ogre::Quaternion& ,
502 const std::string& control_name)
504 boost::recursive_mutex::scoped_lock lock(
mutex_);
508 Ogre::Vector3 point_rel_world = cursor_pos;
509 bool got_3D_point =
true;
511 visualization_msgs::InteractiveMarkerFeedback feedback;
512 feedback.control_name = control_name;
513 feedback.marker_name =
name_;
516 feedback.event_type = ((uint8_t)visualization_msgs::InteractiveMarkerFeedback::POSE_UPDATE);
519 feedback.event_type = (
event.type == QEvent::MouseButtonPress ?
520 (uint8_t)visualization_msgs::InteractiveMarkerFeedback::MOUSE_DOWN :
521 (uint8_t)visualization_msgs::InteractiveMarkerFeedback::MOUSE_UP);
534 if (event.
rightUp() &&
event.buttons_down == Qt::NoButton)
537 Ogre::Vector3 three_d_point = cursor_pos;
538 bool valid_point =
true;
540 QCursor::setPos(event.
panel->mapToGlobal(QPoint(mouse_pos.x, mouse_pos.y)));
541 showMenu(event, control_name, three_d_point, valid_point);
551 boost::recursive_mutex::scoped_lock lock(
mutex_);
555 Ogre::Vector3 point_rel_world;
559 visualization_msgs::InteractiveMarkerFeedback feedback;
560 feedback.control_name = control_name;
561 feedback.marker_name =
name_;
564 feedback.event_type = ((uint8_t)visualization_msgs::InteractiveMarkerFeedback::POSE_UPDATE);
567 feedback.event_type = (
event.type == QEvent::MouseButtonPress ?
568 (uint8_t)visualization_msgs::InteractiveMarkerFeedback::MOUSE_DOWN :
569 (uint8_t)visualization_msgs::InteractiveMarkerFeedback::MOUSE_UP);
582 if (event.
rightUp() &&
event.buttons_down == Qt::NoButton)
585 Ogre::Vector3 three_d_point;
588 showMenu(event, control_name, three_d_point, valid_point);
598 const std::string& control_name,
599 const Ogre::Vector3& three_d_point,
606 event.panel->showContextMenu(
menu_);
613 boost::recursive_mutex::scoped_lock lock(
mutex_);
615 std::map<uint32_t, MenuNode>::iterator it =
menu_entries_.find(menu_item_id);
619 visualization_msgs::MenuEntry& entry = it->second.entry;
621 std::string
command = entry.command;
622 uint8_t command_type = entry.command_type;
624 if (command_type == visualization_msgs::MenuEntry::FEEDBACK)
626 visualization_msgs::InteractiveMarkerFeedback feedback;
627 feedback.event_type = visualization_msgs::InteractiveMarkerFeedback::MENU_SELECT;
628 feedback.menu_entry_id = entry.id;
632 else if (command_type == visualization_msgs::MenuEntry::ROSRUN)
634 std::string sys_cmd =
"rosrun " + command;
640 else if (command_type == visualization_msgs::MenuEntry::ROSLAUNCH)
642 std::string sys_cmd =
"roslaunch " + command;
653 bool mouse_point_valid,
654 const Ogre::Vector3& mouse_point_rel_world)
656 boost::recursive_mutex::scoped_lock lock(
mutex_);
658 feedback.marker_name =
name_;
676 feedback.mouse_point_valid = mouse_point_valid;
677 if (mouse_point_valid)
679 Ogre::Vector3 mouse_rel_reference =
681 feedback.mouse_point.x = mouse_rel_reference.x;
682 feedback.mouse_point.y = mouse_rel_reference.y;
683 feedback.mouse_point.z = mouse_rel_reference.z;
697 feedback.pose.position.x = world_position.x;
698 feedback.pose.position.y = world_position.y;
699 feedback.pose.position.z = world_position.z;
700 feedback.pose.orientation.x = world_orientation.x;
701 feedback.pose.orientation.y = world_orientation.y;
702 feedback.pose.orientation.z = world_orientation.z;
703 feedback.pose.orientation.w = world_orientation.w;
705 feedback.mouse_point_valid = mouse_point_valid;
706 feedback.mouse_point.x = mouse_point_rel_world.x;
707 feedback.mouse_point.y = mouse_point_rel_world.y;
708 feedback.mouse_point.z = mouse_point_rel_world.z;
boost::recursive_mutex mutex_
void translate(Ogre::Vector3 delta_position, const std::string &control_name)
double time_since_last_feedback_
void setOrientation(const Ogre::Quaternion &orientation) override
Set the orientation of the object.
void setShowVisualAids(bool show)
std::string last_control_name_
bool transformHasProblems(const std::string &frame, ros::Time time, std::string &error)
Check to see if a transform is known between a given frame and the fixed frame.
Ogre::Viewport * viewport
void setShowDescription(bool show)
void rotate(Ogre::Quaternion delta_orientation, const std::string &control_name)
INTERACTIVE_MARKERS_PUBLIC visualization_msgs::InteractiveMarkerControl makeTitle(const visualization_msgs::InteractiveMarker &msg)
~InteractiveMarker() override
Ogre::Vector3 three_d_point_for_menu_
void populateMenu(QMenu *menu, std::vector< uint32_t > &ids)
boost::shared_ptr< boost::thread > sys_thread_
Ogre::Vector3 requested_position_
Ogre::Vector2 project3DPointToViewportXY(const Ogre::Viewport *view, const Ogre::Vector3 &pos)
Given a viewport and a 3D position in world coordinates, project that point into the view plane...
QString makeMenuString(const std::string &entry)
void publishFeedback(visualization_msgs::InteractiveMarkerFeedback &feedback, bool mouse_point_valid=false, const Ogre::Vector3 &mouse_point_rel_world=Ogre::Vector3(0, 0, 0))
Pure-virtual base class for objects which give Display subclasses context in which to work...
void handleMenuSelect(int menu_item_id)
ROSLIB_DECL std::string command(const std::string &cmd)
bool handle3DCursorEvent(ViewportMouseEvent &event, const Ogre::Vector3 &cursor_pos, const Ogre::Quaternion &cursor_rot, const std::string &control_name)
bool processMessage(const visualization_msgs::InteractiveMarker &message)
#define ROS_ASSERT_MSG(cond,...)
InteractiveMarker(Ogre::SceneNode *scene_node, DisplayContext *context)
Ogre::Quaternion requested_orientation_
InteractiveMarkerControlPtr description_control_
virtual FrameManager * getFrameManager() const =0
Return the FrameManager instance.
virtual SelectionManager * getSelectionManager() const =0
Return a pointer to the SelectionManager.
void showMenu(ViewportMouseEvent &event, const std::string &control_name, const Ogre::Vector3 &three_d_point, bool valid_point)
tf::TransformListener * getTFClient()
Return the tf::TransformListener used to receive transform data.
const std::string & getFixedFrame()
Return the current fixed frame name.
float normalizeQuaternion(float &w, float &x, float &y, float &z)
An object that displays a set of X/Y/Z axes, with X=Red, Y=Green, Z=Blue.
bool pose_update_requested_
Qt::MouseButton acting_button
void userFeedback(visualization_msgs::InteractiveMarkerFeedback &feedback)
std::vector< uint32_t > top_level_menu_ids_
void setPosition(const Ogre::Vector3 &position) override
Set the position of this object.
virtual Ogre::SceneManager * getSceneManager() const =0
Returns the Ogre::SceneManager used for the main RenderPanel.
virtual void queueRender()=0
Queues a render. Multiple calls before a render happens will only cause a single render.
virtual QString getFixedFrame() const =0
Return the fixed frame name.
#define ROS_INFO_STREAM(args)
void setPose(Ogre::Vector3 position, Ogre::Quaternion orientation, const std::string &control_name)
void statusUpdate(StatusProperty::Level level, const std::string &name, const std::string &text)
bool getTransform(const Header &header, Ogre::Vector3 &position, Ogre::Quaternion &orientation)
Return the pose for a header, relative to the fixed frame, in Ogre classes.
void set(float length, float radius)
Set the parameters on this object.
DisplayContext * context_
std::string reference_frame_
boost::shared_ptr< QMenu > menu_
Ogre::Quaternion orientation_
void update(float wall_dt)
void setShowAxes(bool show)
void requestPoseUpdate(Ogre::Vector3 position, Ogre::Quaternion orientation)
bool handleMouseEvent(ViewportMouseEvent &event, const std::string &control_name)
bool got_3d_point_for_menu_
std::map< uint32_t, MenuNode > menu_entries_
Ogre::SceneNode * getSceneNode()
Get the scene node associated with this object.
bool get3DPoint(Ogre::Viewport *viewport, const int x, const int y, Ogre::Vector3 &result_point)
void updateReferencePose()
ros::Time reference_time_
Ogre::SceneNode * reference_node_