Hi,
 
we are using the IDBuffer technique for object selection for serveral months. Now we have a new requirement, we need to apply cutting planes to our scene. That means they need to be applied to the IDBuffer rendering as well, to make sure that only visible parts of the scene may be selected.
Our approch was as follows:
- create a separate renderAction for the idbuffer rendering
- register custom functions for enter and leave for important object types (see attached source)
- each selectable node gets an id-material that gets activated when node is entered during rendering
 
I tried to extend this approach by collecting the clip plane chunks during render traversal and temporary adding them to the id materials but that doesn't work for some reason..
Does someone may have an idea how to accomplish the goal of a clipped id-buffer rendering?
 
Thanks in adance,
Michael
std::stack<std::pair<NodePtr, VDTNodeAttachmentPtr>> dataStack;
std::stack<osg::MaterialPtr> matStack;

Action::ResultE IDBufferSelectionHelper::onEnterGeometry( CNodePtr& pNode, 
Action * action )
{
        RenderAction *ra = dynamic_cast<RenderAction *>(action);
        MaterialDrawable *pMD = dynamic_cast<MaterialDrawable 
*>(pNode.getCPtr());

         Material::DrawFunctor func;
         func = osgTypedMethodFunctor1ObjPtr(pMD, 
&MaterialDrawable::drawPrimitives);

         ra->dropFunctor(func, NULL);

        if(ra->pushVisibility())
        {
                if(ra->selectVisibles() == 0)
                {
                        ra->popVisibility();
                        return Action::Skip;
                }
        }

        return Action::Continue;
}

Action::ResultE IDBufferSelectionHelper::onLeaveGeometry( CNodePtr&, Action * 
action )
{
        RenderAction *ra = dynamic_cast<RenderAction *>(action);

        ra->popVisibility();

        return Action::Continue;
}

Action::ResultE IDBufferSelectionHelper::onEnterGroup( CNodePtr& pNode, Action 
* action )
{
        RenderAction *ra = dynamic_cast<RenderAction *>(action);

        if (ra->pushVisibility())
        {
                if(ra->selectVisibles() == 0)
                {
                        ra->popVisibility();
                        return Action::Skip;
                }
        }

        return Action::Continue;
}

Action::ResultE IDBufferSelectionHelper::onLeaveGroup( CNodePtr& pNode, Action 
* action )
{
        RenderAction *ra = dynamic_cast<RenderAction *>(action);

        ra->popVisibility();

         return Action::Continue;
}

Action::ResultE IDBufferSelectionHelper::onEnterMatGroup( CNodePtr& pNode, 
Action * action )
{
        Action::ResultE r = IDBufferSelectionHelper::onEnterGroup(pNode, 
action);

        // ok all children are culled away so we leave
        // immediately and don't set the material!
        if(r == Action::Skip)
                return r;
        
        MaterialGroup* g = dynamic_cast<MaterialGroup *>(pNode.getCPtr());
        if(g && g->getMaterial()!=NullFC)
        {
                matStack.push(g->getMaterial());
        }

        return Action::Continue;
}

Action::ResultE IDBufferSelectionHelper::onLeaveMatGroup( CNodePtr& pNode, 
Action * action )
{
        RenderAction *ra = dynamic_cast<RenderAction *>(action);

        MaterialGroup* g = dynamic_cast<MaterialGroup *>(pNode.getCPtr());
        if(g && g->getMaterial()!=NullFC)
        {
                matStack.pop();
        }
        
        return IDBufferSelectionHelper::onLeaveGroup(pNode, action);
}

Action::ResultE IDBufferSelectionHelper::onEnterTransform( CNodePtr& pNode, 
Action * action )
{
        RenderAction *ra = dynamic_cast<RenderAction *>(action);
        NodePtr n = ra->getActNode();

        if( IDBufferSelectionHelper::getInstance()->isDebug() )
                cout << "Transform" << endl;

        if( n != osg::NullFC )
        {
                VDTNodeAttachmentPtr vdtNodeData = 
VDTNodeAttachmentPtr::dcast(n->findAttachment(VDTNodeAttachment::getClassType()));
                if( vdtNodeData != osg::NullFC )
                {
                        dataStack.push(std::pair<NodePtr, 
VDTNodeAttachmentPtr>(n, vdtNodeData));
                        ra->setMaterial(vdtNodeData->getIdMaterial().getCPtr(), 
n);
                }
        }

        ra->pushVisibility();

        TransformPtr tp = TransformPtr::dcast(pNode);
        if(tp != osg::NullFC )
        {
                if( IDBufferSelectionHelper::getInstance()->isDebug() )
                        cout << "push " << tp->getMatrix() << endl;

                ra->push_matrix(tp->getMatrix());
        }

    return Action::Continue;
}

Action::ResultE IDBufferSelectionHelper::onLeaveTransform( CNodePtr& pNode, 
Action * action )
{
        RenderAction *ra = dynamic_cast<RenderAction *>(action);
        NodePtr n = ra->getActNode();

        if( n != osg::NullFC )
        {
                VDTNodeAttachmentPtr vdtNodeData = 
VDTNodeAttachmentPtr::dcast(n->findAttachment(VDTNodeAttachment::getClassType()));
                if( vdtNodeData != osg::NullFC )
                {
                        dataStack.pop();
                        
                        if(dataStack.empty())
                                ra->setMaterial(NULL, osg::NullFC);
                        else
                        {
                                std::pair<NodePtr, VDTNodeAttachmentPtr> 
nextData = dataStack.top();
                                
ra->setMaterial(nextData.second->getIdMaterial().getCPtr(), nextData.first);
                        }
                }
        }

        ra->popVisibility();

        ra->pop_matrix();

        return Action::Continue;
}


IDBufferSelectionHelper::IDBufferSelectionHelper() :
{
        this->_ract = osg::RenderAction::create();
        this->_ract->setSortTrans(true);
        this->_ract->setZWriteTrans(true);
        this->_ract->setLocalLights(true);
        this->_ract->setFrustumCulling(true);
        this->_ract->setStateSorting(true);
        
        this->_ract->registerEnterFunction(OSG::Geometry::getClassType(),
                                OSG::osgTypedFunctionFunctor2CPtrRef<
                                    OSG::Action::ResultE,
                                    OSG::CNodePtr,
                                    OSG::Action *                      >(
                                                                        
IDBufferSelectionHelper::onEnterGeometry ) );

        this->_ract->registerLeaveFunction(OSG::Geometry::getClassType(),
                                OSG::osgTypedFunctionFunctor2CPtrRef<
                                    OSG::Action::ResultE,
                                    OSG::CNodePtr,
                                    OSG::Action *                      >(
                                                                        
IDBufferSelectionHelper::onLeaveGeometry ) );

        this->_ract->registerEnterFunction(OSG::MaterialGroup::getClassType(),
                                OSG::osgTypedFunctionFunctor2CPtrRef<
                                    OSG::Action::ResultE,
                                    OSG::CNodePtr,
                                    OSG::Action *                      >(
                                                                        
IDBufferSelectionHelper::onEnterMatGroup ) );

        this->_ract->registerLeaveFunction(OSG::MaterialGroup::getClassType(),
                                OSG::osgTypedFunctionFunctor2CPtrRef<
                                    OSG::Action::ResultE,
                                    OSG::CNodePtr,
                                    OSG::Action *                      >(
                                                                        
IDBufferSelectionHelper::onLeaveMatGroup ) );

        this->_ract->registerEnterFunction(OSG::Group::getClassType(),
                                OSG::osgTypedFunctionFunctor2CPtrRef<
                                    OSG::Action::ResultE,
                                    OSG::CNodePtr,
                                    OSG::Action *                      >(
                                                                        
IDBufferSelectionHelper::onEnterGroup ) );

        this->_ract->registerLeaveFunction(OSG::Group::getClassType(),
                                OSG::osgTypedFunctionFunctor2CPtrRef<
                                    OSG::Action::ResultE,
                                    OSG::CNodePtr,
                                    OSG::Action *                      >(
                                                                        
IDBufferSelectionHelper::onLeaveGroup ) );

        this->_ract->registerEnterFunction(OSG::Transform::getClassType(),
                                OSG::osgTypedFunctionFunctor2CPtrRef<
                                    OSG::Action::ResultE,
                                    OSG::CNodePtr,
                                    OSG::Action *                      >(
                                                                        
IDBufferSelectionHelper::onEnterTransform) );

        this->_ract->registerLeaveFunction(OSG::Transform::getClassType(),
                                OSG::osgTypedFunctionFunctor2CPtrRef<
                                    OSG::Action::ResultE,
                                    OSG::CNodePtr,
                                    OSG::Action *                      >(
                                                                        
IDBufferSelectionHelper::onLeaveTransform ) );


        and so on....
}

------------------------------------------------------------------------------
See everything from the browser to the database with AppDynamics
Get end-to-end visibility with application monitoring from AppDynamics
Isolate bottlenecks and diagnose root cause in seconds.
Start your free trial of AppDynamics Pro today!
http://pubads.g.doubleclick.net/gampad/clk?id=48808831&iu=/4140/ostg.clktrk
_______________________________________________
Opensg-users mailing list
Opensg-users@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/opensg-users

Reply via email to