您的位置:首页 > 其它

添加场景(模型)到三维空间

2017-07-21 16:13 477 查看

基本思想

将模型添加到三维空间中,即确定其在三维空间中的位置和姿态,我们只需要确定其在世界坐标系中的位置(position)和其在三维空间中的姿态(orientation即可)

一些基本概念可以参考我上一篇博客

三维空间中视角位置和物体取向的确定

gltf

glTF的全称是GL传输格式,是一种针对GL(WebGL,OpenGL ES以及OpenGL)接口的运行时资产(asset)。在3D内容的传输和加载中,glTF通过提供一种高效,易扩展,可协作的格式,填补了3D建模工具和现代GL应用之间的空白。



上图是glTF的一个大概结构,分为四大块,最上面的json是一个表述,描述该模型的节点层级,材质,相机,动画等相关逻辑结构,bin则对应这些对象的具体数据信息,glsl是对该模型渲染的着色器,针对该模型的数据信息,给出渲染“配方”,当然还有纹理内容。大块内容可以以Base64的编码内迁到文件中,方便拷贝和加载,也可以以URI的外链方式,侧重重用性。

Cesium代码

我们首先来定义一些后面所需要的基本信息:

定义Viewer

var viewer = new Cesium.Viewer("cesiumContainer", {
baseLayerPicker: false,
fullscreenButton: false,//全屏按钮
animation: false,//旋转动画按钮
homeButton: false,//回到起始位置
timeline: false,//时间轴
infoBox: false,//
sceneModePicker: false,//二维三维切换窗口
navigationHelpButton: false,//操作说明按钮
geocoder: false,//搜索按钮
selectionIndicator: false,
imageryProvider: new Cesium.UrlTemplateImageryProvider({
url: 'http://mt2.google.cn/vt/lyrs=y@258000000&hl=zh-CN&gl=CN&src=app&x={x}&y={y}&z={z}',
})
});


定义视角位置信息

即我们要视角到达的位置信息和角度

var positionInfo = {
dx:0.95358471687396,
dy:-0.024796469102366,
dz:0.300102187370346,
px:-2861112.79235033,
py:4653758.12525882,
pz:3284567.63829926,
ux:-0.178653710223323,
uy:0.755669174306541,
uz:0.630116616846685
}


定义模型的基本信息

var models =[
{
lat:31.2401294,
lon: 121.5044358,
modelid:34,
modelname:'上海中银大厦',
url:'models/zip上海中银大厦1500522738911/shanghaizhongxindaxia/models/shanghaizhongxindaxia.gltf',
heading:0,
pitch:0,
roll:0,
alt:0
},
{
lat:31.23365548207231,
lon: 121.49975263472346,
modelid:31,
modelname:'花旗集团大厦',
url:'models/ziphuaqijituandaxia1499828901567/huaqijituandaxia/models/huaqijituandaxia.gltf',
heading:0,
pitch:0,
roll:0,
alt:0
}
]


一个场景可能由很多模型组成,所以我们的视角一定要综合考虑所有模型的位置:

变换相机视角

viewer.camera.flyTo({
destination : new Cesium.Cartesian3(positionInfo.px, positionInfo.py, positionInfo.pz),
orientation: {
direction: new Cesium.Cartesian3(positionInfo.dx, positionInfo.dy, positionInfo.dz),
up: new Cesium.Cartesian3(positionInfo.ux, positionInfo.uy, positionInfo.uz)
}
});


加载glTF的过程,提供两种方式,一种是以Entity的方式,一种是以Primitive的方式,消费数码相机(前者)和单反相机(后者)的差别。

entity方式

for (i = 0; i < models.length; i++) {

position = Cesium.Cartesian3.fromDegrees(models[i].lon, models[i].lat, models[i].alt);

hpr = new Cesium.HeadingPitchRoll(
Cesium.Math.toRadians(models[i].heading),
Cesium.Math.toRadians(models[i].pitch),
Cesium.Math.toRadians(models[i].roll));
var orientation = Cesium.Transforms.headingPitchRollQuaternion(position, hpr);

var entity = viewer.entities.add({
name : models[i].modelname,
position : position,
orientation : orientation,
model : {
uri : models[i].url,
minimumPixelSize : 128,
maximumScale : 20000
}
});

}


primitives方式

for (i = 0; i < models.length; i++) {
hpr = new Cesium.HeadingPitchRoll(
Cesium.Math.toRadians(models[i].heading),
Cesium.Math.toRadians(models[i].pitch),
Cesium.Math.toRadians(models[i].roll));

var currentModel = Cesium.Model.fromGltf({
url: models[i].url,
modelMatrix: Cesium.Transforms.headingPitchRollToFixedFrame(position, hpr, Cesium.Ellipsoid.WGS84, fixedFrameTransform),
minimumPixelSize: 128
});
viewer.scene.primitives.add(currentModel);
}


内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  三维 webgl Cesium