|
@@ -7,7 +7,15 @@ import { KTX2Loader } from '../loaders/KTX2Loader.js';
|
|
|
import MeshBasicMaterial from '../../../src/custom/materials/BasicMaterial.js' // xzw改 原先MeshBasicMaterial贴图发黑,可能和贴图有关
|
|
|
|
|
|
let globalThis = window //add 有的app没有globalThis. 2023.1
|
|
|
+
|
|
|
+let rtcCenterGlobal = false//默认false,也就是scale.z要乘以-1
|
|
|
+
|
|
|
+
|
|
|
/*! *****************************************************************************
|
|
|
+
|
|
|
+github: https://github.com/nytimes/three-loader-3dtiles
|
|
|
+
|
|
|
+
|
|
|
Copyright (c) Microsoft Corporation.
|
|
|
|
|
|
Permission to use, copy, modify, and/or distribute this software for any
|
|
@@ -22,13 +30,13 @@ OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
|
|
|
PERFORMANCE OF THIS SOFTWARE.
|
|
|
***************************************************************************** */
|
|
|
|
|
|
-
|
|
|
+
|
|
|
let visiVertexCount = 0
|
|
|
let visiGeoCount = 0
|
|
|
const maxVertexVisi = 5e6
|
|
|
const maxTexVisi = 500
|
|
|
|
|
|
-
|
|
|
+const maxDepth = 100
|
|
|
|
|
|
function getGpuMemoryUsage(win = window){//总的
|
|
|
let c = 0
|
|
@@ -7777,7 +7785,7 @@ class OrientedBoundingBox {
|
|
|
|
|
|
getBoundingSphere(result = new BoundingSphere()) {
|
|
|
const halfAxes = this.halfAxes;
|
|
|
- const u = halfAxes.getColumn(0, scratchVectorU);
|
|
|
+ const u = halfAxes.getColumn(0, scratchVectorU);//前三个
|
|
|
const v = halfAxes.getColumn(1, scratchVectorV);
|
|
|
const w = halfAxes.getColumn(2, scratchVectorW);
|
|
|
const cornerVector = scratchVector3.copy(u).add(v).add(w);
|
|
@@ -7808,8 +7816,51 @@ class OrientedBoundingBox {
|
|
|
distanceTo(point) {
|
|
|
return Math.sqrt(this.distanceSquaredTo(point));
|
|
|
}
|
|
|
+ /* distanceSquaredTo(point) {//相机到bound外壳的距离平方
|
|
|
+
|
|
|
+ let center = this.center.clone()
|
|
|
+ center.z *= -1
|
|
|
+
|
|
|
+ const offset = scratchOffset.from(point).subtract(center);
|
|
|
+ const halfAxes = this.halfAxes;
|
|
|
+ const u = halfAxes.getColumn(0, scratchVectorU);
|
|
|
+ const v = halfAxes.getColumn(1, scratchVectorV);
|
|
|
+ const w = halfAxes.getColumn(2, scratchVectorW);
|
|
|
+
|
|
|
+
|
|
|
+ u.z *= -1
|
|
|
+ v.z *= -1
|
|
|
+ w.z *= -1
|
|
|
+
|
|
|
+ const uHalf = u.magnitude();
|
|
|
+ const vHalf = v.magnitude();
|
|
|
+ const wHalf = w.magnitude();
|
|
|
+ u.normalize();
|
|
|
+ v.normalize();
|
|
|
+ w.normalize();
|
|
|
+ let distanceSquared = 0.0;
|
|
|
+ let d;
|
|
|
+ d = Math.abs(offset.dot(u)) - uHalf;
|
|
|
|
|
|
- distanceSquaredTo(point) {
|
|
|
+ if (d > 0) {
|
|
|
+ distanceSquared += d * d;
|
|
|
+ }
|
|
|
+
|
|
|
+ d = Math.abs(offset.dot(v)) - vHalf;
|
|
|
+
|
|
|
+ if (d > 0) {
|
|
|
+ distanceSquared += d * d;
|
|
|
+ }
|
|
|
+
|
|
|
+ d = Math.abs(offset.dot(w)) - wHalf;
|
|
|
+
|
|
|
+ if (d > 0) {
|
|
|
+ distanceSquared += d * d;
|
|
|
+ }
|
|
|
+
|
|
|
+ return distanceSquared;
|
|
|
+ } */
|
|
|
+ distanceSquaredTo(point) {//相机到bound外壳的距离平方
|
|
|
const offset = scratchOffset.from(point).subtract(this.center);
|
|
|
const halfAxes = this.halfAxes;
|
|
|
const u = halfAxes.getColumn(0, scratchVectorU);
|
|
@@ -7842,7 +7893,7 @@ class OrientedBoundingBox {
|
|
|
}
|
|
|
|
|
|
return distanceSquared;
|
|
|
- }
|
|
|
+ }
|
|
|
|
|
|
computePlaneDistances(position, direction, result = [-0, -0]) {
|
|
|
let minDist = Number.POSITIVE_INFINITY;
|
|
@@ -8529,8 +8580,11 @@ function createBox(box, transform, result) {
|
|
|
const xAxis = transform.transformAsVector(origin.slice(0, 3));
|
|
|
const yAxis = transform.transformAsVector(origin.slice(3, 6));
|
|
|
const zAxis = transform.transformAsVector(origin.slice(6, 9));
|
|
|
- const halfAxes = new Matrix3([xAxis[0], xAxis[1], xAxis[2], yAxis[0], yAxis[1], yAxis[2], zAxis[0], zAxis[1], zAxis[2]]);
|
|
|
-
|
|
|
+ const halfAxes = new Matrix3([xAxis[0], xAxis[1], xAxis[2], yAxis[0], yAxis[1], yAxis[2], zAxis[0], zAxis[1], zAxis[2]]);
|
|
|
+ //const halfAxes = new Matrix3([xAxis[0], xAxis[1], -xAxis[2], yAxis[0], yAxis[1], -yAxis[2], zAxis[0], zAxis[1], -zAxis[2]]);//改
|
|
|
+ //center.z *= -1//add
|
|
|
+
|
|
|
+
|
|
|
if (defined$3(result)) {
|
|
|
result.center = center;
|
|
|
result.halfAxes = halfAxes;
|
|
@@ -8862,7 +8916,7 @@ class TilesetTraverser {
|
|
|
|
|
|
|
|
|
// !zeg改 循环遍历子tile, maxDepth用来限制可加载的最大深度
|
|
|
- if (this.canTraverse(tile, frameState) && tile.depth < this.options.maxDepth) {//add maxDepth
|
|
|
+ if (this.canTraverse(tile, frameState) && (tile.depth < /* this.options. */maxDepth || tile.type != 'scenegraph' )) {//add maxDepth 是否继续遍历子集
|
|
|
this.updateChildTiles(tile, frameState);
|
|
|
shouldRefine = this.updateAndPushChildren(tile, frameState, stack, tile.hasRenderContent ? tile._selectionDepth + 1 : tile._selectionDepth);
|
|
|
}
|
|
@@ -9187,10 +9241,19 @@ class TileHeader {
|
|
|
_defineProperty(this, "_initialTransform", void 0);
|
|
|
|
|
|
_defineProperty(this, "tilesetMatrix", void 0);//add
|
|
|
+
|
|
|
+ _defineProperty(this, "tileContent", void 0);//add
|
|
|
|
|
|
-
|
|
|
-
|
|
|
-
|
|
|
+ _defineProperty(this, "contentTransform", void 0);//add
|
|
|
+
|
|
|
+ _defineProperty(this, "volumeBox", void 0);//add
|
|
|
+
|
|
|
+ _defineProperty(this, "boundUntransformed", void 0);//add
|
|
|
+
|
|
|
+ _defineProperty(this, "rtcCenterState", rtcCenterGlobal);//add 初始时的状态,当mesh加载完检查下
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
this.header = header;
|
|
|
this.tileset = tileset;
|
|
|
this.id = extendedId || header.id;
|
|
@@ -9369,7 +9432,7 @@ class TileHeader {
|
|
|
}
|
|
|
|
|
|
try {
|
|
|
- const contentUrl = this.tileset.getTileUrl(this.contentUrl);
|
|
|
+ const contentUrl = this.tileset.getTileUrl(this.contentUrl)+ `?_=${this.tileset.options.updateTime}` // !zeg改 添加version后缀 原:imageVersion
|
|
|
const loader = this.tileset.loader;
|
|
|
const options = { ...this.tileset.loadOptions,
|
|
|
[loader.id]: { ...this.tileset.loadOptions[loader.id],
|
|
@@ -9380,7 +9443,7 @@ class TileHeader {
|
|
|
this.content = await load(contentUrl, loader, options);
|
|
|
|
|
|
// !zeg改
|
|
|
- if (this.tileset.options.maxDepth < this.depth) {
|
|
|
+ if (/* this.tileset.options. */maxDepth < this.depth && this.type == 'scenegraph') {//有的场景depth为1的不是mesh,只是json,即实际最低depth>1
|
|
|
this.unloadContent()
|
|
|
return false
|
|
|
}
|
|
@@ -9581,13 +9644,21 @@ class TileHeader {
|
|
|
}
|
|
|
|
|
|
_updateBoundingVolume(header) {
|
|
|
-
|
|
|
- let computedTransform = new Matrix4(this.tileset.modelMatrix).multiplyRight(this.computedTransform); //add
|
|
|
- //console.log('_updateBoundingVolume computedTransform', this.tileset.modelMatrix, computedTransform)
|
|
|
-
|
|
|
+ let computedTransform
|
|
|
+ if(header.id == 'root_0' || !header.id){
|
|
|
+ console.log('root_0')
|
|
|
+ }
|
|
|
+ if(!this.tileset.lastRootTransform){//没事过后会因_updateTransform重算
|
|
|
+ computedTransform = new Matrix4(this.tileset.modelMatrix).multiplyRight(this.computedTransform); //add
|
|
|
+ }else{
|
|
|
+ computedTransform = new Matrix4(new Matrix4$1().multiplyMatrices(this.tileset.lastRootTransform, this.getContentTransform()).elements)
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
this.boundingVolume = createBoundingVolume(header.boundingVolume, computedTransform/* this.computedTransform */, this.boundingVolume);
|
|
|
const content = header.content;
|
|
|
-
|
|
|
+
|
|
|
+
|
|
|
if (!content) {
|
|
|
return;
|
|
|
}
|
|
@@ -9600,6 +9671,57 @@ class TileHeader {
|
|
|
this._viewerRequestVolume = createBoundingVolume(header.viewerRequestVolume, computedTransform, this._viewerRequestVolume);
|
|
|
}
|
|
|
}
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+ getBoundUntransformed(){//add 这个会在mesh加载好后才会执行
|
|
|
+ if(!this.contentTransform){
|
|
|
+ console.error('?')
|
|
|
+ }
|
|
|
+ this.getContentTransform()
|
|
|
+
|
|
|
+ let computedTransform2 = new Matrix4(this.contentTransform.elements)
|
|
|
+
|
|
|
+ this.boundUntransformed = createBoundingVolume(this.header.boundingVolume, computedTransform2 , this.boundUntransformed);//add
|
|
|
+
|
|
|
+ return this.boundUntransformed
|
|
|
+
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+ getContentTransform(force){ //add 获取该tile在创建boundingVolume时需要的matrix,不包含最外层对整体模型的变换.
|
|
|
+ let rtcCenter, contentTransform
|
|
|
+ if(this.contentTransform && !force){//无需更新
|
|
|
+ return this.contentTransform.clone()
|
|
|
+ }
|
|
|
+
|
|
|
+ if(!this.tileset.tileTransInvert){
|
|
|
+ this.tileset.tileTransInvert = new Matrix4()
|
|
|
+ }
|
|
|
+
|
|
|
+ this.contentTransform = new Matrix4$1().fromArray(this.computedTransform).premultiply(new Matrix4$1().fromArray(this.tileset.tileTransInvert))
|
|
|
+
|
|
|
+ if(this.tileContent){
|
|
|
+ rtcCenter = this.content.rtcCenter
|
|
|
+ }else{
|
|
|
+ rtcCenter = this.rtcCenterState
|
|
|
+ }
|
|
|
+
|
|
|
+ if(!rtcCenter) {
|
|
|
+ let tranM = new Matrix4$1()
|
|
|
+ tranM.makeScale(1,1,-1)//大部分是这种情况. 就是因为这个变换才加的这个函数,之前bounding没考虑这个不准。不知道为什么原生的代码不用scaleZ
|
|
|
+ this.contentTransform.premultiply(tranM)
|
|
|
+ }
|
|
|
+ //如果有rtcCenter的话一开始boundingVolume不准?会不会有显示问题?
|
|
|
+
|
|
|
+ return this.contentTransform.clone()
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
|
|
|
_updateTransform(parentTransform = new Matrix4()) {
|
|
|
const computedTransform = parentTransform.clone().multiplyRight(this.transform);
|
|
@@ -10269,7 +10391,7 @@ class Tileset3D extends EventDispatcher{//xzw add EventDispatcher
|
|
|
const children = tile.header.children || [];
|
|
|
|
|
|
// !zeg改
|
|
|
- if(tile.depth < this.options.maxDepth){
|
|
|
+ if(tile.depth < /* this.options. */maxDepth){
|
|
|
for (const childHeader of children) {
|
|
|
const childTile = new TileHeader(this, childHeader, tile);
|
|
|
tile.children.push(childTile);
|
|
@@ -10277,7 +10399,7 @@ class Tileset3D extends EventDispatcher{//xzw add EventDispatcher
|
|
|
stack.push(childTile);
|
|
|
}
|
|
|
}
|
|
|
- window.maxDepth = Math.max(window.maxDepth||0,tile.depth)
|
|
|
+ window.maxTileDepth = Math.max(window.maxTileDepth||0, tile.depth)
|
|
|
}
|
|
|
}
|
|
|
|
|
@@ -15852,6 +15974,7 @@ async function parseGLTF(gltf, arrayBufferOrString, byteOffset = 0, options, con
|
|
|
const promise = decodeExtensions(gltf, options, context);
|
|
|
promises.push(promise);
|
|
|
await Promise.all(promises);
|
|
|
+ gltf.json.gltfArrayBuffer = arrayBufferOrString // !zeg add 兼容gltf
|
|
|
return options !== null && options !== void 0 && (_options$gltf4 = options.gltf) !== null && _options$gltf4 !== void 0 && _options$gltf4.postProcess ? postProcessGLTF(gltf, options) : gltf;
|
|
|
}
|
|
|
|
|
@@ -16996,37 +17119,69 @@ function loadersPlaneToMesh(plane) {
|
|
|
}
|
|
|
function loadersBoundingBoxToMesh(tile) {
|
|
|
// Create a basic rectangle geometry from math.gl half-axes
|
|
|
- const { boundingVolume } = tile;
|
|
|
- let redColor = 0;
|
|
|
+
|
|
|
+
|
|
|
+ const boundUntransformed = tile.type == 'empty' ? tile.boundingVolume : tile.getBoundUntransformed() //empty时没创建好,直接给boundingVolume一样
|
|
|
+
|
|
|
+ /* let redColor = 0;
|
|
|
if (tile.content) {
|
|
|
//redColor = Math.min((tile.content.byteLength != void 0 ? tile.content.byteLength : 0) / 500000, 1.0);
|
|
|
redColor = Math.min( tile.depth / 10 , 1.0); //改
|
|
|
- }
|
|
|
-
|
|
|
+ } */
|
|
|
+ let hue = 0
|
|
|
+ if(tile.content){
|
|
|
+ hue = Math.min( tile.depth / 10 , 1.0); //改
|
|
|
+ }
|
|
|
|
|
|
-
|
|
|
- const boxColor = new Color(redColor, 1.0, 0.0);
|
|
|
+ const boxColor = new THREE.Color().setHSL(hue, 0.9, 0.85)
|
|
|
+ //const boxColor = new Color(redColor, 1.0, 0.0);
|
|
|
const boxGeometry = new BoxGeometry(1, 1, 1);
|
|
|
const boxTransform = new Matrix4$1();
|
|
|
- if (boundingVolume.halfAxes) {
|
|
|
- boxTransform.copy(getMatrix4FromHalfAxes(boundingVolume.halfAxes));
|
|
|
+ if (boundUntransformed.halfAxes) {
|
|
|
+ boxTransform.copy(getMatrix4FromHalfAxes(boundUntransformed.halfAxes));
|
|
|
}
|
|
|
- else if (boundingVolume.radius) {
|
|
|
- boxGeometry.scale(boundingVolume.radius * 2, boundingVolume.radius * 2, boundingVolume.radius * 2);
|
|
|
+ else if (boundUntransformed.radius) {
|
|
|
+ boxGeometry.scale(boundUntransformed.radius * 2, boundUntransformed.radius * 2, boundUntransformed.radius * 2);
|
|
|
}
|
|
|
|
|
|
- boxTransform.premultiply((new Matrix4$1()).setPosition(...boundingVolume.center)) //add
|
|
|
-
|
|
|
+ boxTransform.premultiply((new Matrix4$1()).setPosition(...boundUntransformed.center)) //add
|
|
|
|
|
|
+ /* if(tile.type != "empty"){ //root单独处理了
|
|
|
+ boxTransform.premultiply((new Matrix4$1()).makeScale(1,1,-1))//xzw 因为mesh倒转了所以box也
|
|
|
+ }else{
|
|
|
+ console.log('empty')
|
|
|
+ } */
|
|
|
boxGeometry.applyMatrix4(boxTransform);
|
|
|
-
|
|
|
-
|
|
|
const edges = new EdgesGeometry(boxGeometry);
|
|
|
const dispPlane = new LineSegments(edges, new LineBasicMaterial({ color: boxColor, transparent:true }));
|
|
|
//dispPlane.position.copy(new Vector3$1(...boundingVolume.center));
|
|
|
dispPlane.matrixAutoUpdate = false //add
|
|
|
+ let label = new Potree.TextSprite({
|
|
|
+ mat: new THREE.MeshBasicMaterial({transparent:true }), //depthTest:false会导致经常显示不出
|
|
|
+ backgroundColor: {r: 0, g: 0, b: 0, a:0.1},
|
|
|
+ textColor: {r: boxColor.r*255, g: boxColor.g*255, b: boxColor.b*255, a:0.9},
|
|
|
+ fontsize:100,
|
|
|
+ //useDepth : true ,
|
|
|
+ renderOrder : 5,
|
|
|
+ text: tile.id.split('/').pop().split('.b3dm')[0], //Tile_+094_-010.b3dm'
|
|
|
+ name:'tile'
|
|
|
+ })
|
|
|
+ label.addEventListener('mouseover',()=>{
|
|
|
+ if(label.sprite.material.opacity < 1)return
|
|
|
+ window.hoverTile = tile
|
|
|
+ console.log('hoverLabel',tile.id, tile._distanceToCamera)
|
|
|
+ })
|
|
|
+ /* let s = 0.6
|
|
|
+ label.scale.set(s,s,s) */
|
|
|
+ let s = tile.tileset.options.maximumScreenSpaceError / 400
|
|
|
+ label.scale.set(s,s,s)
|
|
|
|
|
|
|
|
|
+ dispPlane.add(label)
|
|
|
+
|
|
|
+ label.position.set(...boundUntransformed.center)
|
|
|
+ //label.position.z *= -1
|
|
|
+
|
|
|
/* if(tile.content.byteLength == void 0){
|
|
|
let oldUpdate = dispPlane.updateMatrixWorld.bind(dispPlane)
|
|
|
dispPlane.updateMatrixWorld = (a,b)=>{
|
|
@@ -17041,7 +17196,7 @@ function loadersBoundingBoxToMesh(tile) {
|
|
|
} */
|
|
|
|
|
|
|
|
|
-
|
|
|
+ tile.volumeBox = dispPlane
|
|
|
return dispPlane;
|
|
|
}
|
|
|
function getMatrix4FromHalfAxes(halfAxes) {
|
|
@@ -17416,7 +17571,8 @@ class Loader3DTiles {
|
|
|
updateTransforms: options.updateTransforms,
|
|
|
throttleRequests: options.throttleRequests,
|
|
|
maxRequests: options.maxRequests,
|
|
|
- maxDepth: options.maxDepth || 50, // !zeg改
|
|
|
+ updateTime: options.updateTime || 0, //add
|
|
|
+ //maxDepth: options.maxDepth || 50, // !zeg改
|
|
|
contentLoader: (tile) => __awaiter(this, void 0, void 0, function* () {
|
|
|
let tileContent = null;
|
|
|
switch (tile.type) {
|
|
@@ -17431,8 +17587,9 @@ class Loader3DTiles {
|
|
|
}
|
|
|
}
|
|
|
if (tileContent) {
|
|
|
- tileContent.visible = false;
|
|
|
+ tileContent.visible = false;
|
|
|
renderMap[tile.id] = tileContent;
|
|
|
+ tileContent.name = tile.id //add
|
|
|
root.add(renderMap[tile.id]);
|
|
|
if (options.debug) {
|
|
|
const box = loadersBoundingBoxToMesh(tile);
|
|
@@ -17466,10 +17623,10 @@ class Loader3DTiles {
|
|
|
}, '3d-tiles': {
|
|
|
loadGLTF: false
|
|
|
} }) }));
|
|
|
- //
|
|
|
+ tileset.boxMap = boxMap //add
|
|
|
// transformations
|
|
|
const threeMat = new Matrix4$1();
|
|
|
- const tileTrasnform = new Matrix4$1();
|
|
|
+ const tileTransform = new Matrix4$1();
|
|
|
const rootCenter = new Vector3$1();
|
|
|
let orientationDetected = false;
|
|
|
if (tileset.root.boundingVolume) {
|
|
@@ -17479,7 +17636,7 @@ class Loader3DTiles {
|
|
|
console.warn("Cannot apply a model matrix to bounding volumes of type region. Tileset stays in original geo-coordinates.");
|
|
|
options.geoTransform = GeoTransform.WGS84Cartesian;
|
|
|
}
|
|
|
- tileTrasnform.setPosition(tileset.root.boundingVolume.center[0], tileset.root.boundingVolume.center[1], tileset.root.boundingVolume.center[2]);
|
|
|
+ tileTransform.setPosition(tileset.root.boundingVolume.center[0], tileset.root.boundingVolume.center[1], tileset.root.boundingVolume.center[2]);
|
|
|
}
|
|
|
else {
|
|
|
console.warn("Bounding volume not found, no transformations applied");
|
|
@@ -17505,6 +17662,10 @@ class Loader3DTiles {
|
|
|
root.updateMatrixWorld(true);
|
|
|
const lastRootTransform = new Matrix4$1().copy(root.matrixWorld);
|
|
|
const rootTransformInverse = new Matrix4$1().copy(lastRootTransform).invert();
|
|
|
+ tileset.lastRootTransform = lastRootTransform //add
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
detectOrientation(tileset.root);
|
|
|
updateResetTransform();
|
|
|
if (options.debug) {
|
|
@@ -17519,7 +17680,7 @@ class Loader3DTiles {
|
|
|
root.updateMatrixWorld(true);
|
|
|
}
|
|
|
else if (options.geoTransform == GeoTransform.WGS84Cartesian) {
|
|
|
- root.applyMatrix4(tileTrasnform);
|
|
|
+ root.applyMatrix4(tileTransform);
|
|
|
root.updateMatrixWorld(true);
|
|
|
rootCenter.copy(root.position);
|
|
|
}
|
|
@@ -17534,20 +17695,24 @@ class Loader3DTiles {
|
|
|
const rotation = new Euler().setFromRotationMatrix(orientationMatrix);
|
|
|
if (!rotation.equals(new Euler())) {
|
|
|
orientationDetected = true;
|
|
|
- const pos = new Vector3$1(tileTrasnform.elements[12], tileTrasnform.elements[13], tileTrasnform.elements[14]);
|
|
|
- tileTrasnform.extractRotation(orientationMatrix);
|
|
|
- tileTrasnform.setPosition(pos);
|
|
|
+ const pos = new Vector3$1(tileTransform.elements[12], tileTransform.elements[13], tileTransform.elements[14]);
|
|
|
+ tileTransform.extractRotation(orientationMatrix);
|
|
|
+ tileTransform.setPosition(pos);
|
|
|
updateResetTransform();
|
|
|
}
|
|
|
}
|
|
|
function updateResetTransform() {
|
|
|
if (options.geoTransform != GeoTransform.WGS84Cartesian) {
|
|
|
// Reset the current model matrix and apply our own transformation
|
|
|
- threeMat.copy(tileTrasnform).invert();
|
|
|
- threeMat.premultiply(lastRootTransform);
|
|
|
- threeMat.copy(lastRootTransform).multiply(new Matrix4$1().copy(tileTrasnform).invert());
|
|
|
+ //threeMat.copy(tileTransform).invert();
|
|
|
+ //threeMat.premultiply(lastRootTransform); //xzw删 被下面copy这句覆盖了
|
|
|
+ let tileTransInvert = new Matrix4$1().copy(tileTransform).invert()
|
|
|
+ threeMat.copy(lastRootTransform).multiply(tileTransInvert);
|
|
|
tileset.modelMatrix = new Matrix4(threeMat.toArray());
|
|
|
//console.log('update tileset ModelMatrix', tileset.modelMatrix.elements)
|
|
|
+
|
|
|
+ tileset.tileTransInvert = tileTransInvert.toArray() // add for volumebox
|
|
|
+
|
|
|
}
|
|
|
}
|
|
|
// 更新瓦片显隐和瓦片迭代更新
|
|
@@ -17605,7 +17770,7 @@ class Loader3DTiles {
|
|
|
if(visiVertexCount<maxVertexVisi){
|
|
|
renderMap[tile.id].visible = true;
|
|
|
visiVertexCount += renderMap[tile.id].vertexCount //xzw add
|
|
|
- options.debug && (boxMap[tile.id].material.opacity = 1)
|
|
|
+ options.debug && (boxMap[tile.id].material.opacity = 1 , boxMap[tile.id].children[0].sprite.material.opacity = 1 )
|
|
|
}else{
|
|
|
//console.log('超出', visiVertexCount)
|
|
|
}
|
|
@@ -17620,7 +17785,7 @@ class Loader3DTiles {
|
|
|
if (renderMap[tile.id]) {
|
|
|
if(renderMap[tile.id].visible){
|
|
|
renderMap[tile.id].visible = false;
|
|
|
- options.debug && (boxMap[tile.id].material.opacity = 0.1)
|
|
|
+ options.debug && (boxMap[tile.id].material.opacity = 0.1, boxMap[tile.id].children[0].sprite.material.opacity = 0.1)
|
|
|
|
|
|
visiVertexCount -= renderMap[tile.id].vertexCount //xzw add
|
|
|
}
|
|
@@ -17809,12 +17974,27 @@ class Loader3DTiles {
|
|
|
dracoLoader.dispose();
|
|
|
}
|
|
|
},
|
|
|
+ limit2lowestDepth: isLowest => {//zeg add 设置是否限制为最低精度tile深度
|
|
|
+
|
|
|
+ maxDepth = isLowest ? 1 : 100 //影响到shouldRefine, 检查方法:可以看到当maxDepth降低了之后viewer.objs.children[0].runtime.getTileset().tiles.filter(e=> e.tileContent.visible)变少
|
|
|
+
|
|
|
+ if (cameraReference) {
|
|
|
+ tileset._frameNumber++
|
|
|
+ tilesetUpdate(tileset, renderMap, rendererReference, cameraReference)
|
|
|
+ }
|
|
|
+ },
|
|
|
},
|
|
|
|
|
|
};
|
|
|
});
|
|
|
}
|
|
|
}
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
function createGLTFNodes(gltfLoader, tile, unlitMaterial, options, rootTransformInverse) {
|
|
|
|
|
|
return __awaiter(this, void 0, void 0, function* () {
|
|
@@ -17824,24 +18004,52 @@ function createGLTFNodes(gltfLoader, tile, unlitMaterial, options, rootTransform
|
|
|
const shouldRotate = ((_a = tile.tileset.asset) === null || _a === void 0 ? void 0 : _a.gltfUpAxis) !== "Z";
|
|
|
// The computed trasnform already contains the root's transform, so we have to invert it
|
|
|
//const contentTransform = new Matrix4$1().fromArray(tile.computedTransform).premultiply(tileMatrix)//.premultiply(rootTransformInverse); //xzw 删。原先的会造成移动后tiles错乱
|
|
|
- const contentTransform = new Matrix4$1().fromArray(tile.computedTransform).premultiply(tile.tileset.modelMatrix).premultiply(rootTransformInverse)
|
|
|
- // 这句同tile.computedTransform左乘tileTrasnform。 因为tileTrasnform拿不到所以使用modelMatrix。modelMatrix为tileTrasnform左乘rootTransform, 所以再左乘rootTransformInverse
|
|
|
-
|
|
|
-
|
|
|
+ //const contentTransform = new Matrix4$1().fromArray(tile.computedTransform).premultiply(tile.tileset.modelMatrix).premultiply(rootTransformInverse)
|
|
|
+
|
|
|
+ // 这句同tile.computedTransform左乘tileTransform。 因为tileTransform拿不到所以使用modelMatrix。modelMatrix为tileTransform左乘rootTransform, 所以再左乘rootTransformInverse
|
|
|
+
|
|
|
//改动:contentTransform中的computedTransform 去掉左乘 root.modelMatrixWorld , 因为移动过后这个computedTransform没更新
|
|
|
|
|
|
-
|
|
|
-
|
|
|
- if (shouldRotate) {
|
|
|
- contentTransform.multiply(rotateX); // convert from GLTF Y-up to Z-up
|
|
|
- }
|
|
|
+
|
|
|
gltfLoader.parse(
|
|
|
tile.content.type == 'glTF' ? tile.content.gltf.gltfArrayBuffer : tile.content.gltfArrayBuffer,//tile.content.gltfArrayBuffer,
|
|
|
tile.contentUrl ? tile.contentUrl.substr(0, tile.contentUrl.lastIndexOf('/') + 1) : '',
|
|
|
(gltf) => {
|
|
|
- const tileContent = gltf.scenes[0];
|
|
|
- //tileContent.applyMatrix4(contentTransform);
|
|
|
+ const tileContent = gltf.scenes[0];
|
|
|
tileContent.vertexCount = 0 //xzw add
|
|
|
+ tile.tileContent = tileContent //xzw add
|
|
|
+
|
|
|
+ let needUpdate
|
|
|
+ if(tile.rtcCenterState != !!tile.content.rtcCenter){ // 等mesh加载好才知道rtcCenter,每个mesh坐标都不一样
|
|
|
+ needUpdate = true
|
|
|
+ //console.error('rtcCenter有变化?!')
|
|
|
+ }
|
|
|
+
|
|
|
+ tile.rtcCenterState = rtcCenterGlobal = !!tile.content.rtcCenter
|
|
|
+
|
|
|
+ let contentTransform = tile.getContentTransform(needUpdate)
|
|
|
+
|
|
|
+ if(tile.content.rtcCenter){//大部分模型无 rtcCenter
|
|
|
+ //console.error('rtcCenter有?!') //似乎bounding中包含这个信息了 所以getContentTransform不含这个
|
|
|
+ let tranM = new Matrix4$1()
|
|
|
+ tranM.makeTranslation(tile.content.rtcCenter[0], tile.content.rtcCenter[1], tile.content.rtcCenter[2])
|
|
|
+ contentTransform.premultiply(tranM)
|
|
|
+ }
|
|
|
+
|
|
|
+ if(needUpdate ){
|
|
|
+ tile._updateBoundingVolume(tile.header) //add 重新更新
|
|
|
+ }
|
|
|
+
|
|
|
+ if (shouldRotate) { //大部分模型 无需 Rotate
|
|
|
+ contentTransform.multiply(rotateX); // convert from GLTF Y-up to Z-up
|
|
|
+ }
|
|
|
+
|
|
|
+ tileContent.applyMatrix4(contentTransform);
|
|
|
+
|
|
|
+ //'https://testgis.4dage.com/LVBADUI_qp/tileset.json', //村庄 这个案例是 要rotateX 且有rtcCenter的。boundingVolume已经是转换这两者后的值所以getContentTransform不加这个
|
|
|
+
|
|
|
+ //tile总共要左乘的矩阵 rotateX -> tileTransInvert * computedTransform -> 对geometry的tranM修改 -> 整个模型的matrixWorld
|
|
|
+
|
|
|
tileContent.traverse((object) => {
|
|
|
if (object.type == "Mesh") {
|
|
|
const mesh = object;
|
|
@@ -17885,14 +18093,16 @@ function createGLTFNodes(gltfLoader, tile, unlitMaterial, options, rootTransform
|
|
|
|
|
|
|
|
|
//------------------add on 2023.1.16----zeg
|
|
|
-
|
|
|
- mesh.geometry.applyMatrix4(contentTransform)
|
|
|
- if (tile.content.rtcCenter) {
|
|
|
+
|
|
|
+ //mesh.geometry.applyMatrix4(contentTransform)
|
|
|
+ /* if (tile.content.rtcCenter) {
|
|
|
// 有些b3dm模型会将坐标写在源码的rtcCenter里 如https://testgis.4dage.com/LVBADUI_qp/tileset.json
|
|
|
mesh.geometry.translate(tile.content.rtcCenter[0], tile.content.rtcCenter[1], tile.content.rtcCenter[2])
|
|
|
} else {
|
|
|
mesh.geometry.scale(1, 1, -1) // 调整缩放,对应box也要进行变换(scaleZ对应box[2])
|
|
|
- }
|
|
|
+ } */
|
|
|
+
|
|
|
+
|
|
|
//---------------------
|
|
|
|
|
|
}
|
|
@@ -18016,7 +18226,7 @@ class tileHeader 也就是tileset里面的一个个tile 。 其上有.tileset
|
|
|
|
|
|
|
|
|
|
|
|
-tileset里算的tileTrasnform之后是不会改变的, tile.transform也是,是json里的。
|
|
|
+tileset里算的tileTransform之后是不会改变的, tile.transform也是,是json里的。
|
|
|
|
|
|
tileset.modelMatrix (通常这个值很大) 会随着位移改变
|
|
|
tile.computedTransform 被我修改了,之前左乘了tileset.modelMatrix,现只包含了transform信息 _updateTransform(parentTransfor 其中有_updateBoundingVolume,这个影响可见性, 在computeVisibilityWithPlaneMask中计算
|
|
@@ -18033,8 +18243,26 @@ get isVisibleAndInRequestVolume() {
|
|
|
|
|
|
显示所有tile似乎也不会卡顿. 但好像影响了加载顺序从而变慢了。visiVertexCount过量。 怀疑应该还是文件的bound有问题。
|
|
|
原本会消失的地方虽然不会消失了但一直是模糊的
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+=========
|
|
|
+访问所有tile:
|
|
|
+viewer.objs.children[0].runtime.getTileset().tiles
|
|
|
+它的mesh: tile.tileContent
|
|
|
+或者直接得到所有mesh: viewer.objs.children[0].children
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+tile.depth最低为1 , root是0
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
*/
|
|
|
|
|
|
+
|
|
|
+
|
|
|
|
|
|
|
|
|
|