123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342 |
- import * as THREE from "../../../libs/three.js/build/three.module.js";
- import { EventDispatcher } from "../../EventDispatcher.js";
- import { Utils } from "../../utils.js";
-
- import {LineDraw} from "../../utils/DrawUtil";
- import CurveCtrl from "../../objects/tool/CurveCtrl";
-
-
- const colors = {
- position: 'red',
- target : 'blue'
- }
-
- let lineMats
- const getLineMat = function(name){
- if(!lineMats){
- lineMats = {
- position: LineDraw.createFatLineMat({
- color: colors.position,
- lineWidth: 3
- }),
- target : LineDraw.createFatLineMat({
- color: colors.target,
- lineWidth: 3
- }),
- frustum: LineDraw.createFatLineMat({
- color: colors.position,
- lineWidth: 2
- }),
- }
- }
- return lineMats[name]
- }
-
- export class CameraAnimation extends EventDispatcher{
- constructor(viewer){
- super();
-
- this.viewer = viewer;
- this.selectedElement = null;
- //this.controlPoints = [];
- this.uuid = THREE.Math.generateUUID();
- this.node = new THREE.Object3D();
- this.node.name = "camera animation";
- this.viewer.scene.scene.add(this.node);
- this.frustum = this.createFrustum();
- this.node.add(this.frustum);
- this.name = "Camera Animation";
- this.duration = 5;
- this.t = 0;
- // "centripetal", "chordal", "catmullrom"
- this.curveType = "centripetal"
- this.visible = true;
-
- this.createPath();
-
-
-
-
-
-
- this.addEventListener('dispose', ()=>{
-
- this.dispose()
- })
-
- }
- static defaultFromView(viewer){
- const animation = new CameraAnimation(viewer);
- const camera = viewer.scene.getActiveCamera();
- const target = viewer.scene.view.getPivot();
- const cpCenter = new THREE.Vector3(
- 0.3 * camera.position.x + 0.7 * target.x,
- 0.3 * camera.position.y + 0.7 * target.y,
- 0.3 * camera.position.z + 0.7 * target.z,
- );
- const targetCenter = new THREE.Vector3(
- 0.05 * camera.position.x + 0.95 * target.x,
- 0.05 * camera.position.y + 0.95 * target.y,
- 0.05 * camera.position.z + 0.95 * target.z,
- );
- const r = 2//camera.position.distanceTo(target) * 0.3;
- //const dir = target.clone().sub(camera.position).normalize();
- const angle = Utils.computeAzimuth(camera.position, target);
- const n = 5;
- for(let i = 0; i < n; i++){
- let u = 1.5 * Math.PI * (i / n) + angle;
- const dx = r * Math.cos(u);
- const dy = r * Math.sin(u);
- const cpPos = [
- cpCenter.x + dx,
- cpCenter.y + dy,
- cpCenter.z,
- ];
- const targetPos = [
- targetCenter.x + dx * 0.1,
- targetCenter.y + dy * 0.1,
- targetCenter.z,
- ];
- animation.createControlPoint();
- animation.posCurve.points[i].fromArray(cpPos)
- animation.targetCurve.points[i].fromArray(targetPos)
-
- }
- animation.changeCallback()
- return animation;
- }
-
- createControlPoint(index){
- const length = this.posCurve.points.length
- const position = new THREE.Vector3
- const target = new THREE.Vector3
-
- if(index === undefined){
- index = length;
- }
-
- if(length >= 2 && index === 0){
- const dir = new THREE.Vector3().subVectors(this.posCurve.points[0], this.posCurve.points[1] )
- position.copy(this.posCurve.points[0]).add(dir);
-
- const tDir = new THREE.Vector3().subVectors(this.targetCurve.points[0], this.targetCurve.points[1] )
- target.copy(this.targetCurve.points[0]).add(dir);
-
- }else if(length >= 2 && index === length){
- const dir = new THREE.Vector3().subVectors(this.posCurve.points[length-1], this.posCurve.points[length-2] )
- position.copy(this.posCurve.points[length-2]).add(dir);
-
- const tDir = new THREE.Vector3().subVectors(this.targetCurve.points[length-1], this.targetCurve.points[length-2] )
- target.copy(this.targetCurve.points[length-2]).add(dir);
-
- }else if(length >= 2){
- position.copy(this.posCurve.points[index-1].clone().add(this.posCurve.points[index]).multiplyScalar(0.5));
- target.copy(this.targetCurve.points[index-1].clone().add(this.targetCurve.points[index]).multiplyScalar(0.5));
- }
-
- this.posCurve.addPoint(position, index)
- this.targetCurve.addPoint(target, index)
-
- this.dispatchEvent({
- type: "controlpoint_added",
- index
- });
-
- }
-
- removeControlPoint(index){
- this.posCurve.removePoint(index)
- this.targetCurve.removePoint(index)
- this.dispatchEvent({
- type: "controlpoint_removed",
- index
- });
-
- }
- createPath(){
- this.posCurve = new CurveCtrl([],getLineMat('position'), colors.position);
- this.targetCurve = new CurveCtrl([], getLineMat('target'), colors.target);
- this.node.add(this.posCurve)
- this.node.add(this.targetCurve)
- }
- createFrustum(){
- const f = 0.3;
- const positions = [
- new THREE.Vector3( 0, 0, 0),
- new THREE.Vector3(-f, -f, +1),
- new THREE.Vector3( 0, 0, 0),
- new THREE.Vector3( f, -f, +1),
- new THREE.Vector3( 0, 0, 0),
- new THREE.Vector3( f, f, +1),
- new THREE.Vector3( 0, 0, 0),
- new THREE.Vector3(-f, f, +1),
- new THREE.Vector3(-f, -f, +1),
- new THREE.Vector3( f, -f, +1),
- new THREE.Vector3( f, -f, +1),
- new THREE.Vector3( f, f, +1),
- new THREE.Vector3( f, f, +1),
- new THREE.Vector3(-f, f, +1),
- new THREE.Vector3(-f, f, +1),
- new THREE.Vector3(-f, -f, +1),
- ]
-
- //geometry.computeBoundingSphere();//?
- const line = LineDraw.createFatLine( positions, {material:getLineMat('frustum')})
- //line.scale.set(20, 20, 20);
- return line;
- }
-
- at(t){
-
- if(t > 1){
- t = 1;
- }else if(t < 0){
- t = 0;
- }
- const camPos = this.posCurve.getPointAt(t);
- const target = this.targetCurve.getPointAt(t);
- const frame = {
- position: camPos,
- target: target,
- };
- return frame;
- }
- set(t){
- this.t = t;
- }
-
- setVisible(visible){
- this.node.visible = visible;
-
- this.posCurve.visible = visible
- this.targetCurve.visible = visible
- this.visible = visible;
- }
- setDuration(duration){
- this.duration = duration;
- }
- getDuration(duration){
- return this.duration;
- }
- play(){
- const tStart = performance.now();
- const duration = this.duration;
- const originalyVisible = this.visible;
- this.setVisible(false);
- const onUpdate = (delta) => {
- let tNow = performance.now();
- let elapsed = (tNow - tStart) / 1000;
- let t = elapsed / duration;
- this.set(t);
- const frame = this.at(t);
- viewer.scene.view.position.copy(frame.position);
- viewer.scene.view.lookAt(frame.target);
- this.updateFrustum()
- if(t > 1){
- this.setVisible(originalyVisible);
- this.viewer.removeEventListener("update", onUpdate);
- }
-
-
- };
- this.viewer.addEventListener("update", onUpdate);
- }
- updateFrustum(){ //
- const frame = this.at(this.t);
- const frustum = this.frustum;
- frustum.position.copy(frame.position);
- frustum.lookAt(...frame.target.toArray());
-
- }
- changeCallback(){
- this.posCurve.update()
- this.targetCurve.update()
- this.updateFrustum()
- }
- dispose(){//add
- this.posCurve.dispatchEvent({type:'dispose'})
- this.targetCurve.dispatchEvent({type:'dispose'})
- this.node.parent.remove(this.node);
- }
- }
- //scene.removeCameraAnimation
|