瀏覽代碼

Fixing mesh impostors positioning

Raanan Weber 7 年之前
父節點
當前提交
0ebd635188
共有 2 個文件被更改,包括 33 次插入40 次删除
  1. 19 6
      src/Physics/Plugins/babylon.cannonJSPlugin.ts
  2. 14 34
      src/Physics/babylon.physicsImpostor.ts

+ 19 - 6
src/Physics/Plugins/babylon.cannonJSPlugin.ts

@@ -116,7 +116,7 @@
             if (meshChildren.length) {
                 var processMesh = (localPosition: Vector3, mesh: AbstractMesh) => {
 
-                    if (!currentRotation || ! mesh.rotationQuaternion) {
+                    if (!currentRotation || !mesh.rotationQuaternion) {
                         return;
                     }
 
@@ -263,10 +263,20 @@
                     returnValue = new this.BJSCANNON.Plane();
                     break;
                 case PhysicsImpostor.MeshImpostor:
+                    // should transform the vertex data to world coordinates!!
                     var rawVerts = object.getVerticesData ? object.getVerticesData(VertexBuffer.PositionKind) : [];
                     var rawFaces = object.getIndices ? object.getIndices() : [];
+                    if (!rawVerts) return;
+                    let transform = object.computeWorldMatrix(true);
+                    // convert rawVerts to object space
+                    var temp = new Array<number>();
+                    var index: number;
+                    for (index = 0; index < rawVerts.length; index += 3) {
+                        Vector3.TransformCoordinates(Vector3.FromArray(rawVerts, index), transform).toArray(temp, index);
+                    }
+
                     Tools.Warn("MeshImpostor only collides against spheres.");
-                    returnValue = new this.BJSCANNON.Trimesh(<number[]>rawVerts, <number[]>rawFaces);
+                    returnValue = new this.BJSCANNON.Trimesh(temp, <number[]>rawFaces);
                     break;
                 case PhysicsImpostor.HeightmapImpostor:
                     returnValue = this._createHeightmap(object);
@@ -289,7 +299,7 @@
             let boundingInfo = <BoundingInfo>(object.getBoundingInfo());
             var dim = Math.min(boundingInfo.boundingBox.extendSizeWorld.x, boundingInfo.boundingBox.extendSizeWorld.z);
             var minY = boundingInfo.boundingBox.extendSizeWorld.y;
-            
+
             var elementSize = dim * 2 / arraySize;
 
             for (var i = 0; i < pos.length; i = i + 3) {
@@ -349,8 +359,11 @@
             //make sure it is updated...
             object.computeWorldMatrix && object.computeWorldMatrix(true);
             // The delta between the mesh position and the mesh bounding box center
+            let bInfo = object.getBoundingInfo();
+            if (!bInfo) return;
             var center = impostor.getObjectCenter();
-            this._tmpDeltaPosition.copyFrom(object.position.subtract(center));
+            //m.getAbsolutePosition().subtract(m.getBoundingInfo().boundingBox.centerWorld)
+            this._tmpDeltaPosition.copyFrom(object.getAbsolutePosition().subtract(center));
             this._tmpPosition.copyFrom(center);
             var quaternion = object.rotationQuaternion;
 
@@ -400,8 +413,8 @@
                 mesh.setPivotMatrix(oldPivot);
                 mesh.computeWorldMatrix(true);
             } else if (impostor.type === PhysicsImpostor.MeshImpostor) {
-                this._tmpDeltaPosition.copyFromFloats(0, 0, 0);
-                this._tmpPosition.copyFrom(object.position);
+                //this._tmpDeltaPosition.copyFromFloats(0, 0, 0);
+                //this._tmpPosition.copyFrom(object.position);
             }
 
             impostor.setDeltaPosition(this._tmpDeltaPosition);

+ 14 - 34
src/Physics/babylon.physicsImpostor.ts

@@ -16,13 +16,17 @@ module BABYLON {
         rotation?: Vector3;
         parent?: any;
         getBoundingInfo(): Nullable<BoundingInfo>;
-        computeWorldMatrix?(force: boolean): void;
+        computeWorldMatrix(force: boolean): Matrix;
         getWorldMatrix?(): Matrix;
         getChildMeshes?(directDescendantsOnly?: boolean): Array<AbstractMesh>;
         getVerticesData(kind: string): Nullable<Array<number> | Float32Array>;
         getIndices?(): Nullable<IndicesArray>;
         getScene?(): Scene;
         getAbsolutePosition(): Vector3;
+        getAbsolutePivotPoint(): Vector3;
+        rotate(axis: Vector3, amount: number, space?: Space): IPhysicsEnabledObject;
+        translate(axis: Vector3, distance: number, space?: Space): IPhysicsEnabledObject;
+        setAbsolutePosition(absolutePosition: Vector3): IPhysicsEnabledObject;
     }
 
     export class PhysicsImpostor {
@@ -370,9 +374,6 @@ module BABYLON {
             }
         }
 
-        private _tmpPositionWithDelta: Vector3 = Vector3.Zero();
-        private _tmpRotationWithDelta: Quaternion = new Quaternion();
-
         /**
          * this function is executed by the physics engine.
          */
@@ -381,23 +382,12 @@ module BABYLON {
                 return;
             }
 
-            if (this._options.ignoreParent && this.object.parent) {
-                this._tmpPositionWithDelta.copyFrom(this.object.getAbsolutePosition());
-                //this.object.getAbsolutePosition().subtractToRef(this._deltaPosition, this._tmpPositionWithDelta);
-            } else {
-                this.object.position.subtractToRef(this._deltaPosition, this._tmpPositionWithDelta);
-            }
-            //conjugate deltaRotation
-            if (this.object.rotationQuaternion) {
-                if (this._deltaRotationConjugated) {
-                    this.object.rotationQuaternion.multiplyToRef(this._deltaRotationConjugated, this._tmpRotationWithDelta);
-                } else {
-                    this._tmpRotationWithDelta.copyFrom(this.object.rotationQuaternion);
-                }
-            }
-            // Only if not disabled
+            this.object.translate(this._deltaPosition, -1);
+            this._deltaRotationConjugated && this.object.rotationQuaternion && this.object.rotationQuaternion.multiplyToRef(this._deltaRotationConjugated, this.object.rotationQuaternion);
+
             if (!this._options.disableBidirectionalTransformation) {
-                this._physicsEngine.getPhysicsPlugin().setPhysicsBodyTransformation(this, this._tmpPositionWithDelta, this._tmpRotationWithDelta);
+                let bInfo = this.object.getBoundingInfo();
+                bInfo && this.object.rotationQuaternion && this._physicsEngine.getPhysicsPlugin().setPhysicsBodyTransformation(this, /*bInfo.boundingBox.centerWorld*/ this.object.getAbsolutePosition(), this.object.rotationQuaternion);
             }
 
             this._onBeforePhysicsStepCallbacks.forEach((func) => {
@@ -413,21 +403,11 @@ module BABYLON {
                 return;
             }
 
-            this._onAfterPhysicsStepCallbacks.forEach((func) => {
-                func(this);
-            });
-
             this._physicsEngine.getPhysicsPlugin().setTransformationFromPhysicsBody(this);
-
-            if (this._options.ignoreParent && this.object.parent) {
-                this.object.position.subtractInPlace(this.object.parent.getAbsolutePosition());
-            } else {
-                this.object.position.addInPlace(this._deltaPosition)
-            }
-
-            if (this._deltaRotation && this.object.rotationQuaternion) {
-                this.object.rotationQuaternion.multiplyInPlace(this._deltaRotation);
-            }
+            // take the position set and make it the absolute position of this object.
+            this.object.setAbsolutePosition(this.object.position);
+            this._deltaRotation && this.object.rotationQuaternion && this.object.rotationQuaternion.multiplyToRef(this._deltaRotation, this.object.rotationQuaternion);
+            this.object.translate(this._deltaPosition, 1);
         }
 
         /**