lerp camera moveto
This commit is contained in:
parent
5ffafa1b48
commit
4518fddb12
|
@ -1,5 +1,5 @@
|
||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
import { onMounted, onUnmounted, reactive, ref, watch } from 'vue';
|
import { onMounted, onUnmounted, reactive, Ref, ref, watch } from 'vue';
|
||||||
import {
|
import {
|
||||||
Box3, Color, DoubleSide, Group, Mesh, PlaneGeometry,
|
Box3, Color, DoubleSide, Group, Mesh, PlaneGeometry,
|
||||||
MeshStandardMaterial, MeshStandardMaterialParameters,
|
MeshStandardMaterial, MeshStandardMaterialParameters,
|
||||||
|
@ -27,6 +27,8 @@ const clickable_items = ref<any[]>([])
|
||||||
const clickable_refs = ref<any[]>([])
|
const clickable_refs = ref<any[]>([])
|
||||||
const envVars = reactive({}) as EnvVars
|
const envVars = reactive({}) as EnvVars
|
||||||
const def_distance = reactive({ max: 10, min: 1 })
|
const def_distance = reactive({ max: 10, min: 1 })
|
||||||
|
const camera_moveto = ref() as Ref<Vector3 | undefined>;
|
||||||
|
const camera_moveto_count = ref(100)
|
||||||
|
|
||||||
const sidebar = usePromoSidebar();
|
const sidebar = usePromoSidebar();
|
||||||
const sidebar_scene = usePromoScene();
|
const sidebar_scene = usePromoScene();
|
||||||
|
@ -218,20 +220,6 @@ const loadModels = async () => {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const { onAfterRender } = useLoop()
|
|
||||||
onAfterRender(() => {
|
|
||||||
clickable_refs.value.map(el => {
|
|
||||||
if (el.value[0] && el.value[0].children) {
|
|
||||||
el.value[0].children[0].lookAt(camera.value?.position)
|
|
||||||
}
|
|
||||||
})
|
|
||||||
if (controls.value) {
|
|
||||||
if (timer.seconds_left == 0) {
|
|
||||||
(controls.value as any).update();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
loadModels()
|
loadModels()
|
||||||
watch(() => props.source, () => {
|
watch(() => props.source, () => {
|
||||||
const loaded = seekByName(scene.value, 'loaded')
|
const loaded = seekByName(scene.value, 'loaded')
|
||||||
|
@ -266,15 +254,80 @@ watch(() => sidebar, () => {
|
||||||
const target_vector = new Vector3();
|
const target_vector = new Vector3();
|
||||||
|
|
||||||
el.getWorldPosition(target_vector);
|
el.getWorldPosition(target_vector);
|
||||||
target_vector.y = 0;
|
camera_moveto.value = target_vector
|
||||||
(controls.value as any).target = target_vector;
|
|
||||||
camera.value?.position.set(30, 30, 30);
|
|
||||||
(controls.value as any)._needsUpdate = true;
|
|
||||||
(controls.value as any).update()
|
|
||||||
// camera.value?.rotation.set(0,0,1)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}, { deep: true })
|
}, { deep: true })
|
||||||
|
|
||||||
|
const { onAfterRender } = useLoop()
|
||||||
|
onAfterRender(() => {
|
||||||
|
clickable_refs.value.map(el => {
|
||||||
|
if (el.value[0] && el.value[0].children) {
|
||||||
|
el.value[0].children[0].lookAt(camera.value?.position)
|
||||||
|
}
|
||||||
|
})
|
||||||
|
if (controls.value) {
|
||||||
|
if (timer.seconds_left == 0) {
|
||||||
|
(controls.value as any).update();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (camera_moveto.value) {
|
||||||
|
timer.stopTimer();
|
||||||
|
(controls.value as any).target.lerp(camera_moveto.value, 0.01);
|
||||||
|
camera_moveto_count.value -= 1
|
||||||
|
if (camera_moveto_count.value == 0) {
|
||||||
|
camera_moveto_count.value = 100
|
||||||
|
camera_moveto.value = undefined
|
||||||
|
// camera.value?.position.set(30, 30, 30);
|
||||||
|
// camera.value?.rotation.set(0, 0, 1);
|
||||||
|
timer.startTimer()
|
||||||
|
}
|
||||||
|
(controls.value as any).update()
|
||||||
|
}
|
||||||
|
})
|
||||||
|
const timer = useTimer()
|
||||||
|
timer.timer_func = () => {
|
||||||
|
if (timer.seconds_left == 0 && !(controls.value as any).autoRotate && (controls.value as any).enabled) {
|
||||||
|
pause()
|
||||||
|
if (controls.value && camera.value) {
|
||||||
|
camera.value?.position.set(
|
||||||
|
(controls.value as any).maxDistance * 0.5,
|
||||||
|
(controls.value as any).maxDistance * 0.5,
|
||||||
|
(controls.value as any).maxDistance * 0.5
|
||||||
|
);
|
||||||
|
(controls.value as any).target = new Vector3(0, 0, 0);
|
||||||
|
(controls.value as any).autoRotate = true;
|
||||||
|
(controls.value as any).autoRotateSpeed = 0.5;
|
||||||
|
}
|
||||||
|
resume()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const stopTimer = () => {
|
||||||
|
timer.resetTimer()
|
||||||
|
if ((controls.value as any).autoRotate) {
|
||||||
|
(controls.value as any).autoRotate = false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const pointer = reactive({ x: 0, y: 0 })
|
||||||
|
const clickEvent = (event: MouseEvent) => {
|
||||||
|
const x = (event.clientX / window.innerWidth) * 2 - 1
|
||||||
|
const y = - (event.clientY / window.innerHeight) * 2 + 1
|
||||||
|
if (x == pointer.x && y == pointer.y) return
|
||||||
|
if (!camera.value) return
|
||||||
|
|
||||||
|
pointer.x = x
|
||||||
|
pointer.y = y
|
||||||
|
raycaster.value.setFromCamera(new Vector2(pointer.x, pointer.y), camera.value);
|
||||||
|
|
||||||
|
const clickable_objects = seekAllByName(scene.value, '_clickable');
|
||||||
|
const intersects = raycaster.value.intersectObjects(clickable_objects);
|
||||||
|
const names = intersects.map(el => (el.object.parent ? el.object.parent.name : el.object.name) ?? false).filter(Boolean)
|
||||||
|
if (names.length) {
|
||||||
|
sidebar.open(parseInt(names[0].replace('_clickable', '')))
|
||||||
|
}
|
||||||
|
}
|
||||||
const timerEvent = ['click', 'contextmenu', 'mousedown', 'mouseup', 'touchstart', 'touchend', 'touchmove']
|
const timerEvent = ['click', 'contextmenu', 'mousedown', 'mouseup', 'touchstart', 'touchend', 'touchmove']
|
||||||
onMounted(() => {
|
onMounted(() => {
|
||||||
document.addEventListener('click', clickEvent)
|
document.addEventListener('click', clickEvent)
|
||||||
|
@ -293,49 +346,6 @@ onUnmounted(() => {
|
||||||
document.removeEventListener(event, stopTimer)
|
document.removeEventListener(event, stopTimer)
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
const pointer = reactive({ x: 0, y: 0 })
|
|
||||||
|
|
||||||
const timer = useTimer()
|
|
||||||
timer.timer_func = () => {
|
|
||||||
if (timer.seconds_left == 0 && !(controls.value as any).autoRotate && (controls.value as any).enabled) {
|
|
||||||
pause()
|
|
||||||
if (controls.value && camera.value) {
|
|
||||||
camera.value?.position.set(
|
|
||||||
(controls.value as any).maxDistance * 0.5,
|
|
||||||
(controls.value as any).maxDistance * 0.5,
|
|
||||||
(controls.value as any).maxDistance * 0.5
|
|
||||||
);
|
|
||||||
(controls.value as any).target = new Vector3(0, 0, 0);
|
|
||||||
(controls.value as any).autoRotate = true;
|
|
||||||
(controls.value as any).autoRotateSpeed = 0.5;
|
|
||||||
}
|
|
||||||
resume()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
const stopTimer = () => {
|
|
||||||
timer.resetTimer()
|
|
||||||
if ((controls.value as any).autoRotate) {
|
|
||||||
(controls.value as any).autoRotate = false
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
const clickEvent = (event: MouseEvent) => {
|
|
||||||
const x = (event.clientX / window.innerWidth) * 2 - 1
|
|
||||||
const y = - (event.clientY / window.innerHeight) * 2 + 1
|
|
||||||
if (x == pointer.x && y == pointer.y) return
|
|
||||||
if (!camera.value) return
|
|
||||||
|
|
||||||
pointer.x = x
|
|
||||||
pointer.y = y
|
|
||||||
raycaster.value.setFromCamera(new Vector2(pointer.x, pointer.y), camera.value);
|
|
||||||
|
|
||||||
const clickable_objects = seekAllByName(scene.value, '_clickable');
|
|
||||||
const intersects = raycaster.value.intersectObjects(clickable_objects);
|
|
||||||
const names = intersects.map(el => (el.object.parent ? el.object.parent.name : el.object.name) ?? false).filter(Boolean)
|
|
||||||
if (names.length) {
|
|
||||||
sidebar.open(parseInt(names[0].replace('_clickable', '')))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
</script>
|
</script>
|
||||||
<template>
|
<template>
|
||||||
<TresGroup name="loaded">
|
<TresGroup name="loaded">
|
||||||
|
|
Loading…
Reference in New Issue