查看: 3745|回复: 7

鼠标拾取物体,显示其节点名称

[复制链接]

该用户从未签到

发表于 2009-10-30 16:21:44 | 显示全部楼层 |阅读模式
刚开始学习,请教各位高手帮忙、!谢谢
下面是我的一部分程序代码。自己整理了一下。

可是不能正确显示出我所要的节点名称(Gang_gan)
在程序运行后,显示的是1-GEODE(见附件图),不知我该如何解决呢,谢谢!!

1.PNG



void cOSG::InitSceneGraph(void)
{
    mRoot  = new osg::Group;
    mModel = osgDB::readNodeFile(m_ModelName);
    mModel.get()->setName("Gang_gan");//此处是我设置的名称。如何可以是中文的就更好了,就是不知getName()支持中文吗?

    osgUtil::Optimizer optimizer;
    optimizer.optimize(mModel.get());
    optimizer.reset();

    //添加模型到场景中
    mRoot->addChild(mModel.get());
}


//事件处理函数
bool CPickHandler::handle(const osgGA::GUIEventAdapter& ea,osgGA::GUIActionAdapter& aa)
{
    switch(ea.getEventType())
    {
    case(osgGA::GUIEventAdapter::FRAME):
        {
            osgViewer::Viewer* viewer = dynamic_cast<osgViewer::Viewer*>(&aa);
            //得到视图矩阵
            viewer ->getCamera() ->getViewMatrixAsLookAt(position, center, up) ;
            if (viewer)
            {   
                //执行PICK动作
                pick(viewer,ea);
            }
            return false;
        }   
    default:
        return false;
    }

}
//PICK动作
void CPickHandler::pick(osgViewer::Viewer* viewer, const osgGA::GUIEventAdapter& ea)
{
    //创建一个线段交集检测对象,
    //与交集包围盒的关系,并允许在某个子图形不可能存在有交集的子节点时,跳过该子图形的遍历。
    osgUtil:ineSegmentIntersector::Intersections intersections;

    std::string gdlist="";
   
    //得到鼠标的位置
    float x = ea.getX();
    float y = ea.getY();

    if(viewer->computeIntersections(x,y,intersections))
    {
        //得到相交交集的交点
        for(osgUtil::LineSegmentIntersector::Intersections::iterator hitr = intersections.begin();//用迭代器,指向交集
            hitr != intersections.end();//若交集没有遍历完,继续
            ++hitr)
        {
            std:stringstream os;

            if (!hitr->nodePath.empty() && !(hitr->nodePath.back()->getName().empty()))//若从根到选取物体(结点Geode)的路径不为空,并且该物体的name不为空,说明已经找到符合要求的物体,网上说这样可以把所有的结点的name取出来
            {                                                               
                os<<"This is a "<<hitr->nodePath.back()->getName()<<std::endl;//输出结点的名字(如何输出之前setName设置名字)
               
                gdlist += os.str();
                break;//只要找到第一个结点,根结点就可以了,找到就跳出循环
                这里怎么会直接选取物体的最底的一层geode层,如何选Group层?如果注释去break,可以选到好多Geode
            }
        }
    }

    setLabel(gdlist);
}

该用户从未签到

发表于 2009-10-30 19:33:39 | 显示全部楼层
请参考osgpick~

该用户从未签到

 楼主| 发表于 2009-11-2 11:06:28 | 显示全部楼层
看了下,osgpick还是对Geode几何的选取,是不是要用getParent()来得到它的父节点?

如何来判断我选取的是一个物体那,我这个图中是由几个几何体组成的。
谢谢。

该用户从未签到

发表于 2009-11-2 11:56:14 | 显示全部楼层
求交肯定是针对几何体进行的,如果想获取求交所经过的节点路径的话,用LineSegmentIntersector::Intersection::nodePath是最好的选择

该用户从未签到

 楼主| 发表于 2009-11-2 15:35:36 | 显示全部楼层
4# array

针对我的问题不知如何实现会好点?
有这样一个函数不知是什么意思?nodePath.back()

谢谢array!!!

另外,发现OpenSceneGraph Reference Docs.chm中的函数并不完整,很多只是一个函数没有解释。不知有什么好的方法学习这些函数?

该用户从未签到

发表于 2009-11-2 15:40:22 | 显示全部楼层
nodePath.back()就是获取的节点路径的最末一个节点
学习函数功能的最好方法是深入源代码,除此之外,任何文档都不是完善的

该用户从未签到

 楼主| 发表于 2009-11-3 09:08:03 | 显示全部楼层
谢谢!!
这么说是不是有与back()函数相对 的函数,可以直接获得上一层的节点?在源文件中没有找到

该用户从未签到

发表于 2009-11-3 09:13:54 | 显示全部楼层
参照std::vector的用法,NodePath就是vector<Node*>,所以很多函数方法根本就不需要再单独说明了
您需要登录后才可以回帖 登录 | 注册

本版积分规则

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

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

联系我们

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