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 #ifndef GAZEBO_ROS_VIDEO_H
00028 #define GAZEBO_ROS_VIDEO_H
00029
00030 #include <ros/ros.h>
00031 #include <opencv/cv.h>
00032 #include <cv_bridge/cv_bridge.h>
00033 #include <image_transport/image_transport.h>
00034 #include <boost/thread/mutex.hpp>
00035 #include <sensor_msgs/Image.h>
00036
00037 #include "rendering/rendering.hh"
00038 #include "transport/TransportTypes.hh"
00039 #include "common/Time.hh"
00040 #include "common/Plugin.hh"
00041 #include "common/Events.hh"
00042
00043 namespace gazebo {
00044
00045 class VideoVisual : public rendering::Visual {
00046 public:
00050 VideoVisual(const std::string &_name, rendering::VisualPtr _parent,
00051 int h, int w) :
00052 rendering::Visual(_name, _parent), height(h), width(w) {
00053
00054 this->texture = Ogre::TextureManager::getSingleton().createManual(
00055 _name + "__VideoTexture__",
00056 Ogre::ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME,
00057 Ogre::TEX_TYPE_2D,
00058 this->width, this->height,
00059 0,
00060 Ogre::PF_BYTE_BGR,
00061 Ogre::TU_DYNAMIC_WRITE_ONLY_DISCARDABLE);
00062
00063 Ogre::MaterialPtr material =
00064 Ogre::MaterialManager::getSingleton().create(
00065 _name + "__VideoMaterial__", "General");
00066 material->getTechnique(0)->getPass(0)->createTextureUnitState(
00067 _name + "__VideoTexture__");
00068 material->setReceiveShadows(false);
00069
00070 double factor = 1.0;
00071
00072 Ogre::ManualObject mo(_name + "__VideoObject__");
00073 mo.begin(_name + "__VideoMaterial__",
00074 Ogre::RenderOperation::OT_TRIANGLE_LIST);
00075
00076 mo.position(-factor / 2, factor / 2, 0.51);
00077 mo.textureCoord(0, 0);
00078
00079 mo.position(factor / 2, factor / 2, 0.51);
00080 mo.textureCoord(1, 0);
00081
00082 mo.position(factor / 2, -factor / 2, 0.51);
00083 mo.textureCoord(1, 1);
00084
00085 mo.position(-factor / 2, -factor / 2, 0.51);
00086 mo.textureCoord(0, 1);
00087
00088 mo.triangle(0, 3, 2);
00089 mo.triangle(2, 1, 0);
00090 mo.end();
00091
00092 mo.convertToMesh(_name + "__VideoMesh__");
00093
00094 Ogre::MovableObject *obj = (Ogre::MovableObject*)
00095 this->sceneNode->getCreator()->createEntity(
00096 _name + "__VideoEntity__",
00097 _name + "__VideoMesh__");
00098 obj->setCastShadows(false);
00099 this->AttachObject(obj);
00100
00101 }
00102
00104 virtual ~VideoVisual() {}
00105
00107 void render(const cv::Mat& image) {
00108
00109
00110 Ogre::HardwarePixelBufferSharedPtr pixelBuffer =
00111 this->texture->getBuffer();
00112
00113
00114 pixelBuffer->lock(Ogre::HardwareBuffer::HBL_DISCARD);
00115 const Ogre::PixelBox& pixelBox = pixelBuffer->getCurrentLock();
00116 uint8_t* pDest = static_cast<uint8_t*>(pixelBox.data);
00117
00118 bool unusedAlpha = Ogre::PixelUtil::getNumElemBytes(
00119 this->texture->getFormat()) > 3 ? true : false;
00120
00121
00122
00123 if (!unusedAlpha) {
00124 memcpy(pDest, image.data, this->height*this->width*3);
00125 } else {
00126 int index;
00127 for (int j = 0; j < this->height; ++j) {
00128 for (int i = 0; i < this->width; ++i) {
00129 index = j*(this->width*3) + (i*3);
00130 *pDest++ = image.data[index + 0];
00131 *pDest++ = image.data[index + 1];
00132 *pDest++ = image.data[index + 2];
00133 *pDest++ = 255;
00134 }
00135 }
00136 }
00137
00138
00139 pixelBuffer->unlock();
00140 }
00141
00142 private:
00143
00145 Ogre::TexturePtr texture;
00146
00148 int height,width;
00149 };
00150
00151 class GazeboRosVideo : public VisualPlugin {
00152 public:
00153
00155 GazeboRosVideo();
00156
00158 virtual ~GazeboRosVideo();
00159
00161 void Load(rendering::VisualPtr _parent, sdf::ElementPtr _sdf );
00162
00163 void processImage(const sensor_msgs::ImageConstPtr &msg);
00164
00165 protected:
00166
00168 virtual void UpdateChild();
00169
00170
00171 rendering::VisualPtr model;
00172
00173 event::ConnectionPtr updateConnection;
00174
00175 boost::shared_ptr<VideoVisual> video_visual_;
00176
00177 cv_bridge::CvImagePtr image_;
00178 boost::mutex m_image_;
00179 bool new_image_available_;
00180
00181
00182 boost::shared_ptr<ros::NodeHandle> rosnode_;
00183 boost::shared_ptr<image_transport::ImageTransport> it_;
00184 image_transport::Subscriber camera_subscriber_;
00185 int height;
00186 int width;
00187 std::string modelNamespace;
00188 std::string topicName;
00189
00190 void QueueThread();
00191 boost::thread callback_queue_thread_;
00192
00193 };
00194
00195 }
00196
00197 #endif
00198