- #include <osg/Group>
- #include <osg/ShapeDrawable>
- #include <osgViewer/ViewerEventHandlers>
- #include <osgViewer/Viewer>
- #include <osgDB/ReadFile>
- #include <osgUtil/LineSegmentIntersector>
- #include <osgGA/GUIEventHandler>
- #include <osgGA/AnimationPathManipulator>
- #include <iostream>
- using namespace std;
- class PickEventHandle :public osgGA::GUIEventHandler
- {
- public:
- PickEventHandle(){
- _points=new osg::Vec3Array;
- }
- virtual ~PickEventHandle(){
- }
- osg::Geode*createBox(osg::Vec3 center){
- osg::ref_ptr<osg::Geode>geode=new osg::Geode;
- geode->getOrCreateStateSet()->setMode(GL_BLEND, osg::StateAttribute::ON);
- osg::ref_ptr<osg::ShapeDrawable>sd=new osg::ShapeDrawable(new osg::Box(center,5,5,5));
- sd->setColor(osg::Vec4(1,0,0,1));
- geode->addDrawable(sd);
- return geode.release();
- }
- float getRunTime(osg::Vec3 res,osg::Vec3 des){
- float xx=(res.x()-des.x())*(res.x()-des.x());
- float yy=(res.y()-des.y())*(res.y()-des.y());
- float zz=(res.z()-des.z())*(res.z()-des.z());
- float distant=sqrt(xx+yy+zz);
- return distant*0.1;
- }
- osg::AnimationPath*createPath(){
- osg::ref_ptr<osg::AnimationPath>anim=new osg::AnimationPath;
- anim->setLoopMode(osg::AnimationPath::LOOP);
- float time=0.0;
- float angle=0.0;
- float roll=1.57;//osg::inDegrees(90);
- if(_points.valid()){
- osg::Vec3Array::iterator iter=_points->begin();
- for(;;){
- osg::Vec3 pos(*iter);
- iter++;
- if(iter!=_points->end()) {
- if(iter->x() > pos.x())
- {
- angle=1.57-atan((iter->y()-pos.y())/(iter->x()-pos.x()));
- if(angle<0)
- angle+=1.57;
- }
- else {
- angle=-(1.57+atan((iter->y()-pos.y())/(iter->x()-pos.x())));
- if(angle>0){
- angle=-(1.57-angle);
- }
- }
- osg::Quat rotate (osg::Quat(roll,osg::Vec3(1.0,0,0))*osg::Quat(-angle,osg::Vec3(0,0,1)));
- anim->insert(time,osg::AnimationPath::ControlPoint(pos,rotate));
- time+=getRunTime(pos, *iter);
- }
- else {
- break;
- }
- }
- }
- ofstream out("/root/a.path");//把信息保存
- anim->write(out);
- out.close();
- return anim.release();
- }
- bool handle(const osgGA::GUIEventAdapter &ea ,osgGA::GUIActionAdapter &aa)
- {
- osgViewer::Viewer *viewer=dynamic_cast<osgViewer::Viewer*>(&aa);
- if(!viewer)
- return false;
- switch (ea.getEventType()){
- case osgGA::GUIEventAdapter::PUSH://寻找关键点
- {
- osgUtil::LineSegmentIntersector::Intersections inters;
- if(viewer->computeIntersections(ea.getX(),ea.getY(),inters)){
- osgUtil::LineSegmentIntersector::Intersections::iterator iter=inters.begin();
- osg::Vec3d pos=iter->getWorldIntersectPoint();
- cout<<pos.x()<<" "<<pos.y()<<" "<<pos.z()<<endl;
- _points->push_back(osg::Vec3(pos.x(),pos.y(),3));
- viewer->getSceneData()->asGroup()->addChild(createBox(pos));
- }
- }
- case osgGA::GUIEventAdapter::KEYDOWN:{
- if(ea.getKey()=='f' || ea.getKey()=='F'){//启动漫游(可以在这保存下操纵器,漫游完毕可以返回原来状态
- if(viewer)
- {
- osg::ref_ptr<osgGA::AnimationPathManipulator>apm=new osgGA::AnimationPathManipulator;
- apm->setAnimationPath(createPath());
- viewer->setCameraManipulator(apm);
- }
- }
- if(ea.getKey()=='g' || ea.getKey()=='G'){//用已经保存的文件里的信息
- osg::ref_ptr<osgGA::AnimationPathManipulator>apm=new osgGA::AnimationPathManipulator("/root/a.path");
- viewer->setCameraManipulator(apm);
- }
- }
- break;
- }
- return false;
- }
- private:
- osg::ref_ptr<osg::Vec3Array> _points;
- };
- int main(int argc, char *argv[])
- {
- osg::ref_ptr<osgViewer::Viewer>viewer=new osgViewer::Viewer;
- viewer->setSceneData(osgDB::readNodeFile("ceep.ive"));
- viewer->addEventHandler(new PickEventHandle());
- viewer->addEventHandler(new osgViewer::ScreenCaptureHandler);
- viewer->run();
- }
osg 路径 动画 效果
最新推荐文章于 2023-11-23 19:00:08 发布