序文
今回は3Dタイルデータを読み込む関数を書きます。
3D タイル データのドキュメント: CesiumGS/3d-tiles: 大規模な異種 3D 地理空間データセットのストリーミング仕様 (github.com)
同時に、読み込みが成功した後にタイルセットデータ セットを取得します (タイルセットを使用すると、後でモデル関連の操作を実行するのに便利です)。下の図は、モデルを読み込んだ後の効果を示しています。
達成
書き方1:
この書き方はPromise
、タイルセットをインスタンス化しCesium3DTileset
てからreadyPromise
タイルセットを返すことによって一致しますが、この書き方は CesiumJS 1.107 以降は非推奨になります。
/**
* @function addThreeDTiles
* @param {String} url - 模型切瓦后的瓦片索引文件URL或者Cesium Resource
* @param {Object} [option] - 选项对象(可选) https://cesium.com/learn/cesiumjs/ref-doc/Cesium3DTileset.html#.ConstructorOptions
*/
export function addThreeDTiles(url, option) {
// 开启地形深度检测:
// 控制在渲染场景时,相机是否进行深度测试以避免将被遮挡的物体绘制在前景
// true: 相机会根据地形高度信息进行深度测试,避免将低于地面的物体绘制在地面之上
viewer.scene.globe.depthTestAgainstTerrain = true
// ! 写法一:将在 1.107 版本后不支持,options.url和Cesium3DTileset.readyPromise将被移除
return new Promise(resolve => {
const tileset = new Cesium.Cesium3DTileset({
url // 模型切瓦后的瓦片索引文件地址或者Cesium Resource
})
tileset.readyPromise.then(() => {
viewer.scene.primitives.add(tileset)
})
resolve(tileset) // 返回模型对象
})
}
移行:
const modelPromise = addThreeDTiles('/model/Tileset/示例建筑/tileset.json') // 模型切瓦后的瓦片索引文件URL
const modelPromise2 = addThreeDTiles(Cesium.IonResource.fromAssetId(75343)) // Cesium Ion Resource
modelPromise.then(tileset=> {
console.log('tileset: ', tileset)
})
推奨事項: 書き方 2:
async/await
または を使用して次のことCesium3DTileset.fromUrl
をfromIonAssetId
実現します。
export async function addThreeDTiles(url, option) {
viewer.scene.globe.depthTestAgainstTerrain = true
// ! 写法二:
let tileset = {
}
if (typeof url == 'number') {
tileset = await Cesium.Cesium3DTileset.fromIonAssetId(url, option);
} else {
tileset = await Cesium.Cesium3DTileset.fromUrl(url, option);
}
viewer.scene.primitives.add(tileset);
return tileset // 返回模型对象
}
呼び出しメソッドは次のようになります。
const modelPromise = addThreeDTiles('/model/Tileset/示例建筑/tileset.json') // 模型切瓦后的瓦片索引文件URL
const modelPromise2 = addThreeDTiles(69380) // Cesium Ion Resource
modelPromise.then(tileset=> {
console.log('tileset: ', tileset)
})
オプション
上記のカプセル化された関数を通じて 3D タイル タイル セットをロードする場合、オプションを に渡すことができ、オプションは Cesium3Dtileset を初期化するときの構成アイテム オブジェクトです。中国語のドキュメントを参照してください: Cesium3Dtileset - Cesium Documentation
タイルセットを削除する
viewer.scene.primitives.remove(tileset);
コード
コード提出リファレンス:
feat: 3D タイルの追加 · c3759ef · ReBeX/cesium-tyro-blog - Gitee.com
修正: 3D タイルの読み込み方法の最適化 · ff20c46 · ReBeX/cesium-tyro-blog - Gitee.com
/*
* @Date: 2023-05-23 10:45:33
* @LastEditors: ReBeX [email protected]
* @LastEditTime: 2023-06-14 23:24:54
* @FilePath: \cesium-tyro-blog\src\utils\ThreeDTiles\loadTileset.js
* @Description: 从给定 URL 加载 3D 模型,添加到场景中,并自动定位到模型所在位置
* import { addThreeDTiles } from '@/utils/ThreeDTiles/loadTileset.js'
* const modelPromise = addThreeDTiles('/model/Tileset/示例建筑/tileset.json')
* const modelPromise = addThreeDTiles(69380)
* modelPromise.then(model => {
* console.log('tileset: ', model)
* })
*/
import {
viewer } from '@/utils/createCesium.js' // 引入地图对象
import * as Cesium from 'cesium'
/**
* @function addThreeDTiles
* @param {String} url - 模型切瓦后的瓦片索引文件URL或者Cesium Resource
* @param {Object} [option] - 选项对象(可选) https://cesium.com/learn/cesiumjs/ref-doc/Cesium3DTileset.html#.ConstructorOptions
*/
const tilesetOption = {
skipLevelOfDetail: true,
baseScreenSpaceError: 1024,
skipScreenSpaceErrorFactor: 16,
skipLevels: 1,
immediatelyLoadDesiredLevelOfDetail: false,
loadSiblings: false,
cullWithChildrenBounds: true
}
export async function addThreeDTiles(url, option) {
// 开启地形深度检测:
// 控制在渲染场景时,相机是否进行深度测试以避免将被遮挡的物体绘制在前景
// true: 相机会根据地形高度信息进行深度测试,避免将低于地面的物体绘制在地面之上
viewer.scene.globe.depthTestAgainstTerrain = true
/*
// ! 写法一:将在 1.107 版本后不支持,options.url和Cesium3DTileset.readyPromise将被移除
return new Promise(resolve => { // 返回 Promise 对象
const tileset = new Cesium.Cesium3DTileset({
url // 模型切瓦后的瓦片索引文件地址或者Cesium Resource: Cesium.IonResource.fromAssetId(75343)
})
tileset.readyPromise.then(() => {
viewer.scene.primitives.add(tileset)
})
resolve(tileset) // 返回模型对象
})
*/
// ! 写法二:
let tileset = {
}
if (typeof url == 'number') {
tileset = await Cesium.Cesium3DTileset.fromIonAssetId(url, option);
} else {
tileset = await Cesium.Cesium3DTileset.fromUrl(url, option);
}
viewer.scene.primitives.add(tileset);
// 定位到模型
viewer.zoomTo(
tileset,
new Cesium.HeadingPitchRange(
0.0,
-0.5,
tileset.boundingSphere.radius * 2.0 // 模型的包围球半径的2倍
)
)
return tileset // 返回模型对象
}