第7课时《osg交互》

原创 2016年05月31日 16:48:15

  1.交互

     所谓交互,一般指的的我们的键盘、鼠标等响应。OSG针对场景的操作封装了一系列的用于交互的事件处理器。

     在osgViewer中存在,addEventHandler方法,用于接收和处理事件。

      viewer->addEventHandler(new osgViewer::StatsHandler);//添加事件的实例,用于显示帧率等状态信息。

    2.自定义事件

      如果想要自己定义处理器,需要了解处理器的格式,一般处理器继承类osgGA::GUIEventHandler.

      class  A :public osgGA::GUIEventHandler,并重写相关的方法。

      viewer->addEventHandler(new A);来使用自定的事件处理类。

     整个过程如下图:

     

   

     实例:改写HelpHandler处理类。

     参照OSG中osgViewer中的HelpHandler的源文件,我们自己定义重写帮助处理类:PintInfo。

  class PrintInfo : public osgGA::GUIEvemtHandler //模拟一个事件类,响应h
    {
     public:
      bool HelpHandler::handle(const osgGA::GUIEventAdapter& ea, osgGA::GUIActionAdapter& aa){
            return false;
      }
      void HelpHandler::getUsage(osg::ApplicationUsage& usage) const
        {
              usage.addKeyboardMouseBinding(‘h’,"Onscreen help.");
       }
     };
     viewer->addEventHandlers(new PrintInfo); //应用事件处理类
       3. 经典实例

        响应键盘鼠标,改实例功能是鼠标右键单击时牛和飞机隐藏,鼠标左键双击是牛和飞机都显示,按住键盘上的LEFT键,显示牛,按RIGHT键显示飞机。

        详细代码如下:

        

class UseEventHandler : public osgGA::GUIEventHandler
{
public:
    ///
    /// \brief 事件处理的关键函数
    /// \param ea 用于识别事件类型
    /// \param aa 控制显示
    /// \return bool
    ///
    virtual bool handle(const osgGA::GUIEventAdapter& ea, osgGA::GUIActionAdapter& aa)
    {
        //获取要响应的view
        osgViewer::Viewer* viewer = dynamic_cast<osgViewer::Viewer*>(&aa);
        if (!viewer) return false;
        //开始判断事件类型
        switch(ea.getEventType())
        {
        case osgGA::GUIEventAdapter::KEYDOWN:
        {
            if (ea.getKey()== 0xFF51)
            {
                viewer ->getSceneData() ->asGroup() ->getChild(1) ->setNodeMask(0) ;
                viewer ->getSceneData() ->asGroup() ->getChild(0) ->setNodeMask(1) ;
            }
            if (ea.getKey()== 0xFF53)
            {
                viewer ->getSceneData() ->asGroup() ->getChild(0) ->setNodeMask(0) ;
                viewer ->getSceneData() ->asGroup() ->getChild(1) ->setNodeMask(1) ;
            }
        }
            break;
        case osgGA::GUIEventAdapter ::PUSH:
            if(ea.getButton () == 4)
            {
                viewer ->getSceneData() ->asGroup() ->getChild(0) ->setNodeMask(0) ;
                viewer ->getSceneData() ->asGroup() ->getChild(1) ->setNodeMask(0) ;
            }
            break;
        case osgGA::GUIEventAdapter::DOUBLECLICK:
            if(ea.getButton() == 1)
            {
                viewer ->getSceneData() ->asGroup() ->getChild(0) ->setNodeMask(1) ;
                viewer ->getSceneData() ->asGroup() ->getChild(1) ->setNodeMask(1) ;
            }
            break;
        default:
            break;
        }
        return false;
    }
    
};

void main()
{
    osgViewer::Viewer viewer;
    osg::ref_ptr<osg::Group> root = new osg::Group() ;
    root ->addChild(osgDB::readNodeFile("cow.osg")) ;
    root ->addChild(osgDB::readNodeFile("glider.osg"));
    viewer.setSceneData(root.get ());
    viewer.addEventHandler(new UseEventHandler) ;
    viewer.realize();
    viewer.run();
}

        


版权声明:本文为博主原创文章,未经博主允许不得转载。

7、osg中响应键盘鼠标事件以及鼠标和键盘编码表

1、首先定义一个类,该类继承与osgGA::GUIEventHandler,在此类中存在一个handle函数,所有的事件都在此函数中进行处理,如下类的代码: //声明类UseEventHandler,...
  • sunxiaoju
  • sunxiaoju
  • 2015年12月08日 22:49
  • 3236

OSG人机交互

OSG人机交互
  • sunnyloves
  • sunnyloves
  • 2017年02月17日 18:52
  • 678

OSG学习笔记12-期末大作业(包含交互、纹理、光照)

这是一个期末大作业,很low的大作业。按老师的要求要实现纹理,光照,交互等,还好可以用OSG,用OpenGL的话不知道要写多少代码。 这个代码主要就是实现了球体的贴图,添加了一个光照,还有通过键盘来...
  • u011310341
  • u011310341
  • 2016年06月13日 18:46
  • 1152

OSG学习笔记23——设置隐藏和显示节点(使用setNodeMask())

首先一开始设置场景中的某个节点为隐藏状态 mtCenter->setNodeMask(0);一开始尝试在eventHandler里面使用节点名字来遍历这个节点,发现根本找不到,因为设置为隐藏节点,大...
  • u011310341
  • u011310341
  • 2017年03月29日 14:47
  • 784

osg隐藏物体或者Node(多个物体轮流显示)

对于OSG源码的下载、编译我就不说明了,网上的例子很多。 使物体或者说Node隐藏方式有两种,一种是设置NodeMask,另外一种是使用osg的switch类来控制。 两者的区别是 前者只是看不到,数...
  • u011417605
  • u011417605
  • 2017年04月15日 12:21
  • 806

OSG 自带事件响应

osgGA::StateSetManipulator:该事件响应类的功能是对渲染状态进行控制,openGL的渲染管线使用了状态机的机制,此事件响应类对状态进行控制体现在当用户按w键时,可在体线点三种模...
  • liuci3234
  • liuci3234
  • 2013年03月29日 22:07
  • 3062

添加自定义事件以及对osg事件队列的简单理解

首先osg在其内部通过osgGA::EventQueue类维护了一个事件队列,队列中的每一个事件都是一个osgGA::GUIEventAdapter对象(这个对象是用来存放所系统捕捉到的事件),在仿真...
  • u010133496
  • u010133496
  • 2014年11月15日 23:24
  • 891

Python 小甲鱼教程 课后练习33 异常处理

第一题: 要求如下,检测输入是否为整数,如果是整数的话,通过,不是的话,捕获错误并报错! 代码如下: def int_input(prompt=''):     whi...
  • bestallen
  • bestallen
  • 2016年07月17日 16:17
  • 708

第35课第五题拓展

#include #include //第五题, 现在北京有一套房子,价格200万,假设房价每年上涨10%,一个软件工程师每年固定能赚40万。如果他想买这套房子,不贷款,不涨工资,没有其 //他收...
  • fh73566021
  • fh73566021
  • 2015年05月05日 20:28
  • 217

添加自定义事件以及对osg事件队列的简单理解

添加自定义事件 首先osg在其内部通过osgGA::EventQueue类维护了一个事件队列,队列中的每一个事件都是一个osgGA::GUIEventAdapter对象(这个对象是用来存放所系统...
  • L_Andy
  • L_Andy
  • 2016年04月04日 22:01
  • 1468
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:第7课时《osg交互》
举报原因:
原因补充:

(最多只允许输入30个字)