robot_model_display.cpp
Go to the documentation of this file.
00001 /*
00002  * Copyright (c) 2008, Willow Garage, Inc.
00003  * All rights reserved.
00004  *
00005  * Redistribution and use in source and binary forms, with or without
00006  * modification, are permitted provided that the following conditions are met:
00007  *
00008  *     * Redistributions of source code must retain the above copyright
00009  *       notice, this list of conditions and the following disclaimer.
00010  *     * Redistributions in binary form must reproduce the above copyright
00011  *       notice, this list of conditions and the following disclaimer in the
00012  *       documentation and/or other materials provided with the distribution.
00013  *     * Neither the name of the Willow Garage, Inc. nor the names of its
00014  *       contributors may be used to endorse or promote products derived from
00015  *       this software without specific prior written permission.
00016  *
00017  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
00018  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
00019  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
00020  * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
00021  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
00022  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
00023  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
00024  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
00025  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
00026  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
00027  * POSSIBILITY OF SUCH DAMAGE.
00028  */
00029 
00030 #include "robot_model_display.h"
00031 #include "rviz/visualization_manager.h"
00032 #include "rviz/robot/robot.h"
00033 #include "rviz/robot/tf_link_updater.h"
00034 #include "rviz/properties/property.h"
00035 #include "rviz/properties/property_manager.h"
00036 
00037 #include <urdf/model.h>
00038 
00039 #include <OGRE/OgreSceneNode.h>
00040 #include <OGRE/OgreSceneManager.h>
00041 
00042 #include <tf/transform_listener.h>
00043 
00044 namespace rviz
00045 {
00046 
00047 void linkUpdaterStatusFunction(StatusLevel level, const std::string& link_name, const std::string& text, RobotModelDisplay* display)
00048 {
00049   display->setStatus(level, link_name, text);
00050 }
00051 
00052 RobotModelDisplay::RobotModelDisplay()
00053 : Display()
00054 , description_param_("robot_description")
00055 , has_new_transforms_( false )
00056 , time_since_last_transform_( 0.0f )
00057 , update_rate_( 0.0f )
00058 {
00059 }
00060 
00061 RobotModelDisplay::~RobotModelDisplay()
00062 {
00063   delete robot_;
00064 }
00065 
00066 void RobotModelDisplay::onInitialize()
00067 {
00068   robot_ = new Robot( vis_manager_, "Robot: " + name_ );
00069 
00070   setVisualVisible( true );
00071   setCollisionVisible( false );
00072 
00073   setAlpha(1.0f);
00074 }
00075 
00076 void RobotModelDisplay::setAlpha( float alpha )
00077 {
00078   alpha_ = alpha;
00079 
00080   robot_->setAlpha(alpha_);
00081 
00082   propertyChanged(alpha_property_);
00083 }
00084 
00085 void RobotModelDisplay::setRobotDescription( const std::string& description_param )
00086 {
00087   description_param_ = description_param;
00088 
00089   propertyChanged(robot_description_property_);
00090 
00091   if ( isEnabled() )
00092   {
00093     load();
00094     causeRender();
00095   }
00096 }
00097 
00098 void RobotModelDisplay::setVisualVisible( bool visible )
00099 {
00100   robot_->setVisualVisible( visible );
00101 
00102   propertyChanged(visual_enabled_property_);
00103 
00104   causeRender();
00105 }
00106 
00107 void RobotModelDisplay::setCollisionVisible( bool visible )
00108 {
00109   robot_->setCollisionVisible( visible );
00110 
00111   propertyChanged(collision_enabled_property_);
00112 
00113   causeRender();
00114 }
00115 
00116 void RobotModelDisplay::setUpdateRate( float rate )
00117 {
00118   update_rate_ = rate;
00119 
00120   propertyChanged(update_rate_property_);
00121 
00122   causeRender();
00123 }
00124 
00125 void RobotModelDisplay::setTFPrefix(const std::string& prefix)
00126 {
00127   tf_prefix_ = prefix;
00128 
00129   propertyChanged(tf_prefix_property_);
00130 
00131   causeRender();
00132 }
00133 
00134 bool RobotModelDisplay::isVisualVisible()
00135 {
00136   return robot_->isVisualVisible();
00137 }
00138 
00139 bool RobotModelDisplay::isCollisionVisible()
00140 {
00141   return robot_->isCollisionVisible();
00142 }
00143 
00144 void RobotModelDisplay::load()
00145 {
00146   std::string content;
00147   if (!update_nh_.getParam(description_param_, content))
00148   {
00149     std::string loc;
00150     if (update_nh_.searchParam(description_param_, loc))
00151     {
00152       update_nh_.getParam(loc, content);
00153     }
00154     else
00155     {
00156       clear();
00157 
00158       std::stringstream ss;
00159       ss << "Parameter [" << description_param_ << "] does not exist, and was not found by searchParam()";
00160       setStatus(status_levels::Error, "URDF", ss.str());
00161       return;
00162     }
00163   }
00164 
00165   if (content.empty())
00166   {
00167     clear();
00168     setStatus(status_levels::Error, "URDF", "URDF is empty");
00169     return;
00170   }
00171 
00172   if ( content == robot_description_ )
00173   {
00174     return;
00175   }
00176 
00177   robot_description_ = content;
00178 
00179   TiXmlDocument doc;
00180   doc.Parse(robot_description_.c_str());
00181   if (!doc.RootElement())
00182   {
00183     clear();
00184     setStatus(status_levels::Error, "URDF", "URDF failed XML parse");
00185     return;
00186   }
00187 
00188   urdf::Model descr;
00189   if (!descr.initXml(doc.RootElement()))
00190   {
00191     clear();
00192     setStatus(status_levels::Error, "URDF", "URDF failed Model parse");
00193     return;
00194   }
00195 
00196   setStatus(status_levels::Ok, "URDF", "URDF parsed OK");
00197   robot_->load( doc.RootElement(), descr );
00198   robot_->update( TFLinkUpdater(vis_manager_->getFrameManager(), boost::bind(linkUpdaterStatusFunction, _1, _2, _3, this), tf_prefix_) );
00199 }
00200 
00201 void RobotModelDisplay::onEnable()
00202 {
00203   load();
00204   robot_->setVisible( true );
00205 }
00206 
00207 void RobotModelDisplay::onDisable()
00208 {
00209   robot_->setVisible( false );
00210   clear();
00211 }
00212 
00213 void RobotModelDisplay::update(float wall_dt, float ros_dt)
00214 {
00215   time_since_last_transform_ += wall_dt;
00216 
00217   bool update = update_rate_ < 0.0001f || time_since_last_transform_ >= update_rate_;
00218 
00219   if ( has_new_transforms_ || update )
00220   {
00221     robot_->update(TFLinkUpdater(vis_manager_->getFrameManager(), boost::bind(linkUpdaterStatusFunction, _1, _2, _3, this), tf_prefix_));
00222     causeRender();
00223 
00224     has_new_transforms_ = false;
00225     time_since_last_transform_ = 0.0f;
00226   }
00227 }
00228 
00229 void RobotModelDisplay::targetFrameChanged()
00230 {
00231   has_new_transforms_ = true;
00232 }
00233 
00234 void RobotModelDisplay::createProperties()
00235 {
00236   visual_enabled_property_ = property_manager_->createProperty<BoolProperty>( "Visual Enabled", property_prefix_, boost::bind( &RobotModelDisplay::isVisualVisible, this ),
00237                                                                                boost::bind( &RobotModelDisplay::setVisualVisible, this, _1 ), parent_category_, this );
00238   setPropertyHelpText(visual_enabled_property_, "Whether to display the visual representation of the robot.");
00239   collision_enabled_property_ = property_manager_->createProperty<BoolProperty>( "Collision Enabled", property_prefix_, boost::bind( &RobotModelDisplay::isCollisionVisible, this ),
00240                                                                                  boost::bind( &RobotModelDisplay::setCollisionVisible, this, _1 ), parent_category_, this );
00241   setPropertyHelpText(collision_enabled_property_, "Whether to display the collision representation of the robot.");
00242   update_rate_property_ = property_manager_->createProperty<FloatProperty>( "Update Interval", property_prefix_, boost::bind( &RobotModelDisplay::getUpdateRate, this ),
00243                                                                                   boost::bind( &RobotModelDisplay::setUpdateRate, this, _1 ), parent_category_, this );
00244   setPropertyHelpText(update_rate_property_, "Interval at which to update the links, in seconds.  0 means to update every update cycle.");
00245   FloatPropertyPtr float_prop = update_rate_property_.lock();
00246   float_prop->setMin( 0.0 );
00247   float_prop->addLegacyName("Update Rate");
00248 
00249   alpha_property_ = property_manager_->createProperty<FloatProperty>( "Alpha", property_prefix_, boost::bind( &RobotModelDisplay::getAlpha, this ),
00250                                                                       boost::bind( &RobotModelDisplay::setAlpha, this, _1 ), parent_category_, this );
00251   setPropertyHelpText(alpha_property_, "Amount of transparency to apply to the links.");
00252   float_prop = alpha_property_.lock();
00253   float_prop->setMin( 0.0 );
00254   float_prop->setMax( 1.0 );
00255 
00256   robot_description_property_ = property_manager_->createProperty<StringProperty>( "Robot Description", property_prefix_, boost::bind( &RobotModelDisplay::getRobotDescription, this ),
00257                                                                                    boost::bind( &RobotModelDisplay::setRobotDescription, this, _1 ), parent_category_, this );
00258   setPropertyHelpText(robot_description_property_, "Name of the parameter to search for to load the robot description.");
00259 
00260   tf_prefix_property_ = property_manager_->createProperty<StringProperty>( "TF Prefix", property_prefix_, boost::bind( &RobotModelDisplay::getTFPrefix, this ),
00261                                                                            boost::bind( &RobotModelDisplay::setTFPrefix, this, _1 ), parent_category_, this );
00262   setPropertyHelpText(tf_prefix_property_, "Robot Model normally assumes the link name is the same as the tf frame name.  This option allows you to set a prefix.  Mainly useful for multi-robot situations.");
00263 
00264   robot_->setPropertyManager( property_manager_, parent_category_ );
00265 }
00266 
00267 void RobotModelDisplay::clear()
00268 {
00269   robot_->clear();
00270   clearStatuses();
00271   robot_description_.clear();
00272 }
00273 
00274 void RobotModelDisplay::reset()
00275 {
00276   Display::reset();
00277   has_new_transforms_ = true;
00278 }
00279 
00280 } // namespace rviz
00281 


rviz_qt
Author(s): Dave Hershberger
autogenerated on Fri Dec 6 2013 20:56:53