123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169 |
- /**
- * @author mikael emtinger / http://gomo.se/
- * @author alteredq / http://alteredqualia.com/
- * @author ikerr / http://verold.com
- */
- THREE.SkinnedMesh = function ( geometry, material, useVertexTexture ) {
- THREE.Mesh.call( this, geometry, material );
- this.type = 'SkinnedMesh';
- this.bindMode = "attached";
- this.bindMatrix = new THREE.Matrix4();
- this.bindMatrixInverse = new THREE.Matrix4();
- // init bones
- // TODO: remove bone creation as there is no reason (other than
- // convenience) for THREE.SkinnedMesh to do this.
- var bones = [];
- if ( this.geometry && this.geometry.bones !== undefined ) {
- var bone, gbone, p, q, s;
- for ( var b = 0, bl = this.geometry.bones.length; b < bl; ++ b ) {
- gbone = this.geometry.bones[ b ];
- p = gbone.pos;
- q = gbone.rotq;
- s = gbone.scl;
- bone = new THREE.Bone( this );
- bones.push( bone );
- bone.name = gbone.name;
- bone.position.set( p[ 0 ], p[ 1 ], p[ 2 ] );
- bone.quaternion.set( q[ 0 ], q[ 1 ], q[ 2 ], q[ 3 ] );
- if ( s !== undefined ) {
- bone.scale.set( s[ 0 ], s[ 1 ], s[ 2 ] );
- } else {
- bone.scale.set( 1, 1, 1 );
- }
- }
- for ( var b = 0, bl = this.geometry.bones.length; b < bl; ++ b ) {
- gbone = this.geometry.bones[ b ];
- if ( gbone.parent !== - 1 ) {
- bones[ gbone.parent ].add( bones[ b ] );
- } else {
- this.add( bones[ b ] );
- }
- }
- }
- this.normalizeSkinWeights();
- this.updateMatrixWorld( true );
- this.bind( new THREE.Skeleton( bones, undefined, useVertexTexture ) );
- };
- THREE.SkinnedMesh.prototype = Object.create( THREE.Mesh.prototype );
- THREE.SkinnedMesh.prototype.constructor = THREE.SkinnedMesh;
- THREE.SkinnedMesh.prototype.bind = function( skeleton, bindMatrix ) {
- this.skeleton = skeleton;
- if ( bindMatrix === undefined ) {
- this.updateMatrixWorld( true );
- bindMatrix = this.matrixWorld;
- }
- this.bindMatrix.copy( bindMatrix );
- this.bindMatrixInverse.getInverse( bindMatrix );
- };
- THREE.SkinnedMesh.prototype.pose = function () {
- this.skeleton.pose();
- };
- THREE.SkinnedMesh.prototype.normalizeSkinWeights = function () {
- if ( this.geometry instanceof THREE.Geometry ) {
- for ( var i = 0; i < this.geometry.skinIndices.length; i ++ ) {
- var sw = this.geometry.skinWeights[ i ];
- var scale = 1.0 / sw.lengthManhattan();
- if ( scale !== Infinity ) {
- sw.multiplyScalar( scale );
- } else {
- sw.set( 1 ); // this will be normalized by the shader anyway
- }
- }
- } else {
- // skinning weights assumed to be normalized for THREE.BufferGeometry
- }
- };
- THREE.SkinnedMesh.prototype.updateMatrixWorld = function( force ) {
- THREE.Mesh.prototype.updateMatrixWorld.call( this, true );
- if ( this.bindMode === "attached" ) {
- this.bindMatrixInverse.getInverse( this.matrixWorld );
- } else if ( this.bindMode === "detached" ) {
- this.bindMatrixInverse.getInverse( this.bindMatrix );
- } else {
- console.warn( 'THREE.SkinnedMesh unrecognized bindMode: ' + this.bindMode );
- }
- };
- THREE.SkinnedMesh.prototype.clone = function() {
- var skinMesh = new THREE.SkinnedMesh( this.geometry, this.material, this.useVertexTexture );
- return skinMesh.copy( this );
- };
- THREE.SkinnedMesh.prototype.copy = function( source ) {
- THREE.Mesh.prototype.copy.call( this, source );
- return this;
- };
|