| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205 |
- import * as THREE from "../../../libs/three.js/build/three.module.js";
- import BasicMaterial from '../materials/BasicMaterial.js'
- const planeGeometry = new THREE.PlaneBufferGeometry(1,1)
- const height4dkk = 0.5 //4dkk的planeGeometry高度
- let texLoader = new THREE.TextureLoader()
- import FlvVideoPlayerBase from '../utils/media/FlvVideoPlayerBase'
- import H5VideoPlayerBase from '../utils/media/H5VideoPlayerBase'
- const videoPlayer = Potree.browser.nonsupportH5Video ? new FlvVideoPlayerBase() : new H5VideoPlayerBase()
- export default class Overlay extends THREE.Object3D {
- constructor(data){
- super()
- this.data = data
-
-
- var plane = new THREE.Mesh(
- planeGeometry,
- new BasicMaterial({
- color: '#00c8af',
- opacity: 0.2,
- transparent: !0,
- polygonOffset: true, //是否开启多边形偏移 //ie不开启时blank也不会闪烁
- polygonOffsetFactor: -0.9, //多边形偏移因子
- polygonOffsetUnits: -4.0, //多边形偏移单位
- })
- )
- this.add(plane)
- this.plane = plane
-
-
- this.setContent( data.media[0], data.url, data.isNew)
- //this.setScale(data.width, data.height)
- this.scale.set(data.width||1, data.height||1, 1) //需要把width转化一下吗,还是后端转化?
- data.reverse && (this.scale.x *= -1)
- this.addEventListener('dispose',this.dispose.bind(this))
-
-
- let updatePlayInSight = ()=>{
- Common.intervalTool.isWaiting('updatePlayInSight', ()=>{
- Overlay.updatePlayInSight()
- },500)
- }
- this.addEventListener('isVisible',updatePlayInSight)
- this.addEventListener('transformChanged',updatePlayInSight)
-
- Potree.Utils.setObjectLayers(this,'dontIntersect')
-
- }
-
-
- setContent(type, src, autoSize){
-
- this.mediaType = type
- let loadDone = ()=>{
- autoSize && this.autoSize()
- this.plane.material.uniforms.color.value = new THREE.Color('#fff')
- this.plane.material.opacity = 1
- }
- if(type == 'photo'){
- this.plane.material.map = texLoader.load(src, loadDone)
-
-
-
- }else{
-
- var video = videoPlayer.getVideo(src,this)
- this.addEventListener('loadedmetadata', loadDone)
-
- /* var video = $(`<video controls="controls" loop x5-playsinline="" webkit-playsinline="true" playsinline="true" controlslist="nodownload" preload="meta" ></video>`)[0]
- video.setAttribute("crossOrigin", 'Anonymous')//要在src设置好前解决跨域
- video.src = src
- video.onloadeddata = loadDone */
- video.play()
- this.plane.material.map = new THREE.VideoTexture(video)
- Potree.Common.mobileAutoPlay(video, ()=>{
- if(!this.disposed){
- video.play()
- }
- })
- }
- }
-
-
- autoSize(){//根据素材改变长宽
- let size = this.getMediaSize()
- if(size.x > 0 && size.y > 0){
- let area = this.plane.scale.x * this.plane.scale.y
- let r = Math.sqrt(area / (size.x * size.y))
- this.scale.x = size.x * r
- this.scale.y = size.y * r
- }
- this.dispatchEvent('scale_changed')
- }
-
- getMediaSize(){
- let size = new THREE.Vector2;
- let media = this.plane.material.map.image
- if(media){
- if(this.mediaType == 'photo'){
- size.x = media.width;
- size.y = media.height;
- }else{
- size.x = media.videoWidth
- size.y = media.videoHeight
- }
- }
- return size
- }
-
-
-
- dispose(){
- //geo和mat已经在mergeEditor里删了,这要删一下video啥的吗?
- let index = viewer.scene.overlays.indexOf(this)
- if(index == -1)return
- viewer.scene.overlays.splice(index,1)
-
- if(this.mediaType == 'video'){
- let media = this.plane.material.map.image
- media?.pause()
- this.disposed = true
- }
- }
-
-
- videoControl(state){
- var video = this.plane.material.map.image
- if(!video)return
-
-
- this.shouldPlay = state
- if (!state || state == 'stop') {
- if (!video.paused){
- video.pause()
- //console.log('videoControl paused ')
- }
- }else if(state) {
- if (video.paused){
- //console.log('videoControl play ')
- //video = this.loadVideo()
- video.play()
- }
- }
- }
-
-
-
-
-
- static updatePlayInSight(){
- const min = 0.15//最小可播放尺寸(屏幕宽高都是2)
- let camera = viewer.mainViewport.camera
- let camDir = viewer.mainViewport.view.direction
- let frustumMatrix = new THREE.Matrix4
- frustumMatrix.multiplyMatrices(camera.projectionMatrix, camera.matrixWorldInverse)
- let frustum = new THREE.Frustum();
- frustum.setFromProjectionMatrix(frustumMatrix)
-
- let insight = (overlay)=>{
- if(overlay.plane.material.side!=2){ //side为0
- let dir = overlay.plane.getWorldDirection(new THREE.Vector3)
- if(dir.dot(camDir)>0 ){
- //console.log('dir.dot(camDir)',dir.dot(camDir))
- return false
- }
- //可能看到背面。若能看到正面,视线方向和plane朝向必定为钝角
- }
-
- let bound = overlay.bound.clone()
- let insight = frustum.intersectsBox(bound )
- if(!insight)return false
- bound.applyMatrix4(frustumMatrix); //project on screen
- let boundSize = bound.getSize(new THREE.Vector3)
- if(boundSize.x < min && boundSize.y < min){
- //console.log('too small', boundSize)
- return false
- }
- return true
- }
-
-
- viewer.scene.overlays.forEach(overlay=>{
- if(overlay.mediaType != 'video')return
- let shouldPlay = overlay.realVisible() && insight(overlay)
- overlay.videoControl(shouldPlay)
- })
- }
- }
-
|