Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
21 changes: 9 additions & 12 deletions examples/js/loaders/ColladaLoader2.js
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,9 @@
THREE.ColladaLoader = function ( manager ) {

this.manager = ( manager !== undefined ) ? manager : THREE.DefaultLoadingManager;
this.options = {
convertUpAxis: false
};

};

Expand All @@ -30,16 +33,6 @@ THREE.ColladaLoader.prototype = {

},

options: {

set convertUpAxis( value ) {

console.log( 'THREE.ColladaLoader.options.convertUpAxis: TODO' );

}

},

setCrossOrigin: function ( value ) {

this.crossOrigin = value;
Expand Down Expand Up @@ -2660,9 +2653,13 @@ THREE.ColladaLoader.prototype = {

var scene = parseScene( getElementsByTagName( collada, 'scene' )[ 0 ] );

if ( asset.upAxis === 'Z_UP' ) {
if ( this.options.convertUpAxis === true ) {

if ( asset.upAxis === 'Z_UP' ) {

scene.rotation.x = - Math.PI / 2;
THREE.SceneUtils.convertFromZUp( scene, animations );

}

}

Expand Down
193 changes: 193 additions & 0 deletions src/extras/SceneUtils.js
Original file line number Diff line number Diff line change
@@ -1,9 +1,13 @@
import { Vector3 } from '../math/Vector3';
import { Quaternion } from '../math/Quaternion';
import { Matrix4 } from '../math/Matrix4';
import { Mesh } from '../objects/Mesh';
import { Group } from '../objects/Group';
import { PropertyBinding } from '../animation/PropertyBinding';

/**
* @author alteredq / http://alteredqualia.com/
* @author Mugen87 / https://github.com/Mugen87
*/

var SceneUtils = {
Expand Down Expand Up @@ -37,9 +41,198 @@ var SceneUtils = {
scene.remove( child );
parent.add( child );

},

convertFromZUp: function ( root, animations ) {

// this change-of-basis matrix performs a change-of basis from right-handed Z-up to right-handed Y-up
// for a given object hierarchy and animations (optional)

var matrix = new Matrix4().set(
1, 0, 0, 0,
0, 0, 1, 0,
0, - 1, 0, 0,
0, 0, 0, 1
);

var converter = new BasisConverter( matrix );
converter.convert( root, animations );

}

};

function BasisConverter( matrix ) {

// change-of-basis matrix

this.matrix = matrix;

// because the change-of-basis matrix is orthonormal, the inverse of
// this.matrix is its transpose

this.matrixInverse = this.matrix.clone().transpose();

}

Object.assign( BasisConverter.prototype, {

convert: function ( root, animations ) {

var scope = this;

root.traverse( function( object ) {

// ensure matrix is up to date

object.updateMatrix();

// convert position, quaternion, scale

scope.convertMatrix4( object.matrix );
object.matrix.decompose( object.position, object.quaternion, object.scale );

// geometry

var geometry = object.geometry;

if ( geometry !== undefined && geometry.isBufferGeometry === true ) {

var position = geometry.attributes.position;
var normal = geometry.attributes.normal;

if ( position !== null ) scope.matrix.applyToBufferAttribute( position );

// the change-of-basis matrix contains no non-uniform scaling

if ( normal !== null ) scope.matrix.applyToBufferAttribute( normal );

}

// skinned mesh

if ( object.isSkinnedMesh ) {

scope.convertMatrix4( object.bindMatrix );
scope.convertMatrix4( object.bindMatrixInverse );

var boneInverses = object.skeleton.boneInverses;

for ( var i = 0, il = boneInverses.length; i < il; i ++ ) {

scope.convertMatrix4( boneInverses[ i ] );

}

// bones are already converted within the scene hierarchy

}

} );

// animations

if ( animations !== undefined ) {

for ( var i = 0, il = animations.length; i < il; i ++ ) {

var clip = animations[ i ];
var tracks = clip.tracks;

for ( var j = 0, jl = tracks.length; j < jl; j ++ ) {

this.convertKeyframeTrack( tracks[ j ] );

}

}

}

},

convertMatrix4: function( matrix ) {

return matrix.premultiply( this.matrix ).multiply( this.matrixInverse );

},

convertKeyframeTrack: function() {

var vector = new Vector3();
var quaternion = new Quaternion();
var rotationMatrix = new Matrix4();

return function convertKeyframeTrack( track ) {

var result = PropertyBinding.parseTrackName( track.name );
var propertyName = result.propertyName;

var values = track.values;
var times = track.times;
var stride = values.length / times.length;

var i, il, j, jl;

switch ( propertyName ) {

case 'position':

for ( i = 0, il = values.length; i < il; i += stride ) {

vector.fromArray( values, i ).applyMatrix4( this.matrix );

for ( j = 0, jl = stride; j < jl; j ++ ) {

values[ i + j ] = vector.getComponent( j );

}

}

break;

case 'scale':

for ( i = 0, il = values.length; i < il; i += stride ) {

vector.fromArray( values, i ).applyMatrix4( this.matrix );

for ( j = 0, jl = stride; j < jl; j ++ ) {

values[ i + j ] = Math.abs( vector.getComponent( j ) );

}

}

break;

case 'quaternion':

for ( i = 0, il = values.length; i < il; i += stride ) {

quaternion.fromArray( values, i );
rotationMatrix.makeRotationFromQuaternion( quaternion );
this.convertMatrix4( rotationMatrix );
quaternion.setFromRotationMatrix( rotationMatrix );

values[ i + 0 ] = quaternion.x;
values[ i + 1 ] = quaternion.y;
values[ i + 2 ] = quaternion.z;
values[ i + 3 ] = quaternion.w;

}

break;

}

};

} (),

} );


export { SceneUtils };