查看: 2073|回复: 8

请教载入模型的淡入淡出的问题

[复制链接]

该用户从未签到

发表于 2009-3-26 18:34:02 | 显示全部楼层 |阅读模式
当显示大型的场景模型时(使用PagedLOD来调用子模型),各个子模型会由于电脑性能限制逐个显示在viewer中,请问如何实现各个子模型在刚刚显示出现时具有淡入效果,而其他已经显示出现的子模型不受影响。我使用更新回调函数总是整个场景全部淡入淡出  请高手们指点迷津 谢谢!

该用户从未签到

发表于 2009-3-26 19:32:24 | 显示全部楼层
这个要看您是怎么编写代码的了,您是如何让整个场景全部淡入淡出的,把被操作的节点换成那个需要淡出效果的节点即可

该用户从未签到

 楼主| 发表于 2009-3-26 20:33:21 | 显示全部楼层
我是遍历每个PagedLOD结点来调用淡入的callback的
class FadeCallback :public osg::NodeCallback
{
public:
        FadeCallback():alpha(0)
        {
                blendFunc = new osg::BlendFunc();
                blendColor= new osg::BlendColor(osg::Vec4(1, 1, 1, 0.0));
                blendFunc->setSource(osg::BlendFunc::CONSTANT_ALPHA);
                blendFunc->setDestination(osg::BlendFunc::ONE_MINUS_CONSTANT_ALPHA);
        }

          virtual void operator()(osg::Node* node ,osg::NodeVisitor* nv)
          {
                  node->getOrCreateStateSet()->setAttributeAndModes(blendFunc,osg::StateAttribute::ON);
                  node->getOrCreateStateSet()->setAttributeAndModes(blendColor,osg::StateAttribute::ON);
                  alpha += 0.01;
                  blendColor->setConstantColor(osg::Vec4(1, 1, 1,alpha));
                  if (alpha > 1) alpha = 1.0f;
                  traverse( node, nv );
        }
          float alpha;
          osg::BlendFunc    *blendFunc;
          osg::BlendColor    *blendColor;
};

class LODVisitor : public osg::NodeVisitor
{
public:
        LODVisitor()sg::NodeVisitor(osg::NodeVisitor::TRAVERSE_ALL_CHILDREN){}
       
        virtual void apply(osg::Node& node)
        {
                osg:agedLOD* mLOD;
                if(dynamic_cast<osg::PagedLOD*>(&node)!=NULL)
                {
                        mLOD=dynamic_cast<osg::PagedLOD*>(&node);
                        mLOD->setUpdateCallback(new FadeCallback());
                }
                traverse(node);
        }
};

int main(int argc, char** argv)
{
        setlocale(LC_ALL,"chs");

        osg::ref_ptr<osg::Node> root = new osg::Node();
        if(argc < 2)
        {
                string strFileName;
                cout<<"lease input File Name:"<<endl;
                cin>>strFileName;
                root=osgDB::readNodeFile(strFileName);
        }
        else
        {
                root=osgDB::readNodeFile(argv[1]);
        }
       
        LODVisitor lv;
        root->accept(lv);
        osg::ref_ptr<osgViewer::Viewer> viewer = new osgViewer::Viewer();
        viewer->setSceneData(root.get());
        viewer->realize();
        viewer->run();
        return 0;
}

该用户从未签到

发表于 2009-3-26 20:50:09 | 显示全部楼层
您用自定义的LODVisitor对每个节点都加了FadeCallback,那么它们当然会同时淡入淡出了。有很多种实现方法,如果您比较喜欢用回调的话,可以设法取得当前要执行淡入的节点指针,然后给其设置FadeCallback,其它不执行淡入的则设置setUpdateCallback(NULL)

该用户从未签到

 楼主| 发表于 2009-3-27 08:59:35 | 显示全部楼层
那请问如何获得当前场景中正在显示子模型的节点呢,在下是osg新人,还请arrray大师多多帮助啊

该用户从未签到

发表于 2009-3-27 11:06:54 | 显示全部楼层
说实话这个用回调似乎不太容易。我个人的建议是继承并派生一个新的LOD节点,并且重点改写它的traverse函数,在其中获取当前范围内的节点并执行淡入操作

该用户从未签到

 楼主| 发表于 2009-3-27 11:28:12 | 显示全部楼层
那如果不用回调,该如何实现呢?

该用户从未签到

发表于 2009-3-27 12:17:32 | 显示全部楼层
我不是已经回答了?自己派生新的LOD节点类并重写traverse函数

该用户从未签到

 楼主| 发表于 2009-3-27 13:47:06 | 显示全部楼层
那我试着写一下吧, 非常感谢
您需要登录后才可以回帖 登录 | 注册

本版积分规则

OSG中国官方论坛-有您OSG在中国才更好

网站简介:osgChina是国内首个三维相关技术开源社区,旨在为国内更多的技术开发人员提供最前沿的技术资讯,为更多的三维从业者提供一个学习、交流的技术平台。

联系我们

  • 工作时间:09:00--18:00
  • 反馈邮箱:1315785073@qq.com
快速回复 返回顶部 返回列表