This commit is contained in:
2025-11-26 17:50:59 +02:00
parent b2824863e4
commit 99bfe70991
+28 -29
View File
@@ -1,13 +1,12 @@
import { AnimationMixer, Vector3 } from 'three'; import { AnimationMixer, Vector3 } from 'three';
import { PointerControls } from './PointerControls'; import { PointerControls } from './PointerControls';
import { getBoundingBox, getBoundingBoxCenterPoint, getBoundingBoxSize, centerOrigin } from './MeshUtils'; import { getBoundingBox, getBoundingBoxCenterPoint, getBoundingBoxSize } from './MeshUtils';
import { QueryFilterFlags } from '@dimforge/rapier3d'; import { QueryFilterFlags } from '@dimforge/rapier3d';
class Hero{ class Hero{
walkDirection = new Vector3() walkDirection = new Vector3()
rotateAngle = new Vector3(0, 1, 0) rotateAngle = new Vector3(0, 1, 0)
cameraY = 3 #cameraZ = 5/1.77
#cameraZ = 5
get cameraZ(){ get cameraZ(){
return this.#cameraZ; return this.#cameraZ;
@@ -17,46 +16,48 @@ class Hero{
this.#cameraZ = Math.min(Math.max(v, 2), 10); this.#cameraZ = Math.min(Math.max(v, 2), 10);
} }
// constants
fadeDuration = 0.2 fadeDuration = 0.2
runVelocity = 11 characterGapOffset = 0.01;
walkVelocity = 7
characterGapOffset = 0.1;
lerp = (x, y, a) => x * (1 - a) + y * a; lerp = (x, y, a) => x * (1 - a) + y * a;
constructor(io, data){ constructor(engine, io, data){
this.source = io.source; this.source = io.source;
this.model = io.object this.model = io.object
this.data = data; this.data = data;
}
init(gameEngine){ this.engine = engine;
this.gameEngine = gameEngine;
this.mixer = new AnimationMixer(this.model); this.mixer = new AnimationMixer(this.model);
gameEngine.mixers.push( this.mixer ); engine.mixers.push( this.mixer );
this.animationsMap = {}; this.animationsMap = {};
this.source.animations.forEach(a=>{ this.source.animations.forEach(a=>{
this.animationsMap[a.name] = this.mixer.clipAction(a); this.animationsMap[a.name] = this.mixer.clipAction(a);
}) })
this.pointerControls = new PointerControls(gameEngine.camera, this.model, gameEngine.renderer.domElement); this.pointerControls = new PointerControls(engine.camera, this.model, engine.renderer.domElement);
gameEngine.hero = this; engine.hero = this;
let bb = this.model.userData.bbox; // let bb = this.model.userData.bbox;
let size = getBoundingBoxSize(bb); // let size = getBoundingBoxSize(bb);
let center = getBoundingBoxCenterPoint(bb, this.model.userData.object.position) // let center = getBoundingBoxCenterPoint(bb, this.model.userData.object.position)
let bb = getBoundingBox(io.object);
this.size = getBoundingBoxSize(bb);
// let center = getBoundingBoxCenterPoint(bb, io.object.position)
this.po = gameEngine.physics.add(this.model, 'kinematicPositionBased', false, undefined, 'capsule', { radius: size.x/2, halfHeight: size.y/2}) // console.log('hero', size, center, size.y - 2*this.characterGapOffset)
this.po.collider.setTranslationWrtParent({x: center.x, y: center.y + size.y/2 + this.characterGapOffset, z: center.z});
this.runVelocity = this.size.y * 5
this.walkVelocity = this.size.y * 3
this.po = engine.physics.add(this.model, 'kinematicPositionBased', false, undefined, 'capsule', { radius: this.size.x/2, halfHeight: (this.size.y-this.size.x)/2})
this.po.collider.setTranslationWrtParent({x: 0, y: this.size.y/2, z: 0});
this.currentAction = 'idle'; this.currentAction = 'idle';
this.animationsMap[this.currentAction].play() this.animationsMap[this.currentAction].play()
this.characterController = this.gameEngine.physics.world.createCharacterController(this.characterGapOffset); this.characterController = this.engine.physics.world.createCharacterController(this.characterGapOffset);
this.characterController.setUp({x:0, y:1, z:0}); this.characterController.setUp({x:0, y:1, z:0});
this.po.rigidBody.setTranslation(this.model.position) this.po.rigidBody.setTranslation(this.model.position)
this.po.characterController = this.characterController; this.po.characterController = this.characterController;
@@ -69,8 +70,9 @@ class Hero{
this.characterController.setApplyImpulsesToDynamicBodies(true); this.characterController.setApplyImpulsesToDynamicBodies(true);
// this.characterController.setCharacterMass(50); // this.characterController.setCharacterMass(50);
this.orbitControl = this.gameEngine.orbitControls this.orbitControl = this.engine.orbitControls
this.camera = this.gameEngine.camera this.camera = this.engine.camera
this.cameraY = this.size.y * 1.5;
this.direction = this.model.rotation.y; this.direction = this.model.rotation.y;
this.directionVelocity = 0; this.directionVelocity = 0;
@@ -85,9 +87,7 @@ class Hero{
} }
update(delta){ update(delta){
if (this.gameEngine.renderer.xr.isPresenting) return; if (this.ready && this.engine.physics.started && !this.disableInput && !this.engine.renderer.xr.isPresenting) {
if (this.ready && !this.disableInput) {
let pc = this.pointerControls; let pc = this.pointerControls;
pc.update(); pc.update();
this.updateCharacterControls(delta, pc) this.updateCharacterControls(delta, pc)
@@ -95,12 +95,11 @@ class Hero{
} }
destroy(){ destroy(){
delete this.gameEngine.hero; delete this.engine.hero;
this.gameEngine.mixers.splice(this.gameEngine.mixers.indexOf(this.mixer), 1); this.engine.mixers.splice(this.engine.mixers.indexOf(this.mixer), 1);
} }
updateCharacterControls(delta) { updateCharacterControls(delta) {
if (!this.gameEngine.physics.started) return;
let input = this.getInput() let input = this.getInput()
let play = this.currentAction || 'idle', velocity = this.walkVelocity; let play = this.currentAction || 'idle', velocity = this.walkVelocity;
@@ -212,7 +211,7 @@ class Hero{
this.camera.position.copy(cameraPosition) this.camera.position.copy(cameraPosition)
this.orbitControl.target.set( this.orbitControl.target.set(
this.model.position.x, this.model.position.x,
this.cameraY - 1 + this.model.position.y, this.cameraY -this.size.y * 0.5 + this.model.position.y,
this.model.position.z this.model.position.z
) )
this.camera.lookAt(this.orbitControl.target) this.camera.lookAt(this.orbitControl.target)