OSG学习笔记6—鸟瞰图相机

// osg4_25.cpp : 定义控制台应用程序的入口点。
//鸟瞰图相机
//新建一个相机对象,并且设置它的投影矩阵为正交投影,设置观察位置在整个模型数据的正上方(Z+方向),构成一种鸟瞰图的效果
//产生目标场景视图的变化过程类似于用相机拍照:
//步骤如下:
//1.设置相机位置:视点变换
//2.调整物体位置:模型变换(OSG中通过某一对象子节点树中多个Transform节点的级联来实现,就是之前的空间变换节点)
//3.调焦拍摄:投影变换
//4.冲洗照片:视口变换
//(1)模型视点变换:相当于调整要拍摄物体的位置,姿态,以及调整相机使其对准景物的过程。视点变换的行为可以看作模型变换的逆操作。
//事实上,改变观察点的位置与方向和改变物体本身的位置与方向具有等效性。
//经过模型视点变换之后可以认为场景从世界坐标系转换到了相机坐标系。
//(2)投影变换:相当于拍照时通过选择镜头和调整焦距等,将景物投射到二维底片的过程。
//投影变换的主要操作对象是一个立法体(平行视景体),结果实生成一个正射投影矩阵
//或者棱台形状的视景体(视锥体),完成透视投影工作,离视点近的物体较大,离视点远的物体较小。
//在视景体为的对象将被裁切,不会被投影到二维面上。
//(3)视口变换:将投影变换所得到的结果反映到指定的屏幕窗口上。意味着场景最终变换到窗口坐标系中。
//相机节点:实现视点变换osg::Camera;构建观察的投影矩阵和窗口矩阵。实现三维场景向二维平面的映射。
//多个Camera节点允许共享同一颗子节点树结构,允许多台相机从不同角度以不同方式拍摄同一物体。




#include "stdafx.h"
#include<osg/Camera>
#include<osgDB/ReadFile>
#include<osgViewer/Viewer>


osg::Camera* creatBirdsEye(const osg::BoundingSphere& bs)
{
osg::ref_ptr<osg::Camera> camera = new osg::Camera;//定义一个相机节点
camera->setClearMask(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT);//清除它的颜色和深度缓存,
                                                             //这意味着这个相机渲染子场景时会覆盖之前任何相机的渲染数据
camera->setReferenceFrame(osg::Transform::ABSOLUTE_RF);//设置相机的参考坐标系,设置为ABSOLUTE_RF意味着相机的所有变换矩阵和观察/投影矩阵的设置
                                                      //都是相对于世界坐标的不会受到上一级矩阵的影响


//根据包围球大小,设置相机的投影矩阵
double viewDistance = 2.0*bs.radius();
double znear = viewDistance - bs.radius();
double zfar = viewDistance + bs.radius();
float top = bs.radius();
float right = bs.radius();
camera->setProjectionMatrixAsOrtho(-right, right, -top, top,znear,zfar);


//根据模型的中心位置,设置相机的观察矩阵。
osg::Vec3d upDirection(0.0,1.0,0.0);
osg::Vec3d viewDirection(0.0,0.0,1.0);
osg::Vec3d center = bs.center();
osg::Vec3d eyePoint = center + viewDirection*viewDistance;
camera->setViewMatrixAsLookAt(eyePoint, center, upDirection);


return camera.release();
}


int _tmain(int argc, char** argv)
{
osg::ArgumentParser arguments(&argc, argv);
osg::Node* model = osgDB::readNodeFiles(arguments);
if (!model)model = osgDB::readNodeFile("lz.osg");


osg::Camera* camera = creatBirdsEye(model->getBound());
camera->addChild(model);


osgViewer::Viewer viewer;
viewer.setSceneData(camera);//相机节点可以直接设置给视景器
return viewer.run();
}

你可能感兴趣的:(OSG学习笔记6—鸟瞰图相机)