Procházet zdrojové kódy

Scaling root bone animation on copy part 2

- passing skelDimensionsRatio arg to Bone.copyAnimationRange()
- using this to scale root bone translation, if dimensionsAtRest
property available

This has not been tested.  I do not have .blend(s).  The need for
an arg change makes this PR easier incase changes on PG during testing,
once .babylon wt skeletons which have dimensionsAtRest property are
available.
jeff před 9 roky
rodič
revize
54feed8ba3

+ 2 - 1
dist/preview release/what's new.md

@@ -27,6 +27,7 @@
     - Added support for various normal maps conventions ([deltakosh](https://github.com/deltakosh))
     - Added postprocess.enablePixelPerfectMode to avoid texture scaling/stretching when dealing with non-power of 2 resolutions. cannot be used on post-processes chain ([deltakosh](https://github.com/deltakosh))
     - Enabled other post processes to be used when also using a 3D Rig ([jcpalmer](https://github.com/Palmer-JC))
+    - Got Skeleton.copyAminationRange scaling better for different bone lengths ([jcpalmer](https://github.com/Palmer-JC))
     - Added skeleton.getBoneIndexByName(boneName: string) ([dad72](https://github.com/dad72))
     - Added node._children to track children hierarchy ([deltakosh](https://github.com/deltakosh))
     - Added Camera.ForceAttachControlToAlwaysPreventDefault to help embedding Babylon.js in iFrames ([deltakosh](https://github.com/deltakosh))
@@ -60,7 +61,7 @@
     - Unity exporter now support skeletons ([sebavan](https://github.com/sebavan))
     - Support for 3dsmax 2017 ([deltakosh](https://github.com/deltakosh))
     - Added support for up to 8 bones influences per vertex for 3dsmax exporter ([deltakosh](https://github.com/deltakosh))
-    - Added console logging for .babylon file loading ([jcpalmer](https://github.com/Palmer-JC))
+    - Added console logging for .babylon file loading & depreciated SceneLoader.Load() in favor of Append() ([jcpalmer](https://github.com/Palmer-JC))
   - **API doc**
     - class `SolidParticleSystem` documented ([jerome](https://github.com/jbousquie))
     - class `MeshBuilder` documented ([jerome](https://github.com/jbousquie))

+ 27 - 12
src/Bones/babylon.bone.ts

@@ -98,7 +98,7 @@
             this._skeleton._markAsDirty();
         }
 
-        public copyAnimationRange(source: Bone, rangeName: string, frameOffset: number, rescaleAsRequired = false): boolean {
+        public copyAnimationRange(source: Bone, rangeName: string, frameOffset: number, rescaleAsRequired = false, skelDimensionsRatio : Vector3 = null): boolean {
             // all animation may be coming from a library skeleton, so may need to create animation
             if (this.animations.length === 0) {
                 this.animations.push(new Animation(this.name, "_matrix", source.animations[0].framePerSecond, Animation.ANIMATIONTYPE_MATRIX, 0));
@@ -116,25 +116,40 @@
             
             // rescaling prep
             var sourceBoneLength = source.length;
-            var scalingReqd = rescaleAsRequired && sourceBoneLength && this.length && sourceBoneLength !== this.length;
-            var ratio = scalingReqd ? this.length / sourceBoneLength : null;
-
+            var sourceParent = source.getParent();
+            var parent = this.getParent();
+            var parentScalingReqd = rescaleAsRequired && sourceParent && sourceBoneLength && this.length && sourceBoneLength !== this.length;
+            var parentRatio = parentScalingReqd ? parent.length / sourceParent.length : null;
+            
+            var dimensionsScalingReqd = rescaleAsRequired && !parent && skelDimensionsRatio && (skelDimensionsRatio.x !== 1 || skelDimensionsRatio.y !== 1 || skelDimensionsRatio.z !== 1);           
+            
             var destKeys = this.animations[0].getKeys();
             
-            // loop vars declaration / initialization
+            // loop vars declaration
             var orig: { frame: number, value: Matrix };
-            var origScale = scalingReqd ? Vector3.Zero() : null;
-            var origRotation = scalingReqd ? new Quaternion() : null;
-            var origTranslation = scalingReqd ? Vector3.Zero() : null;
+            var origTranslation : Vector3;
             var mat: Matrix;
 
             for (var key = 0, nKeys = sourceKeys.length; key < nKeys; key++) {
                 orig = sourceKeys[key];
                 if (orig.frame >= from && orig.frame <= to) {
-                    if (scalingReqd) {
-                        orig.value.decompose(origScale, origRotation, origTranslation);
-                        origTranslation.scaleInPlace(ratio);
-                        mat = Matrix.Compose(origScale, origRotation, origTranslation);
+                    if (rescaleAsRequired) {
+                        mat = orig.value.clone();
+                        
+                        // scale based on parent ratio, when bone has parent
+                        if (parentScalingReqd) {
+                            origTranslation = mat.getTranslation();
+                            mat.setTranslation(origTranslation.scaleInPlace(parentRatio));
+                            
+                        // scale based on skeleton dimension ratio when root bone, and value is passed
+                        } else if (dimensionsScalingReqd) {
+                            origTranslation = mat.getTranslation();
+                            mat.setTranslation(origTranslation.multiplyInPlace(skelDimensionsRatio));                            
+
+                        // use original when root bone, and no data for skelDimensionsRatio
+                        } else {
+                            mat = orig.value;                            
+                        }
                     } else {
                         mat = orig.value;
                     }

+ 2 - 0
src/Bones/babylon.skeleton.ts

@@ -135,6 +135,8 @@
                 Tools.Warn(`copyAnimationRange: this rig has ${this.bones.length} bones, while source as ${sourceBones.length}`);
                 ret = false;
             }
+            
+            var skelDimensionsRatio = (rescaleAsRequired && this.dimensionsAtRest && source.dimensionsAtRest) ? this.dimensionsAtRest.divide(source.dimensionsAtRest) : null;
 
             for (i = 0, nBones = this.bones.length; i < nBones; i++) {
                 var boneName = this.bones[i].name;