123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416 |
- function LWO2Parser( IFFParser ) {
- this.IFF = IFFParser;
- }
- LWO2Parser.prototype = {
- constructor: LWO2Parser,
- parseBlock: function () {
- this.IFF.debugger.offset = this.IFF.reader.offset;
- this.IFF.debugger.closeForms();
- var blockID = this.IFF.reader.getIDTag();
- var length = this.IFF.reader.getUint32(); // size of data in bytes
- if ( length > this.IFF.reader.dv.byteLength - this.IFF.reader.offset ) {
- this.IFF.reader.offset -= 4;
- length = this.IFF.reader.getUint16();
- }
- this.IFF.debugger.dataOffset = this.IFF.reader.offset;
- this.IFF.debugger.length = length;
- // Data types may be found in either LWO2 OR LWO3 spec
- switch ( blockID ) {
- case 'FORM': // form blocks may consist of sub -chunks or sub-forms
- this.IFF.parseForm( length );
- break;
- // SKIPPED CHUNKS
- // if break; is called directly, the position in the lwoTree is not created
- // any sub chunks and forms are added to the parent form instead
- // MISC skipped
- case 'ICON': // Thumbnail Icon Image
- case 'VMPA': // Vertex Map Parameter
- case 'BBOX': // bounding box
- // case 'VMMD':
- // case 'VTYP':
- // normal maps can be specified, normally on models imported from other applications. Currently ignored
- case 'NORM':
- // ENVL FORM skipped
- case 'PRE ':
- case 'POST':
- case 'KEY ':
- case 'SPAN':
- // CLIP FORM skipped
- case 'TIME':
- case 'CLRS':
- case 'CLRA':
- case 'FILT':
- case 'DITH':
- case 'CONT':
- case 'BRIT':
- case 'SATR':
- case 'HUE ':
- case 'GAMM':
- case 'NEGA':
- case 'IFLT':
- case 'PFLT':
- // Image Map Layer skipped
- case 'PROJ':
- case 'AXIS':
- case 'AAST':
- case 'PIXB':
- case 'AUVO':
- case 'STCK':
- // Procedural Textures skipped
- case 'PROC':
- case 'VALU':
- case 'FUNC':
- // Gradient Textures skipped
- case 'PNAM':
- case 'INAM':
- case 'GRST':
- case 'GREN':
- case 'GRPT':
- case 'FKEY':
- case 'IKEY':
- // Texture Mapping Form skipped
- case 'CSYS':
- // Surface CHUNKs skipped
- case 'OPAQ': // top level 'opacity' checkbox
- case 'CMAP': // clip map
- // Surface node CHUNKS skipped
- // These mainly specify the node editor setup in LW
- case 'NLOC':
- case 'NZOM':
- case 'NVER':
- case 'NSRV':
- case 'NVSK': // unknown
- case 'NCRD':
- case 'WRPW': // image wrap w ( for cylindrical and spherical projections)
- case 'WRPH': // image wrap h
- case 'NMOD':
- case 'NSEL':
- case 'NPRW':
- case 'NPLA':
- case 'NODS':
- case 'VERS':
- case 'ENUM':
- case 'TAG ':
- case 'OPAC':
- // Car Material CHUNKS
- case 'CGMD':
- case 'CGTY':
- case 'CGST':
- case 'CGEN':
- case 'CGTS':
- case 'CGTE':
- case 'OSMP':
- case 'OMDE':
- case 'OUTR':
- case 'FLAG':
- case 'TRNL':
- case 'GLOW':
- case 'GVAL': // glow intensity
- case 'SHRP':
- case 'RFOP':
- case 'RSAN':
- case 'TROP':
- case 'RBLR':
- case 'TBLR':
- case 'CLRH':
- case 'CLRF':
- case 'ADTR':
- case 'LINE':
- case 'ALPH':
- case 'VCOL':
- case 'ENAB':
- this.IFF.debugger.skipped = true;
- this.IFF.reader.skip( length );
- break;
- case 'SURF':
- this.IFF.parseSurfaceLwo2( length );
- break;
- case 'CLIP':
- this.IFF.parseClipLwo2( length );
- break;
- // Texture node chunks (not in spec)
- case 'IPIX': // usePixelBlending
- case 'IMIP': // useMipMaps
- case 'IMOD': // imageBlendingMode
- case 'AMOD': // unknown
- case 'IINV': // imageInvertAlpha
- case 'INCR': // imageInvertColor
- case 'IAXS': // imageAxis ( for non-UV maps)
- case 'IFOT': // imageFallofType
- case 'ITIM': // timing for animated textures
- case 'IWRL':
- case 'IUTI':
- case 'IINX':
- case 'IINY':
- case 'IINZ':
- case 'IREF': // possibly a VX for reused texture nodes
- if ( length === 4 ) this.IFF.currentNode[ blockID ] = this.IFF.reader.getInt32();
- else this.IFF.reader.skip( length );
- break;
- case 'OTAG':
- this.IFF.parseObjectTag();
- break;
- case 'LAYR':
- this.IFF.parseLayer( length );
- break;
- case 'PNTS':
- this.IFF.parsePoints( length );
- break;
- case 'VMAP':
- this.IFF.parseVertexMapping( length );
- break;
- case 'AUVU':
- case 'AUVN':
- this.IFF.reader.skip( length - 1 );
- this.IFF.reader.getVariableLengthIndex(); // VX
- break;
- case 'POLS':
- this.IFF.parsePolygonList( length );
- break;
- case 'TAGS':
- this.IFF.parseTagStrings( length );
- break;
- case 'PTAG':
- this.IFF.parsePolygonTagMapping( length );
- break;
- case 'VMAD':
- this.IFF.parseVertexMapping( length, true );
- break;
- // Misc CHUNKS
- case 'DESC': // Description Line
- this.IFF.currentForm.description = this.IFF.reader.getString();
- break;
- case 'TEXT':
- case 'CMNT':
- case 'NCOM':
- this.IFF.currentForm.comment = this.IFF.reader.getString();
- break;
- // Envelope Form
- case 'NAME':
- this.IFF.currentForm.channelName = this.IFF.reader.getString();
- break;
- // Image Map Layer
- case 'WRAP':
- this.IFF.currentForm.wrap = { w: this.IFF.reader.getUint16(), h: this.IFF.reader.getUint16() };
- break;
- case 'IMAG':
- var index = this.IFF.reader.getVariableLengthIndex();
- this.IFF.currentForm.imageIndex = index;
- break;
- // Texture Mapping Form
- case 'OREF':
- this.IFF.currentForm.referenceObject = this.IFF.reader.getString();
- break;
- case 'ROID':
- this.IFF.currentForm.referenceObjectID = this.IFF.reader.getUint32();
- break;
- // Surface Blocks
- case 'SSHN':
- this.IFF.currentSurface.surfaceShaderName = this.IFF.reader.getString();
- break;
- case 'AOVN':
- this.IFF.currentSurface.surfaceCustomAOVName = this.IFF.reader.getString();
- break;
- // Nodal Blocks
- case 'NSTA':
- this.IFF.currentForm.disabled = this.IFF.reader.getUint16();
- break;
- case 'NRNM':
- this.IFF.currentForm.realName = this.IFF.reader.getString();
- break;
- case 'NNME':
- this.IFF.currentForm.refName = this.IFF.reader.getString();
- this.IFF.currentSurface.nodes[ this.IFF.currentForm.refName ] = this.IFF.currentForm;
- break;
- // Nodal Blocks : connections
- case 'INME':
- if ( ! this.IFF.currentForm.nodeName ) this.IFF.currentForm.nodeName = [];
- this.IFF.currentForm.nodeName.push( this.IFF.reader.getString() );
- break;
- case 'IINN':
- if ( ! this.IFF.currentForm.inputNodeName ) this.IFF.currentForm.inputNodeName = [];
- this.IFF.currentForm.inputNodeName.push( this.IFF.reader.getString() );
- break;
- case 'IINM':
- if ( ! this.IFF.currentForm.inputName ) this.IFF.currentForm.inputName = [];
- this.IFF.currentForm.inputName.push( this.IFF.reader.getString() );
- break;
- case 'IONM':
- if ( ! this.IFF.currentForm.inputOutputName ) this.IFF.currentForm.inputOutputName = [];
- this.IFF.currentForm.inputOutputName.push( this.IFF.reader.getString() );
- break;
- case 'FNAM':
- this.IFF.currentForm.fileName = this.IFF.reader.getString();
- break;
- case 'CHAN': // NOTE: ENVL Forms may also have CHAN chunk, however ENVL is currently ignored
- if ( length === 4 ) this.IFF.currentForm.textureChannel = this.IFF.reader.getIDTag();
- else this.IFF.reader.skip( length );
- break;
- // LWO2 Spec chunks: these are needed since the SURF FORMs are often in LWO2 format
- case 'SMAN':
- var maxSmoothingAngle = this.IFF.reader.getFloat32();
- this.IFF.currentSurface.attributes.smooth = ( maxSmoothingAngle < 0 ) ? false : true;
- break;
- // LWO2: Basic Surface Parameters
- case 'COLR':
- this.IFF.currentSurface.attributes.Color = { value: this.IFF.reader.getFloat32Array( 3 ) };
- this.IFF.reader.skip( 2 ); // VX: envelope
- break;
- case 'LUMI':
- this.IFF.currentSurface.attributes.Luminosity = { value: this.IFF.reader.getFloat32() };
- this.IFF.reader.skip( 2 );
- break;
- case 'SPEC':
- this.IFF.currentSurface.attributes.Specular = { value: this.IFF.reader.getFloat32() };
- this.IFF.reader.skip( 2 );
- break;
- case 'DIFF':
- this.IFF.currentSurface.attributes.Diffuse = { value: this.IFF.reader.getFloat32() };
- this.IFF.reader.skip( 2 );
- break;
- case 'REFL':
- this.IFF.currentSurface.attributes.Reflection = { value: this.IFF.reader.getFloat32() };
- this.IFF.reader.skip( 2 );
- break;
- case 'GLOS':
- this.IFF.currentSurface.attributes.Glossiness = { value: this.IFF.reader.getFloat32() };
- this.IFF.reader.skip( 2 );
- break;
- case 'TRAN':
- this.IFF.currentSurface.attributes.opacity = this.IFF.reader.getFloat32();
- this.IFF.reader.skip( 2 );
- break;
- case 'BUMP':
- this.IFF.currentSurface.attributes.bumpStrength = this.IFF.reader.getFloat32();
- this.IFF.reader.skip( 2 );
- break;
- case 'SIDE':
- this.IFF.currentSurface.attributes.side = this.IFF.reader.getUint16();
- break;
- case 'RIMG':
- this.IFF.currentSurface.attributes.reflectionMap = this.IFF.reader.getVariableLengthIndex();
- break;
- case 'RIND':
- this.IFF.currentSurface.attributes.refractiveIndex = this.IFF.reader.getFloat32();
- this.IFF.reader.skip( 2 );
- break;
- case 'TIMG':
- this.IFF.currentSurface.attributes.refractionMap = this.IFF.reader.getVariableLengthIndex();
- break;
- case 'IMAP':
- this.IFF.reader.skip( 2 );
- break;
- case 'TMAP':
- this.IFF.debugger.skipped = true;
- this.IFF.reader.skip( length ); // needs implementing
- break;
- case 'IUVI': // uv channel name
- this.IFF.currentNode.UVChannel = this.IFF.reader.getString( length );
- break;
- case 'IUTL': // widthWrappingMode: 0 = Reset, 1 = Repeat, 2 = Mirror, 3 = Edge
- this.IFF.currentNode.widthWrappingMode = this.IFF.reader.getUint32();
- break;
- case 'IVTL': // heightWrappingMode
- this.IFF.currentNode.heightWrappingMode = this.IFF.reader.getUint32();
- break;
- // LWO2 USE
- case 'BLOK':
- // skip
- break;
- default:
- this.IFF.parseUnknownCHUNK( blockID, length );
- }
- if ( blockID != 'FORM' ) {
- this.IFF.debugger.node = 1;
- this.IFF.debugger.nodeID = blockID;
- this.IFF.debugger.log();
- }
- if ( this.IFF.reader.offset >= this.IFF.currentFormEnd ) {
- this.IFF.currentForm = this.IFF.parentForm;
- }
- }
- };
- export { LWO2Parser };
|