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 #include "qt_ogre_render_window.h"
00030 #include "orthographic.h"
00031 #include "render_system.h"
00032
00033 #include <OgreRoot.h>
00034 #include <OgreViewport.h>
00035 #include <OgreCamera.h>
00036 #include <OgreRenderWindow.h>
00037 #include <OgreStringConverter.h>
00038 #include <OgreGpuProgramManager.h>
00039 #include <OgreRenderTargetListener.h>
00040
00041 #include <ros/console.h>
00042 #include <ros/assert.h>
00043
00044 #if OGRE_PLATFORM == OGRE_PLATFORM_LINUX
00045 #include <stdlib.h>
00046 #endif
00047
00048 namespace rviz
00049 {
00050
00051 QtOgreRenderWindow::QtOgreRenderWindow( QWidget* parent )
00052 : RenderWidget( RenderSystem::get(), parent )
00053 , viewport_( 0 )
00054 , ogre_root_( RenderSystem::get()->root() )
00055 , ortho_scale_( 1.0f )
00056 , auto_render_( true )
00057 , camera_( 0 )
00058 , overlays_enabled_( true )
00059 , background_color_( Ogre::ColourValue::Black )
00060 , stereo_enabled_( false )
00061 , rendering_stereo_( false )
00062 , left_camera_( 0 )
00063 , right_camera_( 0 )
00064 , right_viewport_( 0 )
00065 {
00066 render_window_->setVisible(true);
00067 render_window_->setAutoUpdated(true);
00068
00069 viewport_ = render_window_->addViewport( camera_ );
00070 viewport_->setOverlaysEnabled( overlays_enabled_ );
00071 viewport_->setBackgroundColour( background_color_ );
00072
00073 #if OGRE_STEREO_ENABLE
00074 viewport_->setDrawBuffer(Ogre::CBT_BACK);
00075 #endif
00076 enableStereo(true);
00077
00078 setCameraAspectRatio();
00079 }
00080
00081 QtOgreRenderWindow::~QtOgreRenderWindow()
00082 {
00083 enableStereo(false);
00084 }
00085
00086
00087 bool QtOgreRenderWindow::enableStereo (bool enable)
00088 {
00089 bool was_enabled = stereo_enabled_;
00090 stereo_enabled_ = enable;
00091 setupStereo();
00092 return was_enabled;
00093 }
00094
00095 void QtOgreRenderWindow::setupStereo()
00096 {
00097 bool render_stereo = stereo_enabled_ && RenderSystem::get()->isStereoSupported();
00098
00099 if (render_stereo == rendering_stereo_)
00100 return;
00101
00102 rendering_stereo_ = render_stereo;
00103
00104 if (rendering_stereo_)
00105 {
00106 right_viewport_ = render_window_->addViewport( NULL, 1 );
00107 #if OGRE_STEREO_ENABLE
00108 right_viewport_->setDrawBuffer(Ogre::CBT_BACK_RIGHT);
00109 viewport_->setDrawBuffer(Ogre::CBT_BACK_LEFT);
00110 #endif
00111
00112 setOverlaysEnabled(overlays_enabled_);
00113 setBackgroundColor(background_color_);
00114 if (camera_)
00115 setCamera(camera_);
00116
00117
00118 render_window_->addListener(this);
00119 }
00120 else
00121 {
00122 render_window_->removeListener(this);
00123 render_window_->removeViewport(1);
00124 right_viewport_ = NULL;
00125
00126 #if OGRE_STEREO_ENABLE
00127 viewport_->setDrawBuffer(Ogre::CBT_BACK);
00128 #endif
00129
00130 if (left_camera_)
00131 left_camera_->getSceneManager()->destroyCamera( left_camera_ );
00132 left_camera_ = NULL;
00133 if (right_camera_)
00134 right_camera_->getSceneManager()->destroyCamera( right_camera_ );
00135 right_camera_ = NULL;
00136 }
00137
00138 }
00139
00140
00141 void QtOgreRenderWindow::preViewportUpdate(
00142 const Ogre::RenderTargetViewportEvent& evt)
00143 {
00144 Ogre::Viewport* viewport = evt.source;
00145
00146 const Ogre::Vector2& offset = camera_->getFrustumOffset();
00147 const Ogre::Vector3 pos = camera_->getPosition();
00148 const Ogre::Vector3 right = camera_->getRight();
00149 const Ogre::Vector3 up = camera_->getUp();
00150
00151 if (viewport == right_viewport_)
00152 {
00153 if (camera_->getProjectionType() != Ogre::PT_PERSPECTIVE || !right_camera_)
00154 {
00155 viewport->setCamera( camera_ );
00156 return;
00157 }
00158
00159 Ogre::Vector3 newpos = pos
00160 + right * offset.x
00161 + up * offset.y;
00162
00163 right_camera_->synchroniseBaseSettingsWith(camera_);
00164 right_camera_->setFrustumOffset(-offset);
00165 right_camera_->setPosition(newpos);
00166 viewport->setCamera(right_camera_);
00167 }
00168 else if (viewport == viewport_)
00169 {
00170 if (camera_->getProjectionType() != Ogre::PT_PERSPECTIVE || !left_camera_)
00171 {
00172 viewport->setCamera( camera_ );
00173 return;
00174 }
00175
00176 Ogre::Vector3 newpos = pos
00177 - right * offset.x
00178 - up * offset.y;
00179
00180 left_camera_->synchroniseBaseSettingsWith(camera_);
00181 left_camera_->setFrustumOffset(offset);
00182 left_camera_->setPosition(newpos);
00183 viewport->setCamera(left_camera_);
00184 }
00185 else
00186 {
00187 ROS_WARN("Begin rendering to unknown viewport.");
00188 }
00189 }
00190
00191 void QtOgreRenderWindow::postViewportUpdate(
00192 const Ogre::RenderTargetViewportEvent& evt)
00193 {
00194 Ogre::Viewport* viewport = evt.source;
00195
00196 if (viewport == right_viewport_)
00197 {
00198
00199 }
00200 else if (viewport == viewport_)
00201 {
00202 viewport->setCamera(camera_);
00203 }
00204 else
00205 {
00206 ROS_WARN("End rendering to unknown viewport.");
00207 }
00208
00209 if(!right_camera_->isCustomProjectionMatrixEnabled()) {
00210 right_camera_->synchroniseBaseSettingsWith(camera_);
00211 right_camera_->setFrustumOffset(-camera_->getFrustumOffset());
00212 }
00213 right_viewport_->setCamera(right_camera_);
00214 }
00215
00216 Ogre::Viewport* QtOgreRenderWindow::getViewport () const
00217 {
00218 return viewport_;
00219 }
00220
00221 void QtOgreRenderWindow::setCamera( Ogre::Camera* camera )
00222 {
00223 if (camera)
00224 {
00225 camera_ = camera;
00226 viewport_->setCamera( camera );
00227
00228 setCameraAspectRatio();
00229
00230 if (camera_ && rendering_stereo_ && !left_camera_)
00231 {
00232 left_camera_ = camera_->getSceneManager()->createCamera(camera_->getName() + "-left");
00233 }
00234 if (camera_ && rendering_stereo_ && !right_camera_)
00235 {
00236 right_camera_ = camera_->getSceneManager()->createCamera(camera_->getName() + "-right");
00237 }
00238
00239 update();
00240 }
00241 }
00242
00243 void QtOgreRenderWindow::setOverlaysEnabled( bool overlays_enabled )
00244 {
00245 overlays_enabled_ = overlays_enabled;
00246 viewport_->setOverlaysEnabled( overlays_enabled );
00247 if (right_viewport_)
00248 {
00249 right_viewport_->setOverlaysEnabled( overlays_enabled );
00250 }
00251 }
00252
00253 void QtOgreRenderWindow::setBackgroundColor( Ogre::ColourValue background_color )
00254 {
00255 background_color_ = background_color;
00256 viewport_->setBackgroundColour( background_color );
00257 if (right_viewport_)
00258 {
00259 right_viewport_->setBackgroundColour( background_color );
00260 }
00261 }
00262
00263 void QtOgreRenderWindow::setCameraAspectRatio()
00264 {
00265 if ( camera_ )
00266 {
00267 camera_->setAspectRatio( Ogre::Real( width() ) / Ogre::Real( height() ) );
00268 if (right_camera_ ) {
00269 right_camera_->setAspectRatio( Ogre::Real( width() ) / Ogre::Real( height() ) );
00270 }
00271
00272 if ( camera_->getProjectionType() == Ogre::PT_ORTHOGRAPHIC )
00273 {
00274 Ogre::Matrix4 proj;
00275 buildScaledOrthoMatrix( proj,
00276 -width() / ortho_scale_ / 2, width() / ortho_scale_ / 2,
00277 -height() / ortho_scale_ / 2, height() / ortho_scale_ / 2,
00278 camera_->getNearClipDistance(), camera_->getFarClipDistance() );
00279 camera_->setCustomProjectionMatrix(true, proj);
00280 }
00281 }
00282 }
00283
00284 void QtOgreRenderWindow::setOrthoScale( float scale )
00285 {
00286 ortho_scale_ = scale;
00287
00288 setCameraAspectRatio();
00289 }
00290
00291 void QtOgreRenderWindow::setPreRenderCallback( boost::function<void ()> func )
00292 {
00293 pre_render_callback_ = func;
00294 }
00295
00296 void QtOgreRenderWindow::setPostRenderCallback( boost::function<void ()> func )
00297 {
00298 post_render_callback_ = func;
00299 }
00300
00301
00302 void QtOgreRenderWindow::paintEvent( QPaintEvent* e )
00303 {
00304 if( auto_render_ && render_window_ )
00305 {
00306 if( pre_render_callback_ )
00307 {
00308 pre_render_callback_();
00309 }
00310
00311 if( ogre_root_->_fireFrameStarted() )
00312 {
00313 #if (OGRE_VERSION_MAJOR >= 1 && OGRE_VERSION_MINOR >= 6)
00314 ogre_root_->_fireFrameRenderingQueued();
00315 #endif
00316
00317 render_window_->update();
00318
00319 ogre_root_->_fireFrameEnded();
00320 }
00321
00322 if ( post_render_callback_ )
00323 {
00324 post_render_callback_();
00325 }
00326 }
00327 }
00328
00329
00330 void QtOgreRenderWindow::resizeEvent( QResizeEvent* event )
00331 {
00332 RenderWidget::resizeEvent( event );
00333
00334 if( render_window_ )
00335 {
00336 setCameraAspectRatio();
00337
00338 if( auto_render_ )
00339 {
00340 update();
00341 }
00342 }
00343 }
00344
00345 }