osgearth学习文档.docx
- 文档编号:29329749
- 上传时间:2023-07-22
- 格式:DOCX
- 页数:16
- 大小:73KB
osgearth学习文档.docx
《osgearth学习文档.docx》由会员分享,可在线阅读,更多相关《osgearth学习文档.docx(16页珍藏版)》请在冰豆网上搜索。
osgearth学习文档
osgEarth:
:
Drivers:
:
TMSOptionsClassReference
通过程序加载数据
赶紧进入正题,程序加载各种数据,首先介绍一下总体的方式
/*这里XXXOptions是根据不同的数据类型选择不同驱动,比如加载本地数据可以使用GDALOptions,加载TMS数据可以使用TMSOptions(注意TMSOptions可以加载本地也可以加载网上数据),WMSOptions可以加载网上数据(注意这个options主要加载影像和图片数据),ArcGISOptions加载ArcGISServer发布数据。
*/
osgEarth:
:
Drivers:
:
XXXOptionsXXXLayer;
/*这里就是加载的数据路径,如果加载的本地数据就是本地数据的路径,如果加载是网 上数据就是相应的网址*/
XXXLayer.url()=osgEarth:
:
URI(".................................");
/*加载的数据是分层管理,每加载进来一个数据在earth上就是一个数据层,这里给数据层付个名字。
*/
std:
:
stringLayerName="earth";
/*osgearth里layer主要有三种类型ImageLayer、ElevationLayer和ModleLayer,前两个大家从字面就可以知道第一个是加载影像和第二个是加载高程数据的,第三个是主要用来加载shp数据,至少我是这样用的,不知道还能否加载其他数据类型。
确定加载用的驱动、数据源位置(路径)、数据层名和初始化了数据层,接下来就是把数据层加到地球中如下所示。
*/
osg:
:
ref_ptr : XXXLayer>layer=new osgEarth: : XXXLayer(osgEarth: : XXXLayerOptions(LayerName,XXXLayer)); m_pMap->addImageLayer(layer.get()); (1)加载本地数据 a 本地影像数据,数据类型为tif osgEarth: : Drivers: : GDALOptionsimagelayerOpt;//选择GDALOptions imagelayerOpt.url()=osgEarth: : URI("E: \\vs2010ProgamFiles\\osgVR74\\osgVR74\\world.tif");//影像数据路径 std: : stringimagelayerName="worldimage"; //影像数据层名 osg: : ref_ptr : ImageLayer>imageLayer=new osgEarth: : ImageLayer(osgEarth: : ImageLayerOptions(imagelayerName ,imagelayerOpt)); //初始数据层 m_pMap->addImageLayer(imageLayer .get()); b本地高程数据,数据类型为tif osgEarth: : Drivers: : GDALOptionsdemlayerOpt; //使用还是GDALOptions demlayerOpt.url()=osgEarth: : URI("E: \\vs2010ProgamFiles\\osgVR74\\osgVR74\\worlddem.tif");//高程数据路径 std: : stringdemlayerName="worlddem";//高程数据层名 osg: : ref_ptr : ImageLayer>demLayer=newosgEarth: : ImageLayer(osgEarth: : ImageLayerOptions(demlayerName,demlayerOpt));//初始数据层 m_pMap->addImageLayer(demLayer.get()); 加载本地经过package切片的数据还可以用TMSOptions, osgEarth: : Drivers: : TMSOptionstmsOpt;////选择TMSOptions驱动 tmsOpt.url()=osgEarth: : URI("//Edvis_-1/Layer_0/tms.xml");//package 切片生成金字塔文件下的xml std: : stringDemtmslayerName="TmsDem";//图层名 osgEarth: : ElevationLayerOptionstmslayerOpt(DemtmslayerName,tmsOpt); osg: : ref_ptr : ElevationLayer> TmsDemLayer=newosgEarth: : ElevationLayer(tmslayerOpt); m_pMap->addElevationLayer(TmsDemLayer.get());//初始化图层并加入到地球中 (2)加载网上数据 a加载ArcGISServer发布的数据加载方式与上面提到的类似 osgEarth: : Drivers: : ArcGISOptionsMapImageLayer; MapImageLayer.url()=osgEarth: : URI("http: //xxx.xxx.xxx.xxx.: xxxx/arcgis/rest/services/world/map003/MapServer"); std: : stringCdlayerName="worldimage"; osg: : ref_ptr : ImageLayer>cdlayer=newosgEarth: : ImageLayer(osgEarth: : ImageLayerOptions(CdlayerName,MapImageLayer)); m_pMap->addImageLayer(cdlayer.get()); //这里注意,当osgearth访问ArcGISServer发布数据的时候有些问题很奇怪,用上面的方式访问ArcGISServer国外发布的数据没问题,但是访问自己发布的数据就会有问题,经过试验投影要设成3857才能正常访问。 b加载网上数据还可以用WMSOptions加载方式同上。 2015/12/14 1.osgEarth: : Util: : MapNodeHelper.解析内部的命令行参数。 非静态成员变量不能使用类名直接访问。 例如: osgEarth: : Util: : MapNodeHelper: : load() 这样的形式是错误的。 osg: : Group*load(osg: : ArgumentParser&args,osgViewer: : View*view,Control*userControl=0L)const 函数是载入map文件,解析所有的内部命令行参数与外部的XML文件。 2.osgEarth: : MapNode。 建立OsgEarth的根节点。 3.osgEarth: : Util: : Controls: : Grid.此类是父类Container按照栅格形式组织子类。 4.osgEarth: : Util: : Controls: : LabelControl.表示一个字符串的控件。 2015/12/15 1.voidosgViewer: : View: : setCameraManipulator(osgGA: : CameraManipulator*manipulator, boolresetPosition=true) 设置相机操作器。 OsgViewer: : Viewer的继承关系如下图所示。 视图-View;视景器-Viewer。 osgViewer: : View类别 2015/12/17 1.osgGA: : GUIEventHandler为GUI事件提供一个基本的接口。 2.osgEarth: : Mapmap是mapNode所渲染的主要的数据模型,包括所有的层对象。 3.osgEarth: : Terrain是为地形图的接口服务的 4.osgEarth: : ElevationQuery查询地图上任意点的高程数据 5.osgEarth: : GeoPoint 2015/12/20 1.osg: : ArgumentParser解析参数的类。 2.osgEarth: : Annotation: : ModelNode。 从URI传递一个3D模型(注释节点)然后放置在一个地理节点。 2015/12/21 动态显示经纬度坐标以及高程方法 1.osgEarth: : SpatialReferenceClass.保留描述参考椭球体和地理空间数据的投影的相关数据。 2.osgEarth: : MapNodeClass中的函数constSpatialReference*MapNode: : getMapSRS()const.得到地图的地理空间参考系统。 3.osgEarth: : Util: : Controls: : ControlCanvasClass。 将控件与OSG视景相关联。 4.osgGA: : GUIEventHandler为GUI事件提供一个基本的接口。 在这个类的基础上,派生了其他的类,比如在高程与经纬度查询的osgViewer: : StatsHandler类(为了增加屏幕状态到视景体的事件句柄),osgViewer: : WindowSizeHandler类(改变窗口模式的屏幕分辨率和开关全屏模式和窗口模式的事件句柄),osgGA: : StateSetManipulator类(实验类,不能被观察一段时间,但是能够返回到某个点)。 5.动态显示经纬度和高程 经纬度查询的机制。 主要是利用碰撞检测机制,鼠标点在二维的屏幕上的坐标,然后利用碰撞检测求得世界坐标X,Y,Z,然后再将世界坐标转换成与地理相关的三维坐标,然后再将此地理三维坐标转换成与经纬度有关的坐标。 重写handle函数。 boolhandle(constosgGA: : GUIEventAdapter&ea,osgGA: : GUIActionAdapter&aa) { if(ea.getEventType()==osgGA: : GUIEventAdapter: : MOVE&& aa.asView()->getFrameStamp()->getFrameNumber()%10==0) { osgViewer: : View*view=static_cast : View*>(aa.asView()); update(ea.getX(),ea.getY(),view); } returnfalse; } 其中的osgGA: : GUIEventAdapter类是存储键盘,鼠标和窗口事件。 osgGA: : GUIActionAdapter是抽象基类,它定义了GUIEventHandlers事件句柄将要访问GUI的接口。 然后调用相应的更新函数update(); voidupdate(floatx,floaty,osgViewer: : View*view) { boolyes=false; //lookunderthemouse: osg: : Vec3dworld; osgUtil: : LineSegmentIntersector: : Intersectionshits; if(view->computeIntersections(x,y,hits)) { world=hits.begin()->getWorldIntersectPoint(); //converttomapcoords: GeoPointmapPoint; mapPoint.fromWorld(_terrain->getSRS(),world); //doanelevationquery: doublequery_resolution=0;//1/10thofadegree doubleout_hamsl=0.0; doubleout_resolution=0.0; boolok=_query.getElevation( mapPoint, out_hamsl, query_resolution, &out_resolution); if(ok) { //converttogeodetictogettheHAE: mapPoint.z()=out_hamsl; GeoPointmapPointGeodetic(s_mapNode->getMapSRS()->getGeodeticSRS(),mapPoint); staticLatLongFormatters_f; s_posLabel->setText(Stringify() < : fixed< : setprecision (2) < <<"," < s_mslLabel->setText(Stringify()< s_haeLabel->setText(Stringify()< s_resLabel->setText(Stringify()< yes=true; } //finally,getanormalISECTHAEpoint. GeoPointisectPoint; isectPoint.fromWorld(_terrain->getSRS()->getGeodeticSRS(),world); s_mapLabel->setText(Stringify()< } if(! yes) { s_posLabel->setText("-"); s_mslLabel->setText("-"); s_haeLabel->setText("-"); s_resLabel->setText("-"); } } 其中的osgUtil: : LineSegmentIntersector是直线与场景图交点的实体类。 而其中的hits是多集。 因为typedefstd: : multiset : LineSegmentIntersector: : Intersections,osgUtil: : LineSegmentIntersector: : Intersectionshits。 然后计算交点的三维坐标值: view->computeIntersections(x,y,hits)。 将此交点转换成世界坐标X,Y,Z: world=hits.begin()->getWorldIntersectPoint(),再将世界坐标转换成地理相关的三维坐标: GeoPointmapPoint;mapPoint.fromWorld(_terrain->getSRS(),world);然后进行高程的查询: boolok=_query.getElevation(mapPoint,out_hamsl,query_resolution,&out_resolution); 然后再重新构建地理坐标: GeoPointmapPointGeodetic(s_mapNode->getMapSRS()->getGeodeticSRS(),mapPoint); 此处对getSRS,getMapSRS以及getGeodeticSRS进行区别。 getSRS(): 得到与地形相关的地图的空间参照系。 它是osgEarth: : Terrain类的成员函数。 此类表示与现场地形图的交互服务。 它跟Mapmodel(地图模型)不同,地图代表了地形参数的数据支持,而Terrian代表了内存中实际的几何图形。 通过getSRS()得到的空间参考系是以单元组织的地图坐标值。 getMapSRS(): 得到地图的空间参照系。 它是osgEarth: : MapNode类的成员函数。 此类主要是利用osg中的node建立osgearth中map的根节点。 getGeodeticSRS(): 得到当前空间参照系的地理空间参照系。 它是osgEarth: : SpatialReference类的成员函数。 osgEarth: : SpatialReference类是SpatialReference持有描述参考椭球体/数据的信息和地理空间数据的投影。 然后将得到的地理三维坐标转换成经纬度: staticLatLongFormatters_f;s_f.format(mapPointGeodetic.y(),true);s_f.format(mapPointGeodetic.x(),false)。 最好得到相应的法线与椭球体的交点: GeoPointisectPoint; isectPoint.fromWorld(_terrain->getSRS()->getGeodeticSRS(),world); 2015/12/22 1.坐标系统的区别 世界坐标系: 世界坐标系是一个特殊的坐标系统,它建立了描述其他坐标系所需的参考框架。 它可以用来描述其他的坐标系的位置。 它能够描述整个场景中的所有对象。 世界坐标系的位置是绝对的,它为所有对象的位置提供一个绝对的参考标准,从而避免物体之间的独立的坐标系统之间的混乱。 物体坐标系: 物体坐标是每个物体特定的坐标系,因为每个对象包含了顶点坐标以及其纹理坐标等,如果每个坐标都相对于世界坐标来进行变换将会非常困难,而且坐标的精度也不够高,如果每个对象都建立自己的物体坐标系,而只需通过物体坐标系相对于世界坐标系的变换即可描述物体的。 摄像机坐标系: 摄像机坐标系是和观察者密切相关的坐标系,摄像机坐标系和屏幕坐标系相似,差别在于摄像机坐标系处于3D空间中。 它可视为特殊的物体坐标,该物体坐标系统定义在摄像机的屏幕区域。 摄像机坐标系描述的是哪些物体应该渲染并显示在屏幕上,主要包括物体是否在摄像机坐标区域内,物体的渲染顺序和物体的遮挡渲染等。 2015/12/23 1.osgEarth: : TileSource 2015/12/24 1.osgEarth: : ProgressCallback是一个通用接口类,针对函数进行进程的报告。 2.osg: : ImageClass。 封装存储的纹理图像数据。 3.osgEarth: : TileKey类.相对于轮廓,唯一的标识地图上的瓦片数据。 轮廓从左上角的0,0点开始 4.osgEarth: : Symbology: : GeometryRasterizer。 使用软件渲染路径将几何图形绘制到画布上。 5.osgEarth: : ImageLayerOptions。 初始化图像层的选项 2015/12/25 1.osgEarth: : HTTPClientClass。 工具类的HTTP访问 2.osgDB: : Registry。 注册表是一个单例的工厂模式,存储运行时读取的非内部文件。 3.osgEarth: : BoundsClass。 表示匿名的边界。 2015/12/27 1.osgEarth: : Drivers: : OGRFeatureOptions。 2.osgEarth: : Features: : FeatureSource。 2015/12/29 1.osgEarth: : Util: : EarthManipulatorClass。 可编程的操作器,适用于使用地理地形 2. 解读osgViewer/ViewerBase.cpp中的osgViewer: : ViewerBase: : frame()。 在这个函数中主要有5个过程: 1)、如果这是仿真系统启动后的第一帧,则执行viewerInit();此时如果还没有执行realize()函数,则执行它。 2)、执行advance函数。 3)、执行eventTraversal函数,顾名思义,这个函数将负责处理系统产生的各种事件,诸 如鼠标的移动,点击,键盘的响应,窗口的关闭等等,以及摄像机与场景图形的事件回调(EventCallback)。 4)、执行updateTraversal函数,这个函数负责遍历所有的更新回(UpdateCallback); 除此之外,它的另一个重要任务就是负责更新DatabasePager与ImagePager这两个重要的分页数据处理组件。 5)、执行renderingTraversals函数,这里将使用较为复杂的线程处理方法,完成场景的筛 下面对viewerInit()这个函数进行解读。 它就是调用View: : init()函数。 View: : init函数中出现了两个重要的类成员变量: _eventQueue和_cameraManipulator,并且还将一个osgGA: : GUIEventAdapter的实例传入后者的初始化函数。 代码如下: osg: : ref_ptr : GUIEventAdapter>initEvent=_eventQueue->createEvent(); initEvent->setEventType(osgGA: : GUIEventAdapter: : FRAME); if(_cameraManipulator.valid()) { _cameraManipulator->init(*initEvent,*this); } _eventQueue是存储该视景器的事件队列。 OSG中代表事件的类是 osgGA: : GUIEventAdapter,它可以用于表达各种类型的鼠标、键盘、触压笔和窗口事件。 重写handle函数的方法,获取实时的鼠标/键盘输入,并进而实现相应的用户代码。 _cameraManipulator就是视景器中所用的场景漫游器的实例。 一般的情况下是通过setCameraManipulator来进行场景漫游器的设置,而如果要自定义相应的场景漫游器,我们通过覆写并使用osgGA: : MatrixManipulator: : init就可以灵活地初始化自定义漫游器的功能。 因此在viewerInit()函数中的调用关系如下图所示: osgViewer: : Viewer: : viewerInit函数调用osgViewer: : View: : init,在init函数中调用osgGA: : EventQueue: : createEvent来创建事件的列表,同时通过osgGA: : MatrixManipulator: : init来对场景的漫游器进行操作。 2015/12/30 1.加载矢量图 如何通过EarthFile文件创建地图。 EarthFile的核心作用
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- osgearth 学习 文档