Hi Robert,

I came around a long nightly tests, because i have a strange behaviour in
our application w.r.t. to closing. For some models it raise an access
violation error, for some not. now i worked out the problem we have.

It's only raised (0x00005 : access violation) :
- when we append a slave at run time and remove it
- when we have a shader attached (user shader) osg::Programm

the code for adding removing the slave, just a look at the attachement
(GuiEventHandler.cpp)
releaseGLObjects then the error / crash can avoided.

the problem comes from invalid pointer in _pcpList[x] = 0; the unref gets
crashed. because the objects
is still invalid, removed, in other program, or somewhere else or the
initalization, or .. is not correct
but only we renderer slave, and removed the slave (context) otherwise it
works ok.

i don't yet know where the bugs come from. or how we have to fix it. what
does the _pcpList store? shared
objects ?


/adrian



class WebaddonProgram : public osg::Program {
    public:
        virtual void releaseGLObjects(osg::State* state=0) const {

            for( unsigned int i=0; i < _shaderList.size(); ++i )
            {
                if (_shaderList[i].valid())
_shaderList[i]->releaseGLObjects(state);
            }

            // begin hack (FIX)
            // i don't understand why this has to be done by a such hack.
            // but we believe that under full screen the OSG engine does't
right copy
            // the pcp buffer (we are running under single threaded)
            for (unsigned int i(0);i<_pcpList.size();i++ ) {
                _pcpList[i]->ref();
            }
            // end hack


            osg::buffered_value<double> ARR;
            if (!state) {
                // FIX _pcpList.setAllElementsTo(0);
            } else {
                unsigned int contextID = state->getContextID();
                // FIX _pcpList[contextID] = 0; (FULL SCREEN BUG)
            }
        }
};


2009/2/8 Robert Osfield <[email protected]>

> Hi Paul,
>
> The fix is now checked into svn/trunk and OSG-2.8.
>
> Robert.
>
> On Sun, Feb 8, 2009 at 5:35 PM, Robert Osfield <[email protected]>
> wrote:
> > Hi Paul,
> >
> > After a tea break I got back on the horse and tracked the problem down
> > to the osgText::Text::computeGlyphRepresentation() skipping every
> > second repeated \n due to the way the if(){}else{} were set up.  I
> > moved the end of lip skip to prevent this.  Changed file attached.  I
> > can't check the file in right now, I'll try later on.
> >
> > Robert.
> >
> _______________________________________________
> osg-users mailing list
> [email protected]
> http://lists.openscenegraph.org/listinfo.cgi/osg-users-openscenegraph.org
>



-- 
********************************************
Adrian Egli
/* -*-c++-*- Webaddon - Copyright (C) 2005-2008 AS Software GmbH
*
* This library is may be redistributed and/or modified under
* the terms of the AS Software Webaddon License version 0.0 or
* (at your option) any later version. Please ask the AS Software Gmbh
* for the full license. ( [email protected] )
*
*/
#define WEBADDON3D_LIBRARY

//all implementation files has to use the macros include (memory check, and 
much more features)
#include "macros.h"



#include "Webaddon3D/WebaddonGuiEventHandler.h"

#include "Webaddon3D/PluginManager.h"
#include "Webaddon3D/WebaddonMotionModel.h"

#include <osg/Camera>
#include <osgViewer/Viewer>
#include <osg/GraphicsContext>

#ifdef WIN32
        #include <osgViewer/GraphicsWindowWin32>
#endif

#ifdef MEM_LEAK_CHK
#include "WebaddonBase/DbgMemoryImpl.h"
#endif

#include <Windows.h>

WebaddonGuiEventHandler::WebaddonGuiEventHandler(IWebaddon3D* iweb) :
        m_WebaddonMotionModelAbstraction(NULL),
        m_IWebaddon3D(iweb),
        m_isFullScreen(false),
        m_FullScreenDevice(0),
        m_MasterViewer(NULL)
{
        #ifdef WIN32
                m_ParentHWND = NULL;
        #endif

}

WebaddonGuiEventHandler::~WebaddonGuiEventHandler(){
        SAFE_FREE_REF(m_GraphicsContext_FullScreen);
        SAFE_FREE_REF(m_MasterViewer);
}

/** Handle events, return true if handled, false otherwise. */
bool WebaddonGuiEventHandler::handle(const osgGA::GUIEventAdapter& 
ea,osgGA::GUIActionAdapter& aa, osg::Object*, osg::NodeVisitor*) {
 
#if 1
        if ( ea.getEventType() == osgGA::GUIEventAdapter::RELEASE ) {
                std::cout << ea.getX() << " / " << ea.getY() << "[min/max : " 
<< 
                        ea.getXmin() << "," << ea.getXmax() << "/" <<
                        ea.getYmin() << "," << ea.getYmax() << " | normalized : 
" <<
                        ea.getXnormalized() << "/" << ea.getYnormalized() 
                         << "]" << std::endl;
        }
#endif 
        osg::ref_ptr<osgGA::GUIEventAdapter> webaddonEA = new 
osgGA::GUIEventAdapter(ea);
        webaddonEA->setY(ea.getYmax()-ea.getY());

        //
        // forward to the abstract motion model the normalize mouse position
        //
        if ( m_WebaddonMotionModelAbstraction ) {
                
m_WebaddonMotionModelAbstraction->setNormalizedMousePosition(webaddonEA->getXnormalized(),webaddonEA->getYnormalized());
                WebaddonMotionModel* wmm = 
dynamic_cast<WebaddonMotionModel*>(m_WebaddonMotionModelAbstraction);
                if ( wmm ) {
                        if ( ! webaddonEA->getHandled() 
)wmm->handleActivateGotoObjects(*(webaddonEA.get()),aa);
                }
        }



        //
        // if event still handled to nothing further with the event
        //
        if (webaddonEA->getHandled() ) return false;

        //
        // forward keyboard / mouse event to plugins
        //
        PluginManager* pManager = PluginManager::instance();
        if ( pManager ) {
                pManager->handle(ea);
        };

        //
        // notify each (!) registred GUIEventCallback object with the still 
unhandled event, to not care about
        // handled or not yet.
        //
        bool ret(false);

        for ( EventCallbackSet::iterator it = m_EventCallbackSet.begin(); it != 
m_EventCallbackSet.end();) {
                GUIEventCallback* cb = (*it);
                if (cb->handle(*(webaddonEA.get()),aa)) {
                        ret = true;
                }
                ++it;
        }


        if ( ea.getKey() == osgGA::GUIEventAdapter::KEY_Escape ) {
                ea.setHandled(true);
                std::cout << "ESC : will not be handled as OpenSceneGraph close 
event... " << std::endl;

                if ( ea.getEventType() == osgGA::GUIEventAdapter::KEYUP ) {
                        if ( m_isFullScreen ) {
                                closeFullScreen();
                        } else { 
                                openFullScreen(m_FullScreenDevice);
                        }
                        return true;
                }

        }
        return ret;
}

void WebaddonGuiEventHandler::openFullScreen(unsigned int device) {
        LOCK_MUTEX(m_OpenCloseFullScreenMutex);
        m_OpenCloseFullScreen.push_back(true);
        m_FullScreenDevice = device;
        UNLOCK_MUTEX(m_OpenCloseFullScreenMutex);

}

void WebaddonGuiEventHandler::closeFullScreen() {
        LOCK_MUTEX(m_OpenCloseFullScreenMutex);
        m_OpenCloseFullScreen.push_back(false);
        UNLOCK_MUTEX(m_OpenCloseFullScreenMutex);
}


void 
WebaddonGuiEventHandler::setWebaddonMotionModelAbstraction(WebaddonMotionModelAbstraction*
 wmma) {
        m_WebaddonMotionModelAbstraction = wmma;
}

const osg::Camera* WebaddonGuiEventHandler::getFullScreenCamera() const {
        if ( ! m_isFullScreen ) return NULL;
        if ( ! m_MasterViewer ) return NULL;
        FullScreenSlaves::const_iterator it = m_FullScreenSlaves.begin();
        if ( it!=m_FullScreenSlaves.end()){
                osg::View::Slave &slave = m_MasterViewer->getSlave(it->first);
                return slave._camera.get();
        }
        return NULL;
}
 
void WebaddonGuiEventHandler::nextFrame(double delta_time){
        for ( EventCallbackSet::iterator it = m_EventCallbackSet.begin(); it != 
m_EventCallbackSet.end(); ) {
                GUIEventCallback* cb = (*it);
                cb->nextFrame(delta_time);
                ++it;
        }

        /// full screen 
        if ( ! m_MasterViewer) {
                if ( m_IWebaddon3D->getWebaddonRenderer() ) {
                        m_MasterViewer = 
m_IWebaddon3D->getWebaddonRenderer()->getOSGViewer(); 
                }
        }
        if ( m_MasterViewer ) {

                for (FullScreenSlaves::iterator it = 
m_FullScreenSlaves.begin();it!=m_FullScreenSlaves.end();it++){
                        osg::View::Slave &slave = 
m_MasterViewer->getSlave(it->first);
                        
slave._camera->removeChildren(0,slave._camera->getNumChildren());
                        slave._camera->addChild(m_MasterViewer->getSceneData());

                        osg::Matrixd mat;
                        double fovy,rAspect,zNear,zFar;
                        
m_MasterViewer->getCamera()->getProjectionMatrixAsPerspective(fovy,rAspect,zNear,zFar);
                        mat.makePerspective(fovy,rAspect,zNear,zFar);
                        mat.invert(mat);
                        rAspect = ((double)it->second.w/(double)it->second.h);
                        
slave._camera->setProjectionMatrixAsPerspective(fovy,rAspect,zNear,zFar);
                        slave._projectionOffset = mat * 
slave._camera->getProjectionMatrix();
                }
         
                LOCK_MUTEX(m_OpenCloseFullScreenMutex);

                if ( ! m_OpenCloseFullScreen.empty() ) {

                        
//////////////////////////////////////////////////////////////////////////
                        // stop threading               
                        m_MasterViewer->stopThreading();
                        
//////////////////////////////////////////////////////////////////////////
                        bool lastRequest=false;
                        for (OpenCloseFullScreen::iterator it = 
m_OpenCloseFullScreen.begin();it!=m_OpenCloseFullScreen.end();it++){
                                lastRequest = *it;
                        }
                        if ( lastRequest != m_isFullScreen ) { // toggle .... 

                                if ( ! m_isFullScreen) { 

                                        if ( setupSlaves() ) {
                                                for (FullScreenSlaves::iterator 
it = m_FullScreenSlaves.begin();it!=m_FullScreenSlaves.end();it++){
                                                        osg::View::Slave &slave 
= m_MasterViewer->getSlave(it->first);
                                                        
slave._camera->removeChildren(0,slave._camera->getNumChildren());
                                                        
slave._camera->addChild(m_MasterViewer->getSceneData());
                                                }
                                                m_isFullScreen = true;
                                        } else {
                                                m_isFullScreen = false;
                                        }
                                } else {
                                        for (FullScreenSlaves::iterator it = 
m_FullScreenSlaves.begin();it!=m_FullScreenSlaves.end();it++){
                                                osg::View::Slave &slave = 
m_MasterViewer->getSlave(it->first);
                                                
slave._camera->removeChildren(0,slave._camera->getNumChildren());
                                                
m_MasterViewer->removeSlave(it->first);
                                                SAFE_FREE_REF(slave._camera);
                                        }
                                        m_FullScreenSlaves.clear();
                                        
SAFE_FREE_REF(m_GraphicsContext_FullScreen);
                                        m_isFullScreen = false;
                                }

                        }
                        m_OpenCloseFullScreen.clear();

                        
//////////////////////////////////////////////////////////////////////////
                        // update slaves and start threading
                        m_MasterViewer->updateSlaves();
                        m_MasterViewer->startThreading();                
                        
//////////////////////////////////////////////////////////////////////////

                }


                UNLOCK_MUTEX(m_OpenCloseFullScreenMutex);

        } // Master Camera

}

bool WebaddonGuiEventHandler::setupSlaves() {

        m_FullScreenSlaves.clear();

        osg::GraphicsContext::WindowingSystemInterface* wsi = 
osg::GraphicsContext::getWindowingSystemInterface();
        if (!wsi)
        {
                osg::notify(osg::NOTICE)<<"Error, no WindowSystemInterface 
available, cannot create windows."<<std::endl;
                return false;
        }

        osg::GraphicsContext::ScreenIdentifier si;
        si.readDISPLAY();

        // displayNum has not been set so reset it to 0.
        if (si.displayNum < 0) si.displayNum = 0;

        si.screenNum = m_FullScreenDevice;//screenNum;

        unsigned int width, height;
        wsi->getScreenResolution(si, width, height);

        osg::ref_ptr<osg::GraphicsContext::Traits> traits = new 
osg::GraphicsContext::Traits;
        traits->hostName = si.hostName;
        traits->displayNum = si.displayNum;
        traits->screenNum = si.screenNum;
        traits->x = 0;
        traits->y = 0;
        traits->width = width;
        traits->height = height;
        traits->windowDecoration = false;
        traits->doubleBuffer = true;
        traits->sharedContext =  
m_MasterViewer->getCamera()->getGraphicsContext();
 
        if ( ! m_GraphicsContext_FullScreen.valid()) {
                m_GraphicsContext_FullScreen = 
osg::GraphicsContext::createGraphicsContext(traits.get());
                if ( ! m_GraphicsContext_FullScreen.valid())
                {
                        osg::notify(osg::NOTICE)<<"GraphicsWindow has not been 
created successfully."<<std::endl;
                        return false;
                }
                std::cout << "[" << width << "/" << height << "]" << std::endl;
                m_GraphicsContext_FullScreen->realize();
        }
        
        osg::ref_ptr<osg::Camera> camera = new osg::Camera;
        camera->setGraphicsContext(m_GraphicsContext_FullScreen.get());
        camera->setViewport(new osg::Viewport(0,0,width, height));
        camera->setAllowEventFocus(false);

        m_MasterViewer->addSlave(camera.get(), false);
        WindowRectangle wr;
        wr.x=0;
        wr.y=0;
        wr.w=width;
        wr.h=height;
        m_FullScreenSlaves.insert(
                FullScreenSlaves::value_type(
                        m_MasterViewer->getNumSlaves()-1,
                        wr
                )
        );
 
        return true;
}

void WebaddonGuiEventHandler::registerEventCallback(GUIEventCallback* cb) {
        m_EventCallbackSet.insert(cb);
}

void WebaddonGuiEventHandler::unregisterEventCallback(GUIEventCallback* cb) {
        EventCallbackSet::iterator it = m_EventCallbackSet.find(cb);
        if ( it != m_EventCallbackSet.end() ) m_EventCallbackSet.erase(it);
}
  
_______________________________________________
osg-users mailing list
[email protected]
http://lists.openscenegraph.org/listinfo.cgi/osg-users-openscenegraph.org

Reply via email to