but_distance_circular_indicator.cpp
Go to the documentation of this file.
00001 /******************************************************************************
00002  * \file
00003  *
00004  * $Id: but_distance_circular_indicator.cpp 810 2012-05-19 21:47:51Z stancl $
00005  *
00006  * Copyright (C) Brno University of Technology
00007  *
00008  * This file is part of software developed by dcgm-robotics@FIT group.
00009  *
00010  * Author: Tomas Lokaj (xlokaj03@stud.fit.vutbr.cz)
00011  * Supervised by: Michal Spanel (spanel@fit.vutbr.cz)
00012  * Date: 11/04/2012
00013  * 
00014  * This file is free software: you can redistribute it and/or modify
00015  * it under the terms of the GNU Lesser General Public License as published by
00016  * the Free Software Foundation, either version 3 of the License, or
00017  * (at your option) any later version.
00018  * 
00019  * This file is distributed in the hope that it will be useful,
00020  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00021  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00022  * GNU Lesser General Public License for more details.
00023  * 
00024  * You should have received a copy of the GNU Lesser General Public License
00025  * along with this file.  If not, see <http://www.gnu.org/licenses/>.
00026  */
00027 
00028 #include "but_distance_circular_indicator.h"
00029 
00030 #include <srs_ui_but/topics_list.h>
00031 
00032 using namespace std;
00033 
00034 namespace srs_ui_but
00035 {
00036 CButDistanceCircularIndicator::CButDistanceCircularIndicator(const string & name, rviz::VisualizationManager * manager) :
00037     Display(name, manager)
00038 {
00039   // Default properties
00040   color_.r_ = 0.0;
00041   color_.g_ = 0.0;
00042   color_.b_ = 1.0;
00043   radius_ = 1;
00044   accuracy_ = 35;
00045   thickness_ = 0.5;
00046   robot_link_ = DEFAULT_GRIPPER_LINK;
00047   levels_ = 3;
00048   alpha_ = 1.0;
00049   show_distance_ = true;
00050   orientation_.x = 0.0;
00051   orientation_.y = 0.0;
00052   orientation_.z = 0.0;
00053 
00054   // Get scene node
00055   m_sceneNode_ = scene_manager_->getRootSceneNode()->createChildSceneNode();
00056   m_sceneNode_flipped_ = scene_manager_->getRootSceneNode()->createChildSceneNode();
00057 
00058   // Create basic geometry
00059   createGeometry();
00060 }
00061 
00062 CButDistanceCircularIndicator::~CButDistanceCircularIndicator()
00063 {
00064   destroyGeometry();
00065 }
00066 
00067 bool CButDistanceCircularIndicator::createGeometry()
00068 {
00069 
00070   // Create manual object
00071   static int line_count = 0;
00072   stringstream ss;
00073   ss << "robot_radar_" << line_count++;
00074 
00075   // Set material
00076   material_ = Ogre::MaterialManager::getSingleton().create(ss.str(),
00077                                                            Ogre::ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME);
00078   material_->setCullingMode(Ogre::CULL_NONE);
00079   material_->getTechnique(0)->setLightingEnabled(true);
00080   material_->getTechnique(0)->setAmbient(color_.r_, color_.g_, color_.b_);
00081   material_->getTechnique(0)->setDiffuse(color_.r_, color_.g_, color_.b_, alpha_);
00082   material_->setSceneBlending(Ogre::SBT_TRANSPARENT_ALPHA);
00083 
00084   circle_manual_object_ = scene_manager_->createManualObject(ss.str());
00085 
00086   // Set it to dynamic for further update
00087   circle_manual_object_->setDynamic(true);
00088 
00089   // Create basic geometry
00090   circle_manual_object_->begin(material_->getName(), Ogre::RenderOperation::OT_TRIANGLE_LIST);
00091 
00092   circle_manual_object_->end();
00093 
00094   // Attach it to the scene
00095   m_sceneNode_->attachObject(circle_manual_object_);
00096 
00097   return true;
00098 }
00099 
00100 void CButDistanceCircularIndicator::destroyGeometry()
00101 {
00102   // Destroy manual object
00103   if (circle_manual_object_ != 0)
00104   {
00105     scene_manager_->destroyManualObject(circle_manual_object_);
00106     circle_manual_object_ = NULL;
00107   }
00108   // Destroy scene
00109   if (m_sceneNode_ != 0)
00110     scene_manager_->destroySceneNode(m_sceneNode_->getName());
00111   if (m_sceneNode_flipped_ != 0)
00112     scene_manager_->destroySceneNode(m_sceneNode_flipped_->getName());
00113 
00114 }
00115 
00116 void CButDistanceCircularIndicator::onEnable()
00117 {
00118   m_sceneNode_->setVisible(true);
00119   m_sceneNode_flipped_->setVisible(true);
00120 }
00121 
00122 void CButDistanceCircularIndicator::onDisable()
00123 {
00124   m_sceneNode_->setVisible(false);
00125   m_sceneNode_flipped_->setVisible(false);
00126 }
00127 
00128 void CButDistanceCircularIndicator::createProperties()
00129 {
00130 
00131   m_property_link_ = property_manager_->createProperty<rviz::TFFrameProperty>(
00132       "Link", property_prefix_, boost::bind(&CButDistanceCircularIndicator::getLinkString, this),
00133       boost::bind(&CButDistanceCircularIndicator::setLinkString, this, _1), parent_category_, this);
00134   setPropertyHelpText(m_property_link_, "Link from which to show radar");
00135 
00136   m_property_orientation_ = property_manager_->createProperty<rviz::Vector3Property>(
00137       "Orientation", property_prefix_, boost::bind(&CButDistanceCircularIndicator::getOrientation, this),
00138       boost::bind(&CButDistanceCircularIndicator::setOrientation, this, _1), parent_category_, this);
00139   setPropertyHelpText(m_property_orientation_, "Radar orientation.");
00140 
00141   m_property_color_ = property_manager_->createProperty<rviz::ColorProperty>(
00142       "Color", property_prefix_, boost::bind(&CButDistanceCircularIndicator::getColor, this),
00143       boost::bind(&CButDistanceCircularIndicator::setColor, this, _1), parent_category_, this);
00144   setPropertyHelpText(m_property_color_, "Radar color.");
00145 
00146   m_property_alpha_ = property_manager_->createProperty<rviz::FloatProperty>(
00147       "Alpha", property_prefix_, boost::bind(&CButDistanceCircularIndicator::getAlpha, this),
00148       boost::bind(&CButDistanceCircularIndicator::setAlpha, this, _1), parent_category_, this);
00149   setPropertyHelpText(m_property_alpha_, "Alpha channel.");
00150 
00151   m_property_levels_ = property_manager_->createProperty<rviz::IntProperty>(
00152       "Levels", property_prefix_, boost::bind(&CButDistanceCircularIndicator::getLevels, this),
00153       boost::bind(&CButDistanceCircularIndicator::setLevels, this, _1), parent_category_, this);
00154   setPropertyHelpText(m_property_levels_, "Number of levels.");
00155 
00156   m_property_radius_ = property_manager_->createProperty<rviz::FloatProperty>(
00157       "Radius", property_prefix_, boost::bind(&CButDistanceCircularIndicator::getRadius, this),
00158       boost::bind(&CButDistanceCircularIndicator::setRadius, this, _1), parent_category_, this);
00159   setPropertyHelpText(m_property_radius_, "Radar radius (cm).");
00160 
00161   m_property_thickness_ = property_manager_->createProperty<rviz::FloatProperty>(
00162       "Thickness", property_prefix_, boost::bind(&CButDistanceCircularIndicator::getThickness, this),
00163       boost::bind(&CButDistanceCircularIndicator::setThickness, this, _1), parent_category_, this);
00164   setPropertyHelpText(m_property_thickness_, "Circle thickness (cm).");
00165 
00166   m_property_show_distance_ = property_manager_->createProperty<rviz::BoolProperty>(
00167       "Show distance", property_prefix_, boost::bind(&CButDistanceCircularIndicator::getShowDistance, this),
00168       boost::bind(&CButDistanceCircularIndicator::setShowDistance, this, _1), parent_category_, this);
00169   setPropertyHelpText(m_property_show_distance_, "Draw text with distance into the scene.");
00170 
00171 }
00172 
00173 void CButDistanceCircularIndicator::update(float wall_dt, float ros_dt)
00174 {
00175   Ogre::Vector3 position;
00176   Ogre::Quaternion orientation;
00177   Ogre::Quaternion flip_x(Ogre::Degree(180), Ogre::Vector3::UNIT_X);
00178   Ogre::Quaternion flip_z(Ogre::Degree(180), Ogre::Vector3::UNIT_Z);
00179 
00180   Ogre::Quaternion rotate_x(Ogre::Degree(orientation_.x), Ogre::Vector3::UNIT_X);
00181   Ogre::Quaternion rotate_y(Ogre::Degree(orientation_.y), Ogre::Vector3::UNIT_Y);
00182   Ogre::Quaternion rotate_z(Ogre::Degree(orientation_.z), Ogre::Vector3::UNIT_Z);
00183 
00184   // Transform scene node to link position
00185   if (vis_manager_->getFrameManager()->getTransform(robot_link_, ros::Time(), position, orientation))
00186   {
00187     m_sceneNode_->setPosition(position);
00188     m_sceneNode_->setOrientation(orientation);
00189     m_sceneNode_->rotate(rotate_x);
00190     m_sceneNode_->rotate(rotate_y);
00191     m_sceneNode_->rotate(rotate_z);
00192     m_sceneNode_->detachAllObjects();
00193 
00194     m_sceneNode_flipped_->setPosition(position);
00195     m_sceneNode_flipped_->setOrientation(orientation);
00196     m_sceneNode_flipped_->rotate(rotate_x);
00197     m_sceneNode_flipped_->rotate(rotate_y);
00198     m_sceneNode_flipped_->rotate(rotate_z);
00199     m_sceneNode_flipped_->rotate(flip_x);
00200     m_sceneNode_flipped_->rotate(flip_z);
00201     m_sceneNode_flipped_->detachAllObjects();
00202 
00203     circle_manual_object_->clear();
00204 
00205     circle_manual_object_->begin(material_->getName(), Ogre::RenderOperation::OT_TRIANGLE_LIST);
00206     unsigned point_index = 0;
00207     float thickness = thickness_ / 100;
00208 
00209     for (unsigned int level = 1; level <= levels_; level++)
00210     {
00211       float radius = radius_ * level / 100;
00212       for (float theta = 0; theta <= 2 * M_PI; theta += M_PI / accuracy_)
00213       {
00214         circle_manual_object_->position(radius * cos(theta), radius * sin(theta), 0);
00215         circle_manual_object_->position(radius * cos(theta - M_PI / accuracy_), radius * sin(theta - M_PI / accuracy_),
00216                                         0);
00217         circle_manual_object_->position((radius - thickness) * cos(theta - M_PI / accuracy_),
00218                                         (radius - thickness) * sin(theta - M_PI / accuracy_), 0);
00219         circle_manual_object_->position((radius - thickness) * cos(theta), (radius - thickness) * sin(theta), 0);
00220         circle_manual_object_->quad(point_index, point_index + 1, point_index + 2, point_index + 3);
00221         point_index += 4;
00222       }
00223     }
00224     circle_manual_object_->end();
00225     m_sceneNode_->attachObject(circle_manual_object_);
00226 
00227     if (show_distance_)
00228     {
00229       float char_height = radius_ / 300;
00230 
00231       if (char_height > 0.1)
00232         char_height = 0.1;
00233 
00234       for (unsigned int level = 1; level <= levels_; level++)
00235       {
00236         float radius = radius_ * level;
00237         ostringstream radius_str;
00238         radius_str << setprecision(2) << fixed << fabs(radius) << "cm";
00239         Ogre::Vector3 trans;
00240         trans.x = -char_height / 2 * radius_str.str().length();
00241         trans.y = radius / 100 - char_height / 2;
00242         trans.z = 0.0f;
00243 
00244         ogre_tools::StaticText* text = new ogre_tools::StaticText(radius_str.str());
00245         text->setCharacterHeight(char_height);
00246         text->setLocalTranslation(trans);
00247         text->setColor(Ogre::ColourValue(color_.r_, color_.g_, color_.b_, alpha_));
00248         m_sceneNode_->attachObject(text);
00249 
00250         ogre_tools::StaticText* text_flipped = new ogre_tools::StaticText(radius_str.str());
00251         text_flipped->setCharacterHeight(char_height);
00252         text_flipped->setLocalTranslation(trans);
00253         text_flipped->setColor(Ogre::ColourValue(color_.r_, color_.g_, color_.b_, alpha_));
00254         m_sceneNode_flipped_->attachObject(text_flipped);
00255       }
00256     }
00257     setStatus(rviz::status_levels::Ok, "Status", "OK");
00258   }
00259   else
00260     setStatus(rviz::status_levels::Error, "Status", "Transformation error.");
00261 
00262 }
00263 }


srs_ui_but
Author(s): Vit Stancl (stancl@fit.vutbr.cz), Michal Spanel (spanel@fit.vutbr.cz), Tomas Lokaj
autogenerated on Mon Oct 6 2014 08:49:30