mirror of
				https://github.com/OpenMW/openmw.git
				synced 2025-10-31 20:26:43 +00:00 
			
		
		
		
	OpenCS: Use a CompositeViewer with multiple views instead of multiple viewers
Fixes the rendering glitches, turns out that multiple osgViewers were never an intended use case.
This commit is contained in:
		
							parent
							
								
									5a582e7eb7
								
							
						
					
					
						commit
						d6dea31b88
					
				
					 3 changed files with 74 additions and 35 deletions
				
			
		|  | @ -15,7 +15,7 @@ CSVRender::PreviewWidget::PreviewWidget (const VFS::Manager* vfs, CSMWorld::Data | |||
| { | ||||
|     //setNavigation (&mOrbit);
 | ||||
| 
 | ||||
|     setCameraManipulator(new osgGA::TrackballManipulator); | ||||
|     mView->setCameraManipulator(new osgGA::TrackballManipulator); | ||||
| 
 | ||||
|     QAbstractItemModel *referenceables = | ||||
|         mData.getTableModel (CSMWorld::UniversalId::Type_Referenceables); | ||||
|  |  | |||
|  | @ -14,7 +14,7 @@ | |||
| 
 | ||||
| #include <osgQt/GraphicsWindowQt> | ||||
| #include <osg/GraphicsContext> | ||||
| 
 | ||||
| #include <osgViewer/CompositeViewer> | ||||
| #include <osgViewer/ViewerEventHandlers> | ||||
| 
 | ||||
| namespace CSVRender | ||||
|  | @ -25,20 +25,11 @@ SceneWidget::SceneWidget(QWidget *parent, Qt::WindowFlags f) | |||
|     , mRootNode(0) | ||||
| { | ||||
| 
 | ||||
| #if QT_VERSION >= 0x050000 | ||||
|     // Qt5 is currently crashing and reporting "Cannot make QOpenGLContext current in a different thread" when the viewer is run multi-threaded, this is regression from Qt4
 | ||||
|     osgViewer::ViewerBase::ThreadingModel threadingModel = osgViewer::ViewerBase::SingleThreaded; | ||||
| #else | ||||
|     osgViewer::ViewerBase::ThreadingModel threadingModel = osgViewer::ViewerBase::CullDrawThreadPerContext; | ||||
| #endif | ||||
| 
 | ||||
|     setThreadingModel(threadingModel); | ||||
| 
 | ||||
|     // disable the default setting of viewer.done() by pressing Escape.
 | ||||
|     setKeyEventSetsDone(0); | ||||
|     osgViewer::CompositeViewer& viewer = CompositeViewer::get(); | ||||
| 
 | ||||
|     osg::DisplaySettings* ds = osg::DisplaySettings::instance().get(); | ||||
|     //ds->setNumMultiSamples(8);
 | ||||
| 
 | ||||
|     osg::ref_ptr<osg::GraphicsContext::Traits> traits = new osg::GraphicsContext::Traits; | ||||
|     traits->windowName = ""; | ||||
|     traits->windowDecoration = true; | ||||
|  | @ -54,43 +45,72 @@ SceneWidget::SceneWidget(QWidget *parent, Qt::WindowFlags f) | |||
|     // Doesn't make much sense as we're running on demand updates, and there seems to be a bug with the refresh rate when running multiple QGLWidgets
 | ||||
|     traits->vsync = false; | ||||
| 
 | ||||
|     osgQt::GraphicsWindowQt* window = new osgQt::GraphicsWindowQt(traits.get()); | ||||
|     mView = new osgViewer::View; | ||||
| 
 | ||||
|     osg::ref_ptr<osgQt::GraphicsWindowQt> window = new osgQt::GraphicsWindowQt(traits.get()); | ||||
|     QLayout* layout = new QHBoxLayout(this); | ||||
|     layout->addWidget(window->getGLWidget()); | ||||
|     setLayout(layout); | ||||
| 
 | ||||
|     getCamera()->setGraphicsContext(window); | ||||
| 
 | ||||
|     getCamera()->setClearColor( osg::Vec4(0.2, 0.2, 0.6, 1.0) ); | ||||
|     getCamera()->setViewport( new osg::Viewport(0, 0, traits->width, traits->height) ); | ||||
|     getCamera()->setProjectionMatrixAsPerspective(30.0f, static_cast<double>(traits->width)/static_cast<double>(traits->height), 1.0f, 10000.0f ); | ||||
|     mView->getCamera()->setGraphicsContext(window); | ||||
|     mView->getCamera()->setClearColor( osg::Vec4(0.2, 0.2, 0.6, 1.0) ); | ||||
|     mView->getCamera()->setViewport( new osg::Viewport(0, 0, traits->width, traits->height) ); | ||||
|     mView->getCamera()->setProjectionMatrixAsPerspective(30.0f, static_cast<double>(traits->width)/static_cast<double>(traits->height), 1.0f, 10000.0f ); | ||||
| 
 | ||||
|     mRootNode = new osg::Group; | ||||
|     setSceneData(mRootNode); | ||||
|     mView->setSceneData(mRootNode); | ||||
| 
 | ||||
|     // Press S to reveal profiling stats
 | ||||
|     addEventHandler(new osgViewer::StatsHandler); | ||||
|     mView->addEventHandler(new osgViewer::StatsHandler); | ||||
| 
 | ||||
|     mView->getCamera()->setCullMask(~(0x1)); | ||||
| 
 | ||||
|     viewer.addView(mView); | ||||
|     viewer.setDone(false); | ||||
|     viewer.realize(); | ||||
| } | ||||
| 
 | ||||
| SceneWidget::~SceneWidget() | ||||
| { | ||||
|     CompositeViewer::get().removeView(mView); | ||||
| } | ||||
| 
 | ||||
| void SceneWidget::flagAsModified() | ||||
| { | ||||
|     mView->requestRedraw(); | ||||
| } | ||||
| 
 | ||||
| CompositeViewer::CompositeViewer() | ||||
| { | ||||
| #if QT_VERSION >= 0x050000 | ||||
|     // Qt5 is currently crashing and reporting "Cannot make QOpenGLContext current in a different thread" when the viewer is run multi-threaded, this is regression from Qt4
 | ||||
|     osgViewer::ViewerBase::ThreadingModel threadingModel = osgViewer::ViewerBase::SingleThreaded; | ||||
| #else | ||||
|     osgViewer::ViewerBase::ThreadingModel threadingModel = osgViewer::ViewerBase::CullDrawThreadPerContext; | ||||
| #endif | ||||
| 
 | ||||
|     setThreadingModel(threadingModel); | ||||
| 
 | ||||
|     // disable the default setting of viewer.done() by pressing Escape.
 | ||||
|     setKeyEventSetsDone(0); | ||||
| 
 | ||||
|     // Only render when the camera position changed, or content flagged dirty
 | ||||
|     //setRunFrameScheme(osgViewer::ViewerBase::ON_DEMAND);
 | ||||
|     setRunFrameScheme(osgViewer::ViewerBase::CONTINUOUS); | ||||
| 
 | ||||
|     getCamera()->setCullMask(~(0x1)); | ||||
| 
 | ||||
|     connect( &mTimer, SIGNAL(timeout()), this, SLOT(update()) ); | ||||
|     mTimer.start( 10 ); | ||||
| 
 | ||||
|     realize(); | ||||
| } | ||||
| 
 | ||||
| void SceneWidget::paintEvent(QPaintEvent *event) | ||||
| CompositeViewer &CompositeViewer::get() | ||||
| { | ||||
|     static CompositeViewer sThis; | ||||
|     return sThis; | ||||
| } | ||||
| 
 | ||||
| void CompositeViewer::update() | ||||
| { | ||||
|     frame(); | ||||
| } | ||||
| 
 | ||||
| void SceneWidget::flagAsModified() | ||||
| { | ||||
|     _requestRedraw = true; | ||||
| } | ||||
| 
 | ||||
| } | ||||
|  |  | |||
|  | @ -8,7 +8,8 @@ | |||
| #include "lightingnight.hpp" | ||||
| #include "lightingbright.hpp" | ||||
| 
 | ||||
| #include <osgViewer/Viewer> | ||||
| #include <osgViewer/View> | ||||
| #include <osgViewer/CompositeViewer> | ||||
| 
 | ||||
| namespace osg | ||||
| { | ||||
|  | @ -26,24 +27,42 @@ namespace CSVRender | |||
|     class Navigation; | ||||
|     class Lighting; | ||||
| 
 | ||||
|     class SceneWidget : public QWidget, public osgViewer::Viewer | ||||
|     class SceneWidget : public QWidget | ||||
|     { | ||||
|         Q_OBJECT | ||||
| 
 | ||||
|     public: | ||||
|         SceneWidget(QWidget* parent = 0, Qt::WindowFlags f = 0); | ||||
| 
 | ||||
|         virtual void paintEvent( QPaintEvent* event ); | ||||
|         ~SceneWidget(); | ||||
| 
 | ||||
|         void flagAsModified(); | ||||
| 
 | ||||
|     protected: | ||||
| 
 | ||||
|         osg::ref_ptr<osgViewer::View> mView; | ||||
| 
 | ||||
|         osg::Group* mRootNode; | ||||
| 
 | ||||
|         QTimer mTimer; | ||||
|     }; | ||||
| 
 | ||||
| 
 | ||||
| 
 | ||||
|     // There are rendering glitches when using multiple Viewer instances, work around using CompositeViewer with multiple views
 | ||||
|     class CompositeViewer : public QObject, public osgViewer::CompositeViewer | ||||
|     { | ||||
|         Q_OBJECT | ||||
|     public: | ||||
|         CompositeViewer(); | ||||
| 
 | ||||
|         static CompositeViewer& get(); | ||||
| 
 | ||||
|         QTimer mTimer; | ||||
| 
 | ||||
|     public slots: | ||||
|         void update(); | ||||
|     }; | ||||
| 
 | ||||
| } | ||||
| 
 | ||||
| #endif | ||||
|  |  | |||
		Loading…
	
		Reference in a new issue