Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030 #include "mesh_resource_marker.h"
00031
00032 #include "marker_selection_handler.h"
00033 #include "rviz/default_plugin/marker_display.h"
00034 #include "rviz/selection/selection_manager.h"
00035
00036 #include "rviz/visualization_manager.h"
00037 #include "rviz/mesh_loader.h"
00038 #include "marker_display.h"
00039
00040 #include <OGRE/OgreSceneNode.h>
00041 #include <OGRE/OgreSceneManager.h>
00042 #include <OGRE/OgreEntity.h>
00043 #include <OGRE/OgreSubEntity.h>
00044 #include <OGRE/OgreMaterialManager.h>
00045 #include <OGRE/OgreTextureManager.h>
00046
00047 namespace rviz
00048 {
00049
00050 MeshResourceMarker::MeshResourceMarker(MarkerDisplay* owner, VisualizationManager* manager, Ogre::SceneNode* parent_node)
00051 : MarkerBase(owner, manager, parent_node)
00052 , entity_(0)
00053 {
00054 }
00055
00056 MeshResourceMarker::~MeshResourceMarker()
00057 {
00058 reset();
00059 }
00060
00061 void MeshResourceMarker::reset()
00062 {
00063
00064 if (entity_)
00065 {
00066 vis_manager_->getSceneManager()->destroyEntity( entity_ );
00067 entity_ = 0;
00068 }
00069
00070
00071 S_MaterialPtr::iterator it;
00072 for ( it = materials_.begin(); it!=materials_.end(); it++ )
00073 {
00074 Ogre::MaterialPtr material = *it;
00075 if (!material.isNull())
00076 {
00077 for (size_t i = 0; i < material->getNumTechniques(); ++i)
00078 {
00079 Ogre::Technique* t = material->getTechnique(i);
00080
00081
00082 if (t->getSchemeName() == "Pick")
00083 {
00084 Ogre::TextureManager::getSingleton().remove(t->getPass(0)->getTextureUnitState(0)->getTextureName());
00085 }
00086 }
00087
00088 material->unload();
00089 Ogre::MaterialManager::getSingleton().remove(material->getName());
00090 }
00091 }
00092 materials_.clear();
00093 }
00094
00095 void MeshResourceMarker::onNewMessage(const MarkerConstPtr& old_message, const MarkerConstPtr& new_message)
00096 {
00097 ROS_ASSERT(new_message->type == visualization_msgs::Marker::MESH_RESOURCE);
00098
00099 bool need_color = false;
00100
00101 scene_node_->setVisible(false);
00102
00103 if( !entity_ ||
00104 old_message->mesh_resource != new_message->mesh_resource ||
00105 old_message->mesh_use_embedded_materials != new_message->mesh_use_embedded_materials )
00106 {
00107 reset();
00108
00109 if (new_message->mesh_resource.empty())
00110 {
00111 return;
00112 }
00113
00114 if (loadMeshFromResource(new_message->mesh_resource).isNull())
00115 {
00116 std::stringstream ss;
00117 ss << "Mesh resource marker [" << getStringID() << "] could not load [" << new_message->mesh_resource << "]";
00118 if ( owner_ )
00119 {
00120 owner_->setMarkerStatus(getID(), status_levels::Error, ss.str());
00121 }
00122 ROS_DEBUG("%s", ss.str().c_str());
00123 return;
00124 }
00125
00126 static uint32_t count = 0;
00127 std::stringstream ss;
00128 ss << "mesh_resource_marker_" << count++;
00129 std::string id = ss.str();
00130 entity_ = vis_manager_->getSceneManager()->createEntity(id, new_message->mesh_resource);
00131 scene_node_->attachObject(entity_);
00132 need_color = true;
00133
00134
00135 ss << "Material";
00136 Ogre::MaterialPtr default_material = Ogre::MaterialManager::getSingleton().create( ss.str(), ROS_PACKAGE_NAME );
00137 default_material->setReceiveShadows(false);
00138 default_material->getTechnique(0)->setLightingEnabled(true);
00139 default_material->getTechnique(0)->setAmbient( 0.5, 0.5, 0.5 );
00140 materials_.insert( default_material );
00141
00142 if ( new_message->mesh_use_embedded_materials )
00143 {
00144
00145 S_MaterialPtr materials = getMaterials();
00146
00147 S_MaterialPtr::iterator it;
00148 for ( it = materials.begin(); it!=materials.end(); it++ )
00149 {
00150 if( (*it)->getName() != "BaseWhiteNoLighting" )
00151 {
00152 Ogre::MaterialPtr new_material = (*it)->clone( id + (*it)->getName() );
00153 materials_.insert( new_material );
00154 }
00155 }
00156
00157
00158 for (uint32_t i = 0; i < entity_->getNumSubEntities(); ++i)
00159 {
00160 std::string mat_name = entity_->getSubEntity(i)->getMaterialName();
00161 if( mat_name != "BaseWhiteNoLighting" )
00162 {
00163 entity_->getSubEntity(i)->setMaterialName( id + mat_name );
00164 }
00165 else
00166 {
00167
00168
00169
00170
00171 entity_->getSubEntity(i)->setMaterial( default_material );
00172 }
00173 }
00174 }
00175 else
00176 {
00177 entity_->setMaterial( default_material );
00178 }
00179
00180 vis_manager_->getSelectionManager()->removeObject(coll_);
00181 coll_ = vis_manager_->getSelectionManager()->createCollisionForEntity(entity_, SelectionHandlerPtr(new MarkerSelectionHandler(this, MarkerID(new_message->ns, new_message->id))), coll_);
00182 }
00183
00184 if( need_color ||
00185 old_message->color.r != new_message->color.r ||
00186 old_message->color.g != new_message->color.g ||
00187 old_message->color.b != new_message->color.b ||
00188 old_message->color.a != new_message->color.a )
00189 {
00190 float r = new_message->color.r;
00191 float g = new_message->color.g;
00192 float b = new_message->color.b;
00193 float a = new_message->color.a;
00194
00195
00196
00197
00198
00199
00200
00201 if( new_message->mesh_use_embedded_materials && r == 0 && g == 0 && b == 0 && a == 0 )
00202 {
00203 r = 1; g = 1; b = 1; a = 1;
00204 }
00205
00206 Ogre::SceneBlendType blending;
00207 bool depth_write;
00208
00209 if ( a < 0.9998 )
00210 {
00211 blending = Ogre::SBT_TRANSPARENT_ALPHA;
00212 depth_write = false;
00213 }
00214 else
00215 {
00216 blending = Ogre::SBT_REPLACE;
00217 depth_write = true;
00218 }
00219
00220 S_MaterialPtr::iterator it;
00221 for( it = materials_.begin(); it != materials_.end(); it++ )
00222 {
00223 Ogre::Technique* technique = (*it)->getTechnique( 0 );
00224
00225 technique->setAmbient( r*0.5, g*0.5, b*0.5 );
00226 technique->setDiffuse( r, g, b, a );
00227 technique->setSceneBlending( blending );
00228 technique->setDepthWriteEnabled( depth_write );
00229 }
00230 }
00231
00232 Ogre::Vector3 pos, scale;
00233 Ogre::Quaternion orient;
00234 transform(new_message, pos, orient, scale);
00235
00236 scene_node_->setVisible(true);
00237 setPosition(pos);
00238 setOrientation(orient);
00239
00240
00241
00242
00243 if( scale.x == 1.0 && scale.y == 1.0 && scale.z == 1.0 )
00244 {
00245 scale.z = 1.0001;
00246 }
00247 scene_node_->setScale(scale);
00248 }
00249
00250 S_MaterialPtr MeshResourceMarker::getMaterials()
00251 {
00252 S_MaterialPtr materials;
00253 if( entity_ )
00254 {
00255 extractMaterials( entity_, materials );
00256 }
00257 return materials;
00258 }
00259
00260 }
00261