import math from './math.js' export default class ConvertViews { constructor() { this.sourceApp = null this.targetApp = null this.player1 = null this.player2 = null this.KanKan = null } /* bind(options = { sourceApp: null, targetApp: null }) { if (options.sourceApp) { this.sourceApp = options.sourceApp this.player1 = this.sourceApp.core.get('Player') //this.player1.model.addEventListener('gotPanos', this.init.bind(this)) } else if (options.targetApp) { this.targetApp = options.targetApp this.player2 = this.targetApp.core.get('Player') //this.player2.model.addEventListener('gotPanos', this.init.bind(this)) } if (this.sourceApp && this.targetApp) { // 两个实例都加载完了,可以进行特性处理 this.init() this.applyDiff(options.sourceApp || options.targetApp) } } */ init(viewer, dom2, sceneType, data) { //if (!this.player1.model.panos.list.length || !this.player2.model.panos.list.length) return this.needConvertAxis = sceneType == '4dkk' this.lastCamStatus = viewer.getCameraStatus() viewer.setNavigationMode(Glodon.Bimface.Viewer.NavigationMode3D.Walk) viewer.setFlySpeedRate(5) viewer.getViewer().setTransitionAnimationState(false) //setCameraStatus瞬间变化相机 viewer.addEventListener('Rendered', (e)=>{ let info = viewer.getCameraStatus() let poseChanged = !math.closeTo(this.lastCamStatus.position, info.position) || !math.closeTo(this.lastCamStatus.target, info.target) || !math.closeTo(this.lastCamStatus.fov, info.fov) if(poseChanged){ this.send(info) } this.lastCamStatus = info /* aspect: 0.7879440258342304 coordinateSystem: "world" far: 11485.989363357028 fov: 45 name: "persp" near: 1.1852000000072447 position: {x: -1130.0432094639486, y: -6058.569138159733, z: 2265.9284566100446} target: {x: 310.3968263091223, y: -66.0595010237127, z: 1477.7045866099475} up: {x: 0, y: 1.534753124827774e-13, z: 1} version: 1 zoom: 0 */ }) viewer.addEventListener( Glodon.Bimface.Viewer.Viewer3DEvent.ViewAdded, ()=>{ this.loaded = true if(this.firstData){ this.receive(this.firstData) } } ) this.receive(data) { this.lockCamera(true) let dom1 = viewer.getDomElement() dom1.addEventListener('mousedown',(e)=>{//传递到另一边的dom dom2.dispatchEvent(e) //试试 }) dom1.addEventListener('mousemove',(e)=>{//传递到另一边的dom dom2.dispatchEvent(e) //试试 }) dom1.addEventListener('mouseup',(e)=>{//传递到另一边的dom dom2.dispatchEvent(e) //试试 }) dom1.addEventListener('mousewheel',(e)=>{//传递到另一边的dom dom2.dispatchEvent(e) //试试 }) let stop = (e)=>{ var event = document.createEvent('MouseEvents'); event.initMouseEvent('mouseup', true, false, window, 0, 0, 0, 0, 0, false, false, false, false, 0, null); dom2.dispatchEvent(event) } dom1.addEventListener('mouseout',stop) dom1.addEventListener('mouseover',stop) } this.computeAveDiffLon() } receive(data){ if(!this.loaded){ return this.firstData = data } /* if(this.isMaster){ return //正在操作当前,不接收 } */ let position, target let currStatus = viewer.getCameraStatus() if(data.position){ position = new THREE.Vector3().copy(data.position) }else{ position.copy(currStatus.position) } if(this.needConvertAxis){ position = math.convertVector.YupToZup(position) } if(!data.target){ if(data.quaternion){ if(this.needConvertAxis){ data.quaternion = math.convertQuaternion.YupToZup(data.quaternion) } let dir = new THREE.Vector3(0, 0, -1).applyQuaternion(data.quaternion) dir.applyQuaternion(this.diffQuaternion)/////! target.copy(position).add(dir) } }else{ if(this.needConvertAxis){ target = math.convertVector.YupToZup(target) }else{ target.copy(data.target) } } let msg = { position, target, up: new THREE.Vector3(0,0,1) }//前三个缺一不可 viewer.setCameraStatus(msg) //fov, near, far } send(info){ let camera = viewer.getViewer().camera let data = { position : info.position, quaternion : camera.quaternion, target : info.target, } } lockCamera(locked){ this.locked = locked this.updateCtrlEnable() } setPanoMode(state){ this.isPanoMode = state this.updateCtrlEnable() } updateCtrlEnable(){ viewer.camera3D.enableRotate(this.locked ? false : true) viewer.enableShortcutKey((this.locked || this.isPanoMode) ? false : true) //键盘移动 } computeAveDiffLon() { //获取两个场景的lon偏差值 //需要点的个数>1, 且两个场景点一一对应,位置接近且顺序一致 //pick两个点来计算 let diffLonAve = 0, diffLons = [] let panoPos1 = [//4dkk ] let panoPos2 = [{ x: -0.8948667986001945, y: -0.7200655233964686, z: 1.742798893355817 },{ x: -0.8675960783595227, y: 2.3758592370806317, z: 1.7428102653224462 }] let length = panoPos1.length if(this.needConvertAxis){ panoPos1 = panoPos1.map(e=>math.convertVector.YupToZup(e)) } //挑选连续的两个点为向量来计算,如有123个漫游点,则选取12 23 31作为向量 let index = 0 while (index < length) { let pos11 = new THREE.Vector3().copy(panoPos1[index]) let pos12 = new THREE.Vector3().copy(panoPos1[(index + 1) % length]) let pos21 = new THREE.Vector3().copy(panoPos2[index]) let pos22 = new THREE.Vector3().copy(panoPos2[(index + 1) % length]) let vec1 = new THREE.Vector3().subVectors(pos11, pos12).setY(0) let vec2 = new THREE.Vector3().subVectors(pos21, pos22).setY(0) let diffLon = this.KanKan.Utils.math.getAngle(vec1, vec2, 'z') diffLons.push(diffLon) diffLonAve += diffLon index++ } console.log('diffLons', diffLons) diffLonAve /= length console.log('diffLonAve', diffLonAve) this.diffQuaternion = new THREE.Quaternion().setFromAxisAngle(new THREE.Vector3(0, 1, 0), diffLonAve) this.diffQuaternionInvert = this.diffQuaternion.clone().invert() } /* applyDiff(app) { //sourcePlayer -> targetPlayer if (!this.player1 || !this.player2 || this.targetApp.config.num == this.sourceApp.config.num) return //场景码相同的话返回 if (this.player1.mode != this.player2.mode) return let player1, player2, quaternion //player1为要改变的, player2是参照 if (app == this.sourceApp) { player1 = this.player1 player2 = this.player2 quaternion = this.diffQuaternion } else { player1 = this.player2 player2 = this.player1 quaternion = this.diffQuaternionInvert } let control1 = player1.cameraControls.activeControl let control2 = player2.cameraControls.activeControl //if(!control1 || !control2)return player1.quaternion.copy(player2.quaternion).premultiply(quaternion) if (player1.mode == 'panorama') { //平移 let dir = new this.KanKan.THREE.Vector3().subVectors(control2.target, player2.position) dir.applyQuaternion(quaternion) let target1 = new this.KanKan.THREE.Vector3().addVectors(player1.position, dir) control1.lookAt(target1) control1.target.copy(target1) } else if (control2) { //修改target,保证target在panos之间的相对位置一样 //console.log('target', control2.target.clone()) //console.log('position', control2.target.clone()) let vec = new this.KanKan.THREE.Vector3().subVectors(control2.target, player2.model.panos.list[0].position) vec.applyQuaternion(quaternion) control1.target.addVectors(player1.model.panos.list[0].position, vec) player1.target.copy(control1.target) //修改position,保证方向一样 let dir = new this.KanKan.THREE.Vector3().subVectors(control2.camera.position , control2.target) dir.applyQuaternion(quaternion) player1.position = new this.KanKan.THREE.Vector3().addVectors(control1.target, dir) control1.camera.position.copy(player1.position) } control1.camera.quaternion.copy(player1.quaternion) } */ /* applyDiff(app, data) { //sourcePlayer -> targetPlayer let quaternion if (data.quaternion) { quaternion = new this.KanKan.THREE.Quaternion().copy(data.quaternion) data.quaternion = quaternion } else if (data.info && data.info.quaternion) { //飞出 quaternion = new this.KanKan.THREE.Quaternion(data.info.quaternion._x, data.info.quaternion._y, data.info.quaternion._z, data.info.quaternion._w) data.info.quaternion = quaternion //let radius = data.info.position.distanceTo(data.info.target) } if (!quaternion) return if (app == this.sourceApp) { quaternion.premultiply(this.diffQuaternionInvert) } else { quaternion.premultiply(this.diffQuaternion) } if (data.info && data.info.quaternion) { //飞出 let dir = new this.KanKan.THREE.Vector3().subVectors(data.info.position, data.info.target) dir.applyQuaternion(app == this.sourceApp ? this.diffQuaternionInvert : this.diffQuaternion) data.info.position = new this.KanKan.THREE.Vector3().addVectors(data.info.target, dir) } //先不管飞出后的位置平移 //位置参照第一个漫游点。保持相机相对第一个漫游点的位移和 } */ }