hud observation for generic game objects
This commit is contained in:
@@ -1,3 +1,5 @@
|
||||
import { getBoundingBox, getBoundingBoxCenterPoint, getBoundingBoxMaxLength } from "@/lib/MeshUtils";
|
||||
|
||||
class GenericObject{
|
||||
constructor(engine, data){
|
||||
return new Promise(async(resolve, reject)=>{
|
||||
@@ -6,9 +8,32 @@ class GenericObject{
|
||||
|
||||
if (!data.exclude){
|
||||
engine.clickable.add(this.object, e=>{
|
||||
if (engine.dashboard && data.description){
|
||||
if (engine.dashboard){
|
||||
if (data.description){
|
||||
engine.dashboard.update({ hint: data.description })
|
||||
}
|
||||
if (data.hud){
|
||||
if (this.object._hud ){
|
||||
engine.dashboard.detach(this.object);
|
||||
}else{
|
||||
let bb = getBoundingBox(this.object);
|
||||
let scale = 0.5/getBoundingBoxMaxLength(bb);
|
||||
let position = getBoundingBoxCenterPoint(bb, this.object.position).multiplyScalar(scale).negate()
|
||||
|
||||
let placement = {
|
||||
quaternion: { x:0, y:0, z:0, w:0 },
|
||||
position,
|
||||
scale: {
|
||||
x: scale*this.object.scale.x,
|
||||
y: scale*this.object.scale.y,
|
||||
z: scale*this.object.scale.z
|
||||
}
|
||||
}
|
||||
|
||||
engine.dashboard.attach(this.object, placement, true);
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
@@ -34,34 +34,11 @@ class VideoPlayer {
|
||||
})
|
||||
vi.addEventListener('play', ()=>{
|
||||
if (engine.dashboard?.active){
|
||||
data = {
|
||||
parent: plane.parent,
|
||||
location: {
|
||||
position: plane.position.clone(),
|
||||
quaternion: plane.quaternion.clone(),
|
||||
scale: plane.scale.clone()
|
||||
}
|
||||
}
|
||||
engine.dashboard.group.attach(plane);
|
||||
|
||||
engine.motionQueue.add({
|
||||
o: plane,
|
||||
a: {
|
||||
rotation: { x:0, y:0, z:0 },
|
||||
position: { x:0, y:0, z:-0.25 },
|
||||
scale: { x: 1, y:1, z:1 }
|
||||
},
|
||||
t: 1
|
||||
})
|
||||
engine.dashboard.attach(plane);
|
||||
}
|
||||
})
|
||||
vi.addEventListener('pause', ()=>{
|
||||
data.parent.attach(plane);
|
||||
engine.motionQueue.add({
|
||||
o: plane,
|
||||
a: data.location,
|
||||
t: 1
|
||||
})
|
||||
engine.dashboard?.detach(plane);
|
||||
})
|
||||
})
|
||||
}
|
||||
|
||||
+88
-5
@@ -1,4 +1,7 @@
|
||||
import { PlaneGeometry, CylinderGeometry, CanvasTexture, Group, Mesh, MeshStandardMaterial, DoubleSide } from "three";
|
||||
import {
|
||||
PlaneGeometry, CylinderGeometry, CanvasTexture, Group,
|
||||
Mesh, MeshStandardMaterial, MeshBasicMaterial, DoubleSide
|
||||
} from "three";
|
||||
import Utils from "./Utils";
|
||||
class DashBoard {
|
||||
constructor(engine) {
|
||||
@@ -20,6 +23,7 @@ class DashBoard {
|
||||
let texture = new CanvasTexture(canvas)
|
||||
let updating = false;
|
||||
let params = {}
|
||||
let occupied = false;
|
||||
|
||||
img.addEventListener('load', function () {
|
||||
ctx.drawImage(img, 0, 0, engine.w, engine.h);
|
||||
@@ -28,18 +32,36 @@ class DashBoard {
|
||||
updating = false;
|
||||
})
|
||||
|
||||
const dash = new Group();
|
||||
const dash = new Group(), hud = new Group(), hudTarget = new Group();
|
||||
hud.visible = false;
|
||||
let hudAnimation, hudPlane;
|
||||
this.group = dash;
|
||||
dash.add(hud);
|
||||
hud.add(hudTarget)
|
||||
dash.visible = false;
|
||||
|
||||
const dashGeometry = new PlaneGeometry(engine.aspect, 1);
|
||||
const dashMesh = new Mesh(dashGeometry, new MeshStandardMaterial({
|
||||
roughness: 0, metalness:0.1, transparent: true,
|
||||
const dashMesh = new Mesh(dashGeometry, new MeshBasicMaterial({
|
||||
transparent: true,
|
||||
map: texture
|
||||
}))
|
||||
|
||||
dash.add(dashMesh);
|
||||
engine.scene.add(dash)
|
||||
engine.scene.add(dash);
|
||||
|
||||
(async()=>{
|
||||
hudPlane = new Mesh(
|
||||
new PlaneGeometry(engine.aspect, 1),
|
||||
new MeshBasicMaterial({
|
||||
map: await engine.loadTexture('/static/textures/hud.png', ''),
|
||||
opacity: 0.37,
|
||||
transparent:true
|
||||
})
|
||||
);
|
||||
hudPlane.position.z = -0.25;
|
||||
|
||||
hud.add(hudPlane)
|
||||
})()
|
||||
|
||||
engine.addEventListener('beforeRender', ()=>{
|
||||
dash.quaternion.copy(engine.camera.quaternion)
|
||||
@@ -98,6 +120,67 @@ class DashBoard {
|
||||
});
|
||||
}
|
||||
|
||||
this.attach = (object, dashPlacement, rotate)=>{
|
||||
hud.visible = true;
|
||||
hudPlane.scale.set(0, .1, 1);
|
||||
hudPlane.material.opacity = 0.5;
|
||||
engine.motionQueue.add([{
|
||||
o:hudPlane, a:{material:{opacity:0.73}}, t:.4, d:.8
|
||||
},{
|
||||
o:hudPlane, a:{scale:{x:1}}, t:.4
|
||||
},{
|
||||
o:hudPlane, a:{scale:{y:1}}, t:.4, d:.4,
|
||||
}])
|
||||
if (occupied) return false;
|
||||
object._hud = {
|
||||
parent: object.parent,
|
||||
placement: {
|
||||
position: object.position.clone(),
|
||||
quaternion: object.quaternion.clone(),
|
||||
scale: object.scale.clone()
|
||||
}
|
||||
}
|
||||
hudTarget.attach(object);
|
||||
occupied = true;
|
||||
|
||||
engine.motionQueue.add({
|
||||
o: object,
|
||||
a: dashPlacement || {
|
||||
quaternion: { x:0, y:0, z:0, w:0 },
|
||||
position: { x:0, y:0, z:0 },
|
||||
scale: { x: 1, y:1, z:1 }
|
||||
},
|
||||
t: 1
|
||||
})
|
||||
|
||||
if (rotate){
|
||||
engine.motionQueue.add(hudAnimation = {
|
||||
o: hudTarget,
|
||||
a: {
|
||||
rotation: { y: 2*Math.PI }
|
||||
},
|
||||
t: 4,
|
||||
r: true,
|
||||
d: 1
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
this.detach = object=>{
|
||||
engine.motionQueue.remove(hudAnimation);
|
||||
object._hud.parent.attach(object);
|
||||
hud.rotation.y = 0;
|
||||
hud.visible = false;
|
||||
engine.motionQueue.add({
|
||||
o: object,
|
||||
a: object._hud.placement,
|
||||
t: 1
|
||||
});
|
||||
delete object._hud;
|
||||
occupied = false;
|
||||
hudAnimation = null;
|
||||
}
|
||||
|
||||
this.createProgressBar();
|
||||
this.update();
|
||||
}
|
||||
|
||||
@@ -485,12 +485,6 @@ class GameEngine extends THREE.EventDispatcher{
|
||||
this.hero?.characterControls?.idleReset();
|
||||
}
|
||||
|
||||
autoScale(object, mk = 1) {
|
||||
let bb = new THREE.Box3().setFromObject(object);
|
||||
let k = Math.max(bb.max.x - bb.min.x, bb.max.y - bb.min.y, bb.max.z - bb.min.z);
|
||||
object.scale.multiplyScalar(mk / k);
|
||||
}
|
||||
|
||||
setCamera(camera) {
|
||||
//camera.updateProjectionMatrix();
|
||||
this.camera = camera;
|
||||
|
||||
+25
-2
@@ -1,4 +1,4 @@
|
||||
import { TextureLoader } from "three";
|
||||
import { TextureLoader, Box3, Vector3 } from "three";
|
||||
|
||||
function assignParams(mesh, params){
|
||||
['scale', 'rotation', 'position'].forEach(p=>params[p] && mesh[p].fromArray(params[p]));
|
||||
@@ -26,4 +26,27 @@ function assignMaterial(mesh, params){
|
||||
}
|
||||
}
|
||||
|
||||
export { assignParams, assignMaterial }
|
||||
function getBoundingBox(object){
|
||||
return new Box3().setFromObject(object);
|
||||
}
|
||||
|
||||
function getBoundingBoxMaxLength(bb){
|
||||
return Math.max(bb.max.x - bb.min.x, bb.max.y - bb.min.y, bb.max.z - bb.min.z)
|
||||
}
|
||||
|
||||
function getBoundingBoxCenterPoint(bb, relativeTo){
|
||||
relativeTo = relativeTo || new Vector3(0,0,0)
|
||||
return new Vector3(
|
||||
bb.min.x + (bb.max.x - bb.min.x)/2 - relativeTo.x,
|
||||
bb.min.y + (bb.max.y - bb.min.y)/2 - relativeTo.y,
|
||||
bb.min.z + (bb.max.z - bb.min.z)/2 - relativeTo.z
|
||||
)
|
||||
}
|
||||
|
||||
function autoScale(object, mk = 1) {
|
||||
let bb = getBoundingBox(object);
|
||||
let k = getBoundingBoxMaxLength(bb);
|
||||
object.scale.multiplyScalar(mk / k);
|
||||
}
|
||||
|
||||
export { assignParams, assignMaterial, autoScale, getBoundingBox, getBoundingBoxMaxLength, getBoundingBoxCenterPoint }
|
||||
@@ -26,6 +26,8 @@ class MotionEngine {
|
||||
return target;
|
||||
}
|
||||
|
||||
// a = {o-object, a-action, t-time, f-finish event, d-delay, m-mode, r-repeat,
|
||||
// rd-repeat the delay, rf-reset on finish}
|
||||
this.add = function (a) {
|
||||
a = Array.isArray(a) ? a : [a];
|
||||
a.forEach(e => {
|
||||
@@ -35,7 +37,7 @@ class MotionEngine {
|
||||
|
||||
this.clear = function (object) {
|
||||
for (var i = aq.length - 1; i >= 0; i--) {
|
||||
if (object && aq[i].o == object || !object && aq[i].ct == aq[i].t) {
|
||||
if (object && aq[i].o == object || !object && (aq[i].ct == aq[i].t || aq[i].rr)) {
|
||||
aq.splice(i, 1);
|
||||
}
|
||||
}
|
||||
@@ -75,7 +77,11 @@ class MotionEngine {
|
||||
e.ct = e.ct + t;
|
||||
if (e.ct > e.t) {
|
||||
e.ct = e.t;
|
||||
e.f && e.f();
|
||||
e.f?.();
|
||||
if (e.rf){
|
||||
e.ct = t = 0;
|
||||
e.rr = true;
|
||||
}
|
||||
}
|
||||
calcValues(e.o, e.a, e.iv, e.ct / e.t, e.m || 'value');
|
||||
if (e.ct == e.t && e.r) {
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
import { InteractiveObject } from '@/components/InteractiveObjects/InteractiveObject';
|
||||
import { GameEngine } from '@/lib/GameEngine';
|
||||
import { Hero } from '@/lib/Hero';
|
||||
import { autoScale } from '@/lib/MeshUtils';
|
||||
let gameEngine = null;
|
||||
|
||||
export default {
|
||||
@@ -185,7 +186,7 @@ export default {
|
||||
object[p].copy(l[data.id][p])
|
||||
})
|
||||
}else if (!data.type || data.type == 'GenericObject'){
|
||||
gameEngine.autoScale(object, autoScaleFactor);
|
||||
autoScale(object, autoScaleFactor);
|
||||
}
|
||||
l[data.id] = l[data.id] || {};
|
||||
['position', 'scale', 'rotation', 'visible'].forEach(p=>{
|
||||
|
||||
Reference in New Issue
Block a user