Refactored physics to reduce duplicate code.
This commit is contained in:
parent
cdefd3bb70
commit
89623b5007
Binary file not shown.
|
Before Width: | Height: | Size: 35 MiB |
@ -40,7 +40,7 @@ export class App {
|
|||||||
|
|
||||||
constructor() {
|
constructor() {
|
||||||
const config = AppConfig.config;
|
const config = AppConfig.config;
|
||||||
log.setLevel('warn');
|
log.setLevel('debug');
|
||||||
const canvas = document.createElement("canvas");
|
const canvas = document.createElement("canvas");
|
||||||
canvas.style.width = "100%";
|
canvas.style.width = "100%";
|
||||||
canvas.style.height = "100%";
|
canvas.style.height = "100%";
|
||||||
@ -125,7 +125,6 @@ export class App {
|
|||||||
this.scene.gamepadManager.onGamepadConnectedObservable.add((gamepad) => {
|
this.scene.gamepadManager.onGamepadConnectedObservable.add((gamepad) => {
|
||||||
try {
|
try {
|
||||||
const dualshock = (gamepad as DualShockPad);
|
const dualshock = (gamepad as DualShockPad);
|
||||||
|
|
||||||
dualshock.onButtonDownObservable.add((button: any) => {
|
dualshock.onButtonDownObservable.add((button: any) => {
|
||||||
const buttonEvent = DualshockEventMapper.mapButtonEvent(button, 1);
|
const buttonEvent = DualshockEventMapper.mapButtonEvent(button, 1);
|
||||||
if (buttonEvent.objectName) {
|
if (buttonEvent.objectName) {
|
||||||
|
|||||||
@ -1,9 +1,7 @@
|
|||||||
import {
|
import {
|
||||||
AbstractMesh,
|
AbstractMesh,
|
||||||
HavokPlugin,
|
HavokPlugin,
|
||||||
PhysicsAggregate,
|
|
||||||
PhysicsMotionType,
|
PhysicsMotionType,
|
||||||
PhysicsShapeType,
|
|
||||||
Scene,
|
Scene,
|
||||||
TransformNode,
|
TransformNode,
|
||||||
Vector3,
|
Vector3,
|
||||||
@ -44,9 +42,7 @@ export class Base {
|
|||||||
this.controller = controller;
|
this.controller = controller;
|
||||||
|
|
||||||
this.scene = scene;
|
this.scene = scene;
|
||||||
this.scene.onAfterRenderObservable.add(() => {
|
|
||||||
|
|
||||||
}, -1, false, this);
|
|
||||||
|
|
||||||
this.scene.onBeforeRenderObservable.add(() => {
|
this.scene.onBeforeRenderObservable.add(() => {
|
||||||
if (this?.grabbedMesh?.physicsBody) {
|
if (this?.grabbedMesh?.physicsBody) {
|
||||||
@ -106,7 +102,16 @@ export class Base {
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private grab(mesh) {
|
private setupTransformNode(mesh: TransformNode) {
|
||||||
|
const transformNode = new TransformNode("grabAnchor, this.scene");
|
||||||
|
transformNode.id = "grabAnchor";
|
||||||
|
transformNode.position = mesh.position.clone();
|
||||||
|
transformNode.rotationQuaternion = mesh.rotationQuaternion.clone();
|
||||||
|
transformNode.setParent(this.controller.motionController.rootMesh);
|
||||||
|
return transformNode;
|
||||||
|
}
|
||||||
|
|
||||||
|
private grab(mesh: AbstractMesh) {
|
||||||
|
|
||||||
if (this.xr.pointerSelection.getMeshUnderPointer) {
|
if (this.xr.pointerSelection.getMeshUnderPointer) {
|
||||||
mesh = this.xr.pointerSelection.getMeshUnderPointer(this.controller.uniqueId);
|
mesh = this.xr.pointerSelection.getMeshUnderPointer(this.controller.uniqueId);
|
||||||
@ -130,12 +135,9 @@ export class Base {
|
|||||||
|
|
||||||
if ("toolbox" != mesh?.parent?.parent?.id) {
|
if ("toolbox" != mesh?.parent?.parent?.id) {
|
||||||
if (mesh.physicsBody) {
|
if (mesh.physicsBody) {
|
||||||
const transformNode = new TransformNode("grabAnchor, this.scene");
|
|
||||||
transformNode.id = "grabAnchor";
|
const transformNode = this.setupTransformNode(mesh);
|
||||||
transformNode.position = mesh.position.clone();
|
mesh.physicsBody.setMotionType(PhysicsMotionType.ANIMATED);
|
||||||
transformNode.rotationQuaternion = mesh.rotationQuaternion.clone();
|
|
||||||
transformNode.setParent(this.controller.motionController.rootMesh);
|
|
||||||
mesh.physicsBody.setMotionType(PhysicsMotionType.STATIC);
|
|
||||||
//mesh.setParent(transformNode);
|
//mesh.setParent(transformNode);
|
||||||
this.grabbedMeshParentId = transformNode.id;
|
this.grabbedMeshParentId = transformNode.id;
|
||||||
} else {
|
} else {
|
||||||
@ -143,18 +145,7 @@ export class Base {
|
|||||||
}
|
}
|
||||||
this.grabbedMesh = mesh;
|
this.grabbedMesh = mesh;
|
||||||
} else {
|
} else {
|
||||||
const config = AppConfig.config;
|
|
||||||
const newMesh = this.diagramManager.createCopy(mesh);
|
const newMesh = this.diagramManager.createCopy(mesh);
|
||||||
newMesh.position = mesh.absolutePosition.clone();
|
|
||||||
if (mesh.absoluteRotationQuaternion) {
|
|
||||||
newMesh.rotation = mesh.absoluteRotationQuaternion.toEulerAngles().clone();
|
|
||||||
} else {
|
|
||||||
newMesh.rotation = mesh.absoluteRotation.clone();
|
|
||||||
}
|
|
||||||
|
|
||||||
newMesh.scaling = config.createSnapVal;
|
|
||||||
newMesh.material = mesh.material;
|
|
||||||
newMesh.metadata = mesh.metadata;
|
|
||||||
const transformNode = new TransformNode("grabAnchor, this.scene");
|
const transformNode = new TransformNode("grabAnchor, this.scene");
|
||||||
transformNode.id = "grabAnchor";
|
transformNode.id = "grabAnchor";
|
||||||
transformNode.position = newMesh.position.clone();
|
transformNode.position = newMesh.position.clone();
|
||||||
@ -163,14 +154,11 @@ export class Base {
|
|||||||
} else {
|
} else {
|
||||||
transformNode.rotation = newMesh.rotation.clone();
|
transformNode.rotation = newMesh.rotation.clone();
|
||||||
}
|
}
|
||||||
|
|
||||||
transformNode.setParent(this.controller.motionController.rootMesh);
|
transformNode.setParent(this.controller.motionController.rootMesh);
|
||||||
//newMesh?.physicsBody?.setMotionType(PhysicsMotionType.STATIC);
|
|
||||||
//mesh.setParent(transformNode);
|
|
||||||
this.grabbedMeshParentId = transformNode.id;
|
this.grabbedMeshParentId = transformNode.id;
|
||||||
const aggregate = new PhysicsAggregate(newMesh,
|
MeshConverter
|
||||||
PhysicsShapeType.BOX, {mass: 10, restitution: .1, friction: .9}, this.scene);
|
.applyPhysics(newMesh, this.scene)
|
||||||
aggregate.body.setMotionType(PhysicsMotionType.STATIC);
|
.setMotionType(PhysicsMotionType.ANIMATED);
|
||||||
|
|
||||||
|
|
||||||
//newMesh && newMesh.setParent(this.controller.motionController.rootMesh);
|
//newMesh && newMesh.setParent(this.controller.motionController.rootMesh);
|
||||||
@ -199,10 +187,6 @@ export class Base {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private reparent(mesh: AbstractMesh) {
|
private reparent(mesh: AbstractMesh) {
|
||||||
const config = AppConfig.config;
|
|
||||||
const snappedRotation = config.snapRotateVal(mesh.absoluteRotationQuaternion.toEulerAngles().clone());
|
|
||||||
const snappedPosition = config.snapGridVal(mesh.absolutePosition.clone());
|
|
||||||
|
|
||||||
if (this.previousParentId) {
|
if (this.previousParentId) {
|
||||||
const parent = this.scene.getMeshById(this.previousParentId);
|
const parent = this.scene.getMeshById(this.previousParentId);
|
||||||
if (parent) {
|
if (parent) {
|
||||||
@ -211,21 +195,28 @@ export class Base {
|
|||||||
//@note: this is not implemented yet
|
//@note: this is not implemented yet
|
||||||
} else {
|
} else {
|
||||||
//mesh.setParent(null);
|
//mesh.setParent(null);
|
||||||
mesh.rotation = snappedRotation;
|
this.applyTransform(mesh)
|
||||||
mesh.position = snappedPosition;
|
|
||||||
mesh?.physicsBody?.setMotionType(PhysicsMotionType.DYNAMIC);
|
mesh?.physicsBody?.setMotionType(PhysicsMotionType.DYNAMIC);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
const parent = this.scene.getTransformNodeById(this.grabbedMeshParentId);
|
const parent = this.scene.getTransformNodeById(this.grabbedMeshParentId);
|
||||||
if (parent) {
|
if (parent) {
|
||||||
parent.rotation = snappedRotation;
|
this.applyTransform(parent);
|
||||||
parent.position = snappedPosition;
|
|
||||||
this.grabbedMeshParentId = null;
|
this.grabbedMeshParentId = null;
|
||||||
parent.dispose();
|
parent.dispose();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private applyTransform(mesh: TransformNode) {
|
||||||
|
const config = AppConfig.config;
|
||||||
|
const snappedRotation = config.snapRotateVal(mesh.absoluteRotationQuaternion.toEulerAngles().clone());
|
||||||
|
const snappedPosition = config.snapGridVal(mesh.absolutePosition.clone());
|
||||||
|
|
||||||
|
mesh.rotation = snappedRotation;
|
||||||
|
mesh.position = snappedPosition;
|
||||||
|
}
|
||||||
|
|
||||||
private drop() {
|
private drop() {
|
||||||
const mesh = this.grabbedMesh;
|
const mesh = this.grabbedMesh;
|
||||||
if (!mesh) {
|
if (!mesh) {
|
||||||
@ -258,11 +249,7 @@ export class Base {
|
|||||||
//body.setLinearVelocity(this.lastPosition.subtract(body.transformNode.absolutePosition).scale(20));
|
//body.setLinearVelocity(this.lastPosition.subtract(body.transformNode.absolutePosition).scale(20));
|
||||||
this.logger.debug(this.lastPosition.subtract(body.transformNode.absolutePosition).scale(20));
|
this.logger.debug(this.lastPosition.subtract(body.transformNode.absolutePosition).scale(20));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private initGrip(grip: WebXRControllerComponent) {
|
private initGrip(grip: WebXRControllerComponent) {
|
||||||
|
|||||||
@ -1,5 +1,6 @@
|
|||||||
import {Color3, Vector3} from "@babylonjs/core";
|
import {Color3, Vector3} from "@babylonjs/core";
|
||||||
import {BmenuState} from "../menus/MenuState";
|
import {BmenuState} from "../menus/MenuState";
|
||||||
|
|
||||||
export enum DiagramEventType {
|
export enum DiagramEventType {
|
||||||
ADD,
|
ADD,
|
||||||
REMOVE,
|
REMOVE,
|
||||||
@ -11,6 +12,8 @@ export enum DiagramEventType {
|
|||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
export type DiagramEvent = {
|
export type DiagramEvent = {
|
||||||
type: DiagramEventType;
|
type: DiagramEventType;
|
||||||
menustate?: BmenuState;
|
menustate?: BmenuState;
|
||||||
|
|||||||
@ -6,9 +6,7 @@ import {
|
|||||||
InstancedMesh,
|
InstancedMesh,
|
||||||
Mesh,
|
Mesh,
|
||||||
Observable,
|
Observable,
|
||||||
PhysicsAggregate,
|
|
||||||
PhysicsMotionType,
|
PhysicsMotionType,
|
||||||
PhysicsShapeType,
|
|
||||||
PlaySoundAction,
|
PlaySoundAction,
|
||||||
Scene,
|
Scene,
|
||||||
WebXRExperienceHelper
|
WebXRExperienceHelper
|
||||||
@ -19,6 +17,7 @@ import {MeshConverter} from "./meshConverter";
|
|||||||
import log from "loglevel";
|
import log from "loglevel";
|
||||||
import {Controllers} from "../controllers/controllers";
|
import {Controllers} from "../controllers/controllers";
|
||||||
import {DiaSounds} from "../util/diaSounds";
|
import {DiaSounds} from "../util/diaSounds";
|
||||||
|
import {AppConfig} from "../util/appConfig";
|
||||||
|
|
||||||
export class DiagramManager {
|
export class DiagramManager {
|
||||||
public readonly onDiagramEventObservable: Observable<DiagramEvent> = new Observable();
|
public readonly onDiagramEventObservable: Observable<DiagramEvent> = new Observable();
|
||||||
@ -72,8 +71,17 @@ export class DiagramManager {
|
|||||||
newMesh = new InstancedMesh("new", (mesh as InstancedMesh).sourceMesh);
|
newMesh = new InstancedMesh("new", (mesh as InstancedMesh).sourceMesh);
|
||||||
}
|
}
|
||||||
newMesh.actionManager = this.actionManager;
|
newMesh.actionManager = this.actionManager;
|
||||||
return newMesh;
|
newMesh.position = mesh.absolutePosition.clone();
|
||||||
|
if (mesh.absoluteRotationQuaternion) {
|
||||||
|
newMesh.rotation = mesh.absoluteRotationQuaternion.toEulerAngles().clone();
|
||||||
|
} else {
|
||||||
|
this.logger.error("no rotation quaternion");
|
||||||
|
}
|
||||||
|
newMesh.scaling = AppConfig.config.createSnapVal;
|
||||||
|
newMesh.material = mesh.material;
|
||||||
|
newMesh.metadata = mesh.metadata;
|
||||||
|
|
||||||
|
return newMesh;
|
||||||
}
|
}
|
||||||
|
|
||||||
private onRemoteEvent(event: DiagramEntity) {
|
private onRemoteEvent(event: DiagramEntity) {
|
||||||
@ -91,8 +99,8 @@ export class DiagramManager {
|
|||||||
if (event.parent) {
|
if (event.parent) {
|
||||||
mesh.parent = this.scene.getMeshById(event.parent);
|
mesh.parent = this.scene.getMeshById(event.parent);
|
||||||
}
|
}
|
||||||
const body = new PhysicsAggregate(mesh, PhysicsShapeType.BOX, {mass: 10, restitution: .1}, this.scene);
|
MeshConverter.applyPhysics(mesh, this.scene)
|
||||||
body.body.setMotionType(PhysicsMotionType.DYNAMIC);
|
.setMotionType(PhysicsMotionType.DYNAMIC);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -6,6 +6,9 @@ import {
|
|||||||
InstancedMesh,
|
InstancedMesh,
|
||||||
Mesh,
|
Mesh,
|
||||||
MeshBuilder,
|
MeshBuilder,
|
||||||
|
PhysicsAggregate,
|
||||||
|
PhysicsBody,
|
||||||
|
PhysicsShapeType,
|
||||||
Scene,
|
Scene,
|
||||||
StandardMaterial
|
StandardMaterial
|
||||||
} from "@babylonjs/core";
|
} from "@babylonjs/core";
|
||||||
@ -110,6 +113,37 @@ export class MeshConverter {
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static applyPhysics(mesh: AbstractMesh, scene: Scene): PhysicsBody {
|
||||||
|
if (!mesh?.metadata?.template || !scene) {
|
||||||
|
this.logger.error("applyPhysics: mesh or scene is null");
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
if (mesh.physicsBody) {
|
||||||
|
return mesh.physicsBody;
|
||||||
|
}
|
||||||
|
let shapeType = PhysicsShapeType.BOX;
|
||||||
|
switch (mesh.metadata.template) {
|
||||||
|
case "#sphere-template":
|
||||||
|
shapeType = PhysicsShapeType.SPHERE;
|
||||||
|
break;
|
||||||
|
case "#cylinder-template":
|
||||||
|
shapeType = PhysicsShapeType.CYLINDER;
|
||||||
|
break;
|
||||||
|
case "#cone-template":
|
||||||
|
shapeType = PhysicsShapeType.CONVEX_HULL;
|
||||||
|
break;
|
||||||
|
|
||||||
|
}
|
||||||
|
const aggregate = new PhysicsAggregate(mesh,
|
||||||
|
shapeType, {mass: 20, restitution: .2, friction: .9}, scene);
|
||||||
|
aggregate.body.setLinearDamping(.9);
|
||||||
|
aggregate.body.setAngularDamping(.5);
|
||||||
|
|
||||||
|
|
||||||
|
return aggregate.body;
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
public static updateTextNode(mesh: AbstractMesh, text: string) {
|
public static updateTextNode(mesh: AbstractMesh, text: string) {
|
||||||
if (!mesh) {
|
if (!mesh) {
|
||||||
this.logger.error("updateTextNode: mesh is null");
|
this.logger.error("updateTextNode: mesh is null");
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user