Hi All, On Thu, Nov 20, 2008 at 4:01 PM, Robert Osfield <[EMAIL PROTECTED]> wrote: > I think the best lead would be that perhaps the texture object/display > lists buffer_value containers aren't being resized to fit the new > number of contexts which the app is running single threaded. In > theory addView should be stopping all threads, and then issuing the > Node::resizeGLObejcts() on the scene graph so handling this situation, > but perhaps this isn't happening.
I've looked into the CompositeViewer:::addView()/View::setSceneData()/Viewer::setSceneData() methods and only the Viewer::setSceneData() has a call to resize the GL objects. The actual code looks like: void Viewer::setSceneData(osg::Node* node) { setReferenceTime(0.0); View::setSceneData(node); if (_threadingModel!=SingleThreaded && getSceneData()) { // make sure that existing scene graph objects are allocated with thread safe ref/unref getSceneData()->setThreadSafeRefUnref(true); // update the scene graph so that it has enough GL object buffer memory for the graphics contexts that will be using it. getSceneData()->resizeGLObjectBuffers(osg::DisplaySettings::instance()->getMaxNumberOfGraphicsContexts()); } } My guess is that we need to move the resize/setThreadSafeRefUnref() up into the View::setSceneData() method. The Viewer::setSceneData() method is a viewer so has access to members of ViewerBase that View doesn't have. Another issue is that if we are setting the View up prior to any call to stopThreading as the resize isn't thread safe. As we don't know whether this is the cause of the problem yet, I've modified J-S's osgviewer.cpp to do the resize. Could users who've seen problems try this version out, if this works then we have workaround that end users can apply to existing apps, and we can figure out a solution to fix it permanently in svn/trunk. Robert. Robert.
/* -*-c++-*- OpenSceneGraph - Copyright (C) 1998-2006 Robert Osfield * * This application is open source and may be redistributed and/or modified * freely and without restriction, both in commericial and non commericial applications, * as long as this copyright notice is maintained. * * This application is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. */ #include <osgDB/ReadFile> #include <osgUtil/Optimizer> #include <osg/CoordinateSystemNode> #include <osg/Switch> #include <osgText/Text> #include <osgViewer/CompositeViewer> #include <osgViewer/ViewerEventHandlers> #include <osgGA/TrackballManipulator> #include <osgGA/FlightManipulator> #include <osgGA/DriveManipulator> #include <osgGA/KeySwitchMatrixManipulator> #include <osgGA/StateSetManipulator> #include <osgGA/AnimationPathManipulator> #include <osgGA/TerrainManipulator> #include <iostream> void addEventHandlers(osgViewer::View* view) { // set up the camera manipulators. view->setCameraManipulator( new osgGA::TrackballManipulator() ); // add the state manipulator view->addEventHandler( new osgGA::StateSetManipulator(view->getCamera()->getOrCreateStateSet()) ); // add the thread model handler view->addEventHandler(new osgViewer::ThreadingHandler); // add the window size toggle handler view->addEventHandler(new osgViewer::WindowSizeHandler); // add the stats handler view->addEventHandler(new osgViewer::StatsHandler); // add the record camera path handler view->addEventHandler(new osgViewer::RecordCameraPathHandler); // add the LOD Scale handler view->addEventHandler(new osgViewer::LODScaleHandler); // add the screen capture handler view->addEventHandler(new osgViewer::ScreenCaptureHandler); } class AddViewHandler : public osgGA::GUIEventHandler { public: AddViewHandler(osgViewer::CompositeViewer* viewer, osg::Node* sceneRoot) : _viewer(viewer), _sceneRoot(sceneRoot) {} bool handle(const osgGA::GUIEventAdapter& ea, osgGA::GUIActionAdapter& aa) { if (ea.getEventType() == osgGA::GUIEventAdapter::KEYDOWN && ea.getKey()== 'a') { osgViewer::View* view = new osgViewer::View; view->setUpViewInWindow(50, 50, 800, 600); view->getCamera()->getGraphicsContext()->realize(); view->setSceneData(_sceneRoot.get()); addEventHandlers(view); _viewer->stopThreading(); _viewer->addView(view); osg::notify(osg::NOTICE)<<"osg::DisplaySettings::instance()->getMaxNumberOfGraphicsContexts()="<< osg::DisplaySettings::instance()->getMaxNumberOfGraphicsContexts()<<std::endl; view->getSceneData()->setThreadSafeRefUnref(true); view->getSceneData()->resizeGLObjectBuffers(osg::DisplaySettings::instance()->getMaxNumberOfGraphicsContexts()); _viewer->startThreading(); return true; } return false; } protected: osg::observer_ptr<osgViewer::CompositeViewer> _viewer; osg::ref_ptr<osg::Node> _sceneRoot; }; int main(int argc, char** argv) { // use an ArgumentParser object to manage the program arguments. osg::ArgumentParser arguments(&argc,argv); arguments.getApplicationUsage()->setApplicationName(arguments.getApplicationName()); arguments.getApplicationUsage()->setDescription(arguments.getApplicationName()+" is the standard OpenSceneGraph example which loads and visualises 3d models."); arguments.getApplicationUsage()->setCommandLineUsage(arguments.getApplicationName()+" [options] filename ..."); arguments.getApplicationUsage()->addCommandLineOption("--image <filename>","Load an image and render it on a quad"); arguments.getApplicationUsage()->addCommandLineOption("--dem <filename>","Load an image/DEM and render it on a HeightField"); arguments.getApplicationUsage()->addCommandLineOption("--login <url> <username> <password>","Provide authentication information for http file access."); osgViewer::CompositeViewer viewer(arguments); unsigned int helpType = 0; if ((helpType = arguments.readHelpType())) { arguments.getApplicationUsage()->write(std::cout, helpType); return 1; } // report any errors if they have occurred when parsing the program arguments. if (arguments.errors()) { arguments.writeErrorMessages(std::cout); return 1; } if (arguments.argc()<=1) { arguments.getApplicationUsage()->write(std::cout,osg::ApplicationUsage::COMMAND_LINE_OPTION); return 1; } std::string url, username, password; while(arguments.read("--login",url, username, password)) { if (!osgDB::Registry::instance()->getAuthenticationMap()) { osgDB::Registry::instance()->setAuthenticationMap(new osgDB::AuthenticationMap); osgDB::Registry::instance()->getAuthenticationMap()->addAuthenticationDetails( url, new osgDB::AuthenticationDetails(username, password) ); } } osg::ref_ptr<osgViewer::View> defaultView = new osgViewer::View; viewer.addView(defaultView.get()); addEventHandlers(defaultView.get()); // load the data osg::ref_ptr<osg::Node> loadedModel = osgDB::readNodeFiles(arguments); if (!loadedModel) { std::cout << arguments.getApplicationName() <<": No data loaded" << std::endl; return 1; } // any option left unread are converted into errors to write out later. arguments.reportRemainingOptionsAsUnrecognized(); // report any errors if they have occurred when parsing the program arguments. if (arguments.errors()) { arguments.writeErrorMessages(std::cout); return 1; } // optimize the scene graph, remove redundant nodes and state etc. //osgUtil::Optimizer optimizer; //optimizer.optimize(loadedModel.get()); defaultView->setSceneData( loadedModel.get() ); defaultView->setUpViewInWindow(50, 50, 800, 600); defaultView->addEventHandler(new AddViewHandler(&viewer, loadedModel.get())); viewer.realize(); return viewer.run(); }
_______________________________________________ osg-users mailing list osg-users@lists.openscenegraph.org http://lists.openscenegraph.org/listinfo.cgi/osg-users-openscenegraph.org