three-stdlib 2.32.0 → 2.32.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/_polyfill/uv1.cjs +6 -0
- package/_polyfill/uv1.cjs.map +1 -0
- package/_polyfill/uv1.d.ts +5 -0
- package/_polyfill/uv1.js +6 -0
- package/_polyfill/uv1.js.map +1 -0
- package/exporters/ColladaExporter.cjs +3 -2
- package/exporters/ColladaExporter.cjs.map +1 -1
- package/exporters/ColladaExporter.js +3 -2
- package/exporters/ColladaExporter.js.map +1 -1
- package/lines/LineSegments2.cjs +3 -2
- package/lines/LineSegments2.cjs.map +1 -1
- package/lines/LineSegments2.js +3 -2
- package/lines/LineSegments2.js.map +1 -1
- package/loaders/ColladaLoader.cjs +7 -6
- package/loaders/ColladaLoader.cjs.map +1 -1
- package/loaders/ColladaLoader.js +7 -6
- package/loaders/ColladaLoader.js.map +1 -1
- package/loaders/FBXLoader.cjs +4 -4
- package/loaders/FBXLoader.cjs.map +1 -1
- package/loaders/FBXLoader.js +4 -4
- package/loaders/FBXLoader.js.map +1 -1
- package/loaders/LWOLoader.cjs +3 -1
- package/loaders/LWOLoader.cjs.map +1 -1
- package/loaders/LWOLoader.js +3 -1
- package/loaders/LWOLoader.js.map +1 -1
- package/misc/ProgressiveLightmap.cjs +12 -10
- package/misc/ProgressiveLightmap.cjs.map +1 -1
- package/misc/ProgressiveLightmap.js +12 -10
- package/misc/ProgressiveLightmap.js.map +1 -1
- package/modifiers/TessellateModifier.cjs +20 -19
- package/modifiers/TessellateModifier.cjs.map +1 -1
- package/modifiers/TessellateModifier.js +20 -19
- package/modifiers/TessellateModifier.js.map +1 -1
- package/package.json +1 -1
package/loaders/FBXLoader.js.map
CHANGED
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"file":"FBXLoader.js","sources":["../../src/loaders/FBXLoader.js"],"sourcesContent":["import {\n AmbientLight,\n AnimationClip,\n Bone,\n BufferGeometry,\n ClampToEdgeWrapping,\n Color,\n DirectionalLight,\n EquirectangularReflectionMapping,\n Euler,\n FileLoader,\n Float32BufferAttribute,\n Group,\n Line,\n LineBasicMaterial,\n Loader,\n LoaderUtils,\n MathUtils,\n Matrix3,\n Matrix4,\n Mesh,\n MeshLambertMaterial,\n MeshPhongMaterial,\n NumberKeyframeTrack,\n Object3D,\n OrthographicCamera,\n PerspectiveCamera,\n PointLight,\n PropertyBinding,\n Quaternion,\n QuaternionKeyframeTrack,\n RepeatWrapping,\n Skeleton,\n SkinnedMesh,\n SpotLight,\n Texture,\n TextureLoader,\n Uint16BufferAttribute,\n Vector3,\n Vector4,\n VectorKeyframeTrack,\n} from 'three'\nimport { unzlibSync } from 'fflate'\nimport { NURBSCurve } from '../curves/NURBSCurve'\nimport { decodeText } from '../_polyfill/LoaderUtils'\n\n/**\n * Loader loads FBX file and generates Group representing FBX scene.\n * Requires FBX file to be >= 7.0 and in ASCII or >= 6400 in Binary format\n * Versions lower than this may load but will probably have errors\n *\n * Needs Support:\n * Morph normals / blend shape normals\n *\n * FBX format references:\n * \thttps://help.autodesk.com/view/FBX/2017/ENU/?guid=__cpp_ref_index_html (C++ SDK reference)\n *\n * Binary format specification:\n *\thttps://code.blender.org/2013/08/fbx-binary-file-format-specification/\n */\n\nlet fbxTree\nlet connections\nlet sceneGraph\n\nclass FBXLoader extends Loader {\n constructor(manager) {\n super(manager)\n }\n\n load(url, onLoad, onProgress, onError) {\n const scope = this\n\n const path = scope.path === '' ? LoaderUtils.extractUrlBase(url) : scope.path\n\n const loader = new FileLoader(this.manager)\n loader.setPath(scope.path)\n loader.setResponseType('arraybuffer')\n loader.setRequestHeader(scope.requestHeader)\n loader.setWithCredentials(scope.withCredentials)\n\n loader.load(\n url,\n function (buffer) {\n try {\n onLoad(scope.parse(buffer, path))\n } catch (e) {\n if (onError) {\n onError(e)\n } else {\n console.error(e)\n }\n\n scope.manager.itemError(url)\n }\n },\n onProgress,\n onError,\n )\n }\n\n parse(FBXBuffer, path) {\n if (isFbxFormatBinary(FBXBuffer)) {\n fbxTree = new BinaryParser().parse(FBXBuffer)\n } else {\n const FBXText = convertArrayBufferToString(FBXBuffer)\n\n if (!isFbxFormatASCII(FBXText)) {\n throw new Error('THREE.FBXLoader: Unknown format.')\n }\n\n if (getFbxVersion(FBXText) < 7000) {\n throw new Error('THREE.FBXLoader: FBX version not supported, FileVersion: ' + getFbxVersion(FBXText))\n }\n\n fbxTree = new TextParser().parse(FBXText)\n }\n\n // console.log( fbxTree );\n\n const textureLoader = new TextureLoader(this.manager)\n .setPath(this.resourcePath || path)\n .setCrossOrigin(this.crossOrigin)\n\n return new FBXTreeParser(textureLoader, this.manager).parse(fbxTree)\n }\n}\n\n// Parse the FBXTree object returned by the BinaryParser or TextParser and return a Group\nclass FBXTreeParser {\n constructor(textureLoader, manager) {\n this.textureLoader = textureLoader\n this.manager = manager\n }\n\n parse() {\n connections = this.parseConnections()\n\n const images = this.parseImages()\n const textures = this.parseTextures(images)\n const materials = this.parseMaterials(textures)\n const deformers = this.parseDeformers()\n const geometryMap = new GeometryParser().parse(deformers)\n\n this.parseScene(deformers, geometryMap, materials)\n\n return sceneGraph\n }\n\n // Parses FBXTree.Connections which holds parent-child connections between objects (e.g. material -> texture, model->geometry )\n // and details the connection type\n parseConnections() {\n const connectionMap = new Map()\n\n if ('Connections' in fbxTree) {\n const rawConnections = fbxTree.Connections.connections\n\n rawConnections.forEach(function (rawConnection) {\n const fromID = rawConnection[0]\n const toID = rawConnection[1]\n const relationship = rawConnection[2]\n\n if (!connectionMap.has(fromID)) {\n connectionMap.set(fromID, {\n parents: [],\n children: [],\n })\n }\n\n const parentRelationship = { ID: toID, relationship: relationship }\n connectionMap.get(fromID).parents.push(parentRelationship)\n\n if (!connectionMap.has(toID)) {\n connectionMap.set(toID, {\n parents: [],\n children: [],\n })\n }\n\n const childRelationship = { ID: fromID, relationship: relationship }\n connectionMap.get(toID).children.push(childRelationship)\n })\n }\n\n return connectionMap\n }\n\n // Parse FBXTree.Objects.Video for embedded image data\n // These images are connected to textures in FBXTree.Objects.Textures\n // via FBXTree.Connections.\n parseImages() {\n const images = {}\n const blobs = {}\n\n if ('Video' in fbxTree.Objects) {\n const videoNodes = fbxTree.Objects.Video\n\n for (const nodeID in videoNodes) {\n const videoNode = videoNodes[nodeID]\n\n const id = parseInt(nodeID)\n\n images[id] = videoNode.RelativeFilename || videoNode.Filename\n\n // raw image data is in videoNode.Content\n if ('Content' in videoNode) {\n const arrayBufferContent = videoNode.Content instanceof ArrayBuffer && videoNode.Content.byteLength > 0\n const base64Content = typeof videoNode.Content === 'string' && videoNode.Content !== ''\n\n if (arrayBufferContent || base64Content) {\n const image = this.parseImage(videoNodes[nodeID])\n\n blobs[videoNode.RelativeFilename || videoNode.Filename] = image\n }\n }\n }\n }\n\n for (const id in images) {\n const filename = images[id]\n\n if (blobs[filename] !== undefined) images[id] = blobs[filename]\n else images[id] = images[id].split('\\\\').pop()\n }\n\n return images\n }\n\n // Parse embedded image data in FBXTree.Video.Content\n parseImage(videoNode) {\n const content = videoNode.Content\n const fileName = videoNode.RelativeFilename || videoNode.Filename\n const extension = fileName.slice(fileName.lastIndexOf('.') + 1).toLowerCase()\n\n let type\n\n switch (extension) {\n case 'bmp':\n type = 'image/bmp'\n break\n\n case 'jpg':\n case 'jpeg':\n type = 'image/jpeg'\n break\n\n case 'png':\n type = 'image/png'\n break\n\n case 'tif':\n type = 'image/tiff'\n break\n\n case 'tga':\n if (this.manager.getHandler('.tga') === null) {\n console.warn('FBXLoader: TGA loader not found, skipping ', fileName)\n }\n\n type = 'image/tga'\n break\n\n default:\n console.warn('FBXLoader: Image type \"' + extension + '\" is not supported.')\n return\n }\n\n if (typeof content === 'string') {\n // ASCII format\n\n return 'data:' + type + ';base64,' + content\n } else {\n // Binary Format\n\n const array = new Uint8Array(content)\n return window.URL.createObjectURL(new Blob([array], { type: type }))\n }\n }\n\n // Parse nodes in FBXTree.Objects.Texture\n // These contain details such as UV scaling, cropping, rotation etc and are connected\n // to images in FBXTree.Objects.Video\n parseTextures(images) {\n const textureMap = new Map()\n\n if ('Texture' in fbxTree.Objects) {\n const textureNodes = fbxTree.Objects.Texture\n for (const nodeID in textureNodes) {\n const texture = this.parseTexture(textureNodes[nodeID], images)\n textureMap.set(parseInt(nodeID), texture)\n }\n }\n\n return textureMap\n }\n\n // Parse individual node in FBXTree.Objects.Texture\n parseTexture(textureNode, images) {\n const texture = this.loadTexture(textureNode, images)\n\n texture.ID = textureNode.id\n\n texture.name = textureNode.attrName\n\n const wrapModeU = textureNode.WrapModeU\n const wrapModeV = textureNode.WrapModeV\n\n const valueU = wrapModeU !== undefined ? wrapModeU.value : 0\n const valueV = wrapModeV !== undefined ? wrapModeV.value : 0\n\n // http://download.autodesk.com/us/fbx/SDKdocs/FBX_SDK_Help/files/fbxsdkref/class_k_fbx_texture.html#889640e63e2e681259ea81061b85143a\n // 0: repeat(default), 1: clamp\n\n texture.wrapS = valueU === 0 ? RepeatWrapping : ClampToEdgeWrapping\n texture.wrapT = valueV === 0 ? RepeatWrapping : ClampToEdgeWrapping\n\n if ('Scaling' in textureNode) {\n const values = textureNode.Scaling.value\n\n texture.repeat.x = values[0]\n texture.repeat.y = values[1]\n }\n\n return texture\n }\n\n // load a texture specified as a blob or data URI, or via an external URL using TextureLoader\n loadTexture(textureNode, images) {\n let fileName\n\n const currentPath = this.textureLoader.path\n\n const children = connections.get(textureNode.id).children\n\n if (children !== undefined && children.length > 0 && images[children[0].ID] !== undefined) {\n fileName = images[children[0].ID]\n\n if (fileName.indexOf('blob:') === 0 || fileName.indexOf('data:') === 0) {\n this.textureLoader.setPath(undefined)\n }\n }\n\n let texture\n\n const extension = textureNode.FileName.slice(-3).toLowerCase()\n\n if (extension === 'tga') {\n const loader = this.manager.getHandler('.tga')\n\n if (loader === null) {\n console.warn('FBXLoader: TGA loader not found, creating placeholder texture for', textureNode.RelativeFilename)\n texture = new Texture()\n } else {\n loader.setPath(this.textureLoader.path)\n texture = loader.load(fileName)\n }\n } else if (extension === 'psd') {\n console.warn(\n 'FBXLoader: PSD textures are not supported, creating placeholder texture for',\n textureNode.RelativeFilename,\n )\n texture = new Texture()\n } else {\n texture = this.textureLoader.load(fileName)\n }\n\n this.textureLoader.setPath(currentPath)\n\n return texture\n }\n\n // Parse nodes in FBXTree.Objects.Material\n parseMaterials(textureMap) {\n const materialMap = new Map()\n\n if ('Material' in fbxTree.Objects) {\n const materialNodes = fbxTree.Objects.Material\n\n for (const nodeID in materialNodes) {\n const material = this.parseMaterial(materialNodes[nodeID], textureMap)\n\n if (material !== null) materialMap.set(parseInt(nodeID), material)\n }\n }\n\n return materialMap\n }\n\n // Parse single node in FBXTree.Objects.Material\n // Materials are connected to texture maps in FBXTree.Objects.Textures\n // FBX format currently only supports Lambert and Phong shading models\n parseMaterial(materialNode, textureMap) {\n const ID = materialNode.id\n const name = materialNode.attrName\n let type = materialNode.ShadingModel\n\n // Case where FBX wraps shading model in property object.\n if (typeof type === 'object') {\n type = type.value\n }\n\n // Ignore unused materials which don't have any connections.\n if (!connections.has(ID)) return null\n\n const parameters = this.parseParameters(materialNode, textureMap, ID)\n\n let material\n\n switch (type.toLowerCase()) {\n case 'phong':\n material = new MeshPhongMaterial()\n break\n case 'lambert':\n material = new MeshLambertMaterial()\n break\n default:\n console.warn('THREE.FBXLoader: unknown material type \"%s\". Defaulting to MeshPhongMaterial.', type)\n material = new MeshPhongMaterial()\n break\n }\n\n material.setValues(parameters)\n material.name = name\n\n return material\n }\n\n // Parse FBX material and return parameters suitable for a three.js material\n // Also parse the texture map and return any textures associated with the material\n parseParameters(materialNode, textureMap, ID) {\n const parameters = {}\n\n if (materialNode.BumpFactor) {\n parameters.bumpScale = materialNode.BumpFactor.value\n }\n\n if (materialNode.Diffuse) {\n parameters.color = new Color().fromArray(materialNode.Diffuse.value)\n } else if (\n materialNode.DiffuseColor &&\n (materialNode.DiffuseColor.type === 'Color' || materialNode.DiffuseColor.type === 'ColorRGB')\n ) {\n // The blender exporter exports diffuse here instead of in materialNode.Diffuse\n parameters.color = new Color().fromArray(materialNode.DiffuseColor.value)\n }\n\n if (materialNode.DisplacementFactor) {\n parameters.displacementScale = materialNode.DisplacementFactor.value\n }\n\n if (materialNode.Emissive) {\n parameters.emissive = new Color().fromArray(materialNode.Emissive.value)\n } else if (\n materialNode.EmissiveColor &&\n (materialNode.EmissiveColor.type === 'Color' || materialNode.EmissiveColor.type === 'ColorRGB')\n ) {\n // The blender exporter exports emissive color here instead of in materialNode.Emissive\n parameters.emissive = new Color().fromArray(materialNode.EmissiveColor.value)\n }\n\n if (materialNode.EmissiveFactor) {\n parameters.emissiveIntensity = parseFloat(materialNode.EmissiveFactor.value)\n }\n\n if (materialNode.Opacity) {\n parameters.opacity = parseFloat(materialNode.Opacity.value)\n }\n\n if (parameters.opacity < 1.0) {\n parameters.transparent = true\n }\n\n if (materialNode.ReflectionFactor) {\n parameters.reflectivity = materialNode.ReflectionFactor.value\n }\n\n if (materialNode.Shininess) {\n parameters.shininess = materialNode.Shininess.value\n }\n\n if (materialNode.Specular) {\n parameters.specular = new Color().fromArray(materialNode.Specular.value)\n } else if (materialNode.SpecularColor && materialNode.SpecularColor.type === 'Color') {\n // The blender exporter exports specular color here instead of in materialNode.Specular\n parameters.specular = new Color().fromArray(materialNode.SpecularColor.value)\n }\n\n const scope = this\n connections.get(ID).children.forEach(function (child) {\n const type = child.relationship\n\n switch (type) {\n case 'Bump':\n parameters.bumpMap = scope.getTexture(textureMap, child.ID)\n break\n\n case 'Maya|TEX_ao_map':\n parameters.aoMap = scope.getTexture(textureMap, child.ID)\n break\n\n case 'DiffuseColor':\n case 'Maya|TEX_color_map':\n parameters.map = scope.getTexture(textureMap, child.ID)\n if (parameters.map !== undefined) {\n if ('colorSpace' in parameters.map) parameters.map.colorSpace = 'srgb'\n else parameters.map.encoding = 3001 // sRGBEncoding\n }\n\n break\n\n case 'DisplacementColor':\n parameters.displacementMap = scope.getTexture(textureMap, child.ID)\n break\n\n case 'EmissiveColor':\n parameters.emissiveMap = scope.getTexture(textureMap, child.ID)\n if (parameters.emissiveMap !== undefined) {\n if ('colorSpace' in parameters.emissiveMap) parameters.emissiveMap.colorSpace = 'srgb'\n else parameters.emissiveMap.encoding = 3001 // sRGBEncoding\n }\n\n break\n\n case 'NormalMap':\n case 'Maya|TEX_normal_map':\n parameters.normalMap = scope.getTexture(textureMap, child.ID)\n break\n\n case 'ReflectionColor':\n parameters.envMap = scope.getTexture(textureMap, child.ID)\n if (parameters.envMap !== undefined) {\n parameters.envMap.mapping = EquirectangularReflectionMapping\n\n if ('colorSpace' in parameters.envMap) parameters.envMap.colorSpace = 'srgb'\n else parameters.envMap.encoding = 3001 // sRGBEncoding\n }\n\n break\n\n case 'SpecularColor':\n parameters.specularMap = scope.getTexture(textureMap, child.ID)\n if (parameters.specularMap !== undefined) {\n if ('colorSpace' in parameters.specularMap) parameters.specularMap.colorSpace = 'srgb'\n else parameters.specularMap.encoding = 3001 // sRGBEncoding\n }\n\n break\n\n case 'TransparentColor':\n case 'TransparencyFactor':\n parameters.alphaMap = scope.getTexture(textureMap, child.ID)\n parameters.transparent = true\n break\n\n case 'AmbientColor':\n case 'ShininessExponent': // AKA glossiness map\n case 'SpecularFactor': // AKA specularLevel\n case 'VectorDisplacementColor': // NOTE: Seems to be a copy of DisplacementColor\n default:\n console.warn('THREE.FBXLoader: %s map is not supported in three.js, skipping texture.', type)\n break\n }\n })\n\n return parameters\n }\n\n // get a texture from the textureMap for use by a material.\n getTexture(textureMap, id) {\n // if the texture is a layered texture, just use the first layer and issue a warning\n if ('LayeredTexture' in fbxTree.Objects && id in fbxTree.Objects.LayeredTexture) {\n console.warn('THREE.FBXLoader: layered textures are not supported in three.js. Discarding all but first layer.')\n id = connections.get(id).children[0].ID\n }\n\n return textureMap.get(id)\n }\n\n // Parse nodes in FBXTree.Objects.Deformer\n // Deformer node can contain skinning or Vertex Cache animation data, however only skinning is supported here\n // Generates map of Skeleton-like objects for use later when generating and binding skeletons.\n parseDeformers() {\n const skeletons = {}\n const morphTargets = {}\n\n if ('Deformer' in fbxTree.Objects) {\n const DeformerNodes = fbxTree.Objects.Deformer\n\n for (const nodeID in DeformerNodes) {\n const deformerNode = DeformerNodes[nodeID]\n\n const relationships = connections.get(parseInt(nodeID))\n\n if (deformerNode.attrType === 'Skin') {\n const skeleton = this.parseSkeleton(relationships, DeformerNodes)\n skeleton.ID = nodeID\n\n if (relationships.parents.length > 1) {\n console.warn('THREE.FBXLoader: skeleton attached to more than one geometry is not supported.')\n }\n skeleton.geometryID = relationships.parents[0].ID\n\n skeletons[nodeID] = skeleton\n } else if (deformerNode.attrType === 'BlendShape') {\n const morphTarget = {\n id: nodeID,\n }\n\n morphTarget.rawTargets = this.parseMorphTargets(relationships, DeformerNodes)\n morphTarget.id = nodeID\n\n if (relationships.parents.length > 1) {\n console.warn('THREE.FBXLoader: morph target attached to more than one geometry is not supported.')\n }\n\n morphTargets[nodeID] = morphTarget\n }\n }\n }\n\n return {\n skeletons: skeletons,\n morphTargets: morphTargets,\n }\n }\n\n // Parse single nodes in FBXTree.Objects.Deformer\n // The top level skeleton node has type 'Skin' and sub nodes have type 'Cluster'\n // Each skin node represents a skeleton and each cluster node represents a bone\n parseSkeleton(relationships, deformerNodes) {\n const rawBones = []\n\n relationships.children.forEach(function (child) {\n const boneNode = deformerNodes[child.ID]\n\n if (boneNode.attrType !== 'Cluster') return\n\n const rawBone = {\n ID: child.ID,\n indices: [],\n weights: [],\n transformLink: new Matrix4().fromArray(boneNode.TransformLink.a),\n // transform: new Matrix4().fromArray( boneNode.Transform.a ),\n // linkMode: boneNode.Mode,\n }\n\n if ('Indexes' in boneNode) {\n rawBone.indices = boneNode.Indexes.a\n rawBone.weights = boneNode.Weights.a\n }\n\n rawBones.push(rawBone)\n })\n\n return {\n rawBones: rawBones,\n bones: [],\n }\n }\n\n // The top level morph deformer node has type \"BlendShape\" and sub nodes have type \"BlendShapeChannel\"\n parseMorphTargets(relationships, deformerNodes) {\n const rawMorphTargets = []\n\n for (let i = 0; i < relationships.children.length; i++) {\n const child = relationships.children[i]\n\n const morphTargetNode = deformerNodes[child.ID]\n\n const rawMorphTarget = {\n name: morphTargetNode.attrName,\n initialWeight: morphTargetNode.DeformPercent,\n id: morphTargetNode.id,\n fullWeights: morphTargetNode.FullWeights.a,\n }\n\n if (morphTargetNode.attrType !== 'BlendShapeChannel') return\n\n rawMorphTarget.geoID = connections.get(parseInt(child.ID)).children.filter(function (child) {\n return child.relationship === undefined\n })[0].ID\n\n rawMorphTargets.push(rawMorphTarget)\n }\n\n return rawMorphTargets\n }\n\n // create the main Group() to be returned by the loader\n parseScene(deformers, geometryMap, materialMap) {\n sceneGraph = new Group()\n\n const modelMap = this.parseModels(deformers.skeletons, geometryMap, materialMap)\n\n const modelNodes = fbxTree.Objects.Model\n\n const scope = this\n modelMap.forEach(function (model) {\n const modelNode = modelNodes[model.ID]\n scope.setLookAtProperties(model, modelNode)\n\n const parentConnections = connections.get(model.ID).parents\n\n parentConnections.forEach(function (connection) {\n const parent = modelMap.get(connection.ID)\n if (parent !== undefined) parent.add(model)\n })\n\n if (model.parent === null) {\n sceneGraph.add(model)\n }\n })\n\n this.bindSkeleton(deformers.skeletons, geometryMap, modelMap)\n\n this.createAmbientLight()\n\n sceneGraph.traverse(function (node) {\n if (node.userData.transformData) {\n if (node.parent) {\n node.userData.transformData.parentMatrix = node.parent.matrix\n node.userData.transformData.parentMatrixWorld = node.parent.matrixWorld\n }\n\n const transform = generateTransform(node.userData.transformData)\n\n node.applyMatrix4(transform)\n node.updateWorldMatrix()\n }\n })\n\n const animations = new AnimationParser().parse()\n\n // if all the models where already combined in a single group, just return that\n if (sceneGraph.children.length === 1 && sceneGraph.children[0].isGroup) {\n sceneGraph.children[0].animations = animations\n sceneGraph = sceneGraph.children[0]\n }\n\n sceneGraph.animations = animations\n }\n\n // parse nodes in FBXTree.Objects.Model\n parseModels(skeletons, geometryMap, materialMap) {\n const modelMap = new Map()\n const modelNodes = fbxTree.Objects.Model\n\n for (const nodeID in modelNodes) {\n const id = parseInt(nodeID)\n const node = modelNodes[nodeID]\n const relationships = connections.get(id)\n\n let model = this.buildSkeleton(relationships, skeletons, id, node.attrName)\n\n if (!model) {\n switch (node.attrType) {\n case 'Camera':\n model = this.createCamera(relationships)\n break\n case 'Light':\n model = this.createLight(relationships)\n break\n case 'Mesh':\n model = this.createMesh(relationships, geometryMap, materialMap)\n break\n case 'NurbsCurve':\n model = this.createCurve(relationships, geometryMap)\n break\n case 'LimbNode':\n case 'Root':\n model = new Bone()\n break\n case 'Null':\n default:\n model = new Group()\n break\n }\n\n model.name = node.attrName ? PropertyBinding.sanitizeNodeName(node.attrName) : ''\n\n model.ID = id\n }\n\n this.getTransformData(model, node)\n modelMap.set(id, model)\n }\n\n return modelMap\n }\n\n buildSkeleton(relationships, skeletons, id, name) {\n let bone = null\n\n relationships.parents.forEach(function (parent) {\n for (const ID in skeletons) {\n const skeleton = skeletons[ID]\n\n skeleton.rawBones.forEach(function (rawBone, i) {\n if (rawBone.ID === parent.ID) {\n const subBone = bone\n bone = new Bone()\n\n bone.matrixWorld.copy(rawBone.transformLink)\n\n // set name and id here - otherwise in cases where \"subBone\" is created it will not have a name / id\n\n bone.name = name ? PropertyBinding.sanitizeNodeName(name) : ''\n bone.ID = id\n\n skeleton.bones[i] = bone\n\n // In cases where a bone is shared between multiple meshes\n // duplicate the bone here and and it as a child of the first bone\n if (subBone !== null) {\n bone.add(subBone)\n }\n }\n })\n }\n })\n\n return bone\n }\n\n // create a PerspectiveCamera or OrthographicCamera\n createCamera(relationships) {\n let model\n let cameraAttribute\n\n relationships.children.forEach(function (child) {\n const attr = fbxTree.Objects.NodeAttribute[child.ID]\n\n if (attr !== undefined) {\n cameraAttribute = attr\n }\n })\n\n if (cameraAttribute === undefined) {\n model = new Object3D()\n } else {\n let type = 0\n if (cameraAttribute.CameraProjectionType !== undefined && cameraAttribute.CameraProjectionType.value === 1) {\n type = 1\n }\n\n let nearClippingPlane = 1\n if (cameraAttribute.NearPlane !== undefined) {\n nearClippingPlane = cameraAttribute.NearPlane.value / 1000\n }\n\n let farClippingPlane = 1000\n if (cameraAttribute.FarPlane !== undefined) {\n farClippingPlane = cameraAttribute.FarPlane.value / 1000\n }\n\n let width = window.innerWidth\n let height = window.innerHeight\n\n if (cameraAttribute.AspectWidth !== undefined && cameraAttribute.AspectHeight !== undefined) {\n width = cameraAttribute.AspectWidth.value\n height = cameraAttribute.AspectHeight.value\n }\n\n const aspect = width / height\n\n let fov = 45\n if (cameraAttribute.FieldOfView !== undefined) {\n fov = cameraAttribute.FieldOfView.value\n }\n\n const focalLength = cameraAttribute.FocalLength ? cameraAttribute.FocalLength.value : null\n\n switch (type) {\n case 0: // Perspective\n model = new PerspectiveCamera(fov, aspect, nearClippingPlane, farClippingPlane)\n if (focalLength !== null) model.setFocalLength(focalLength)\n break\n\n case 1: // Orthographic\n model = new OrthographicCamera(\n -width / 2,\n width / 2,\n height / 2,\n -height / 2,\n nearClippingPlane,\n farClippingPlane,\n )\n break\n\n default:\n console.warn('THREE.FBXLoader: Unknown camera type ' + type + '.')\n model = new Object3D()\n break\n }\n }\n\n return model\n }\n\n // Create a DirectionalLight, PointLight or SpotLight\n createLight(relationships) {\n let model\n let lightAttribute\n\n relationships.children.forEach(function (child) {\n const attr = fbxTree.Objects.NodeAttribute[child.ID]\n\n if (attr !== undefined) {\n lightAttribute = attr\n }\n })\n\n if (lightAttribute === undefined) {\n model = new Object3D()\n } else {\n let type\n\n // LightType can be undefined for Point lights\n if (lightAttribute.LightType === undefined) {\n type = 0\n } else {\n type = lightAttribute.LightType.value\n }\n\n let color = 0xffffff\n\n if (lightAttribute.Color !== undefined) {\n color = new Color().fromArray(lightAttribute.Color.value)\n }\n\n let intensity = lightAttribute.Intensity === undefined ? 1 : lightAttribute.Intensity.value / 100\n\n // light disabled\n if (lightAttribute.CastLightOnObject !== undefined && lightAttribute.CastLightOnObject.value === 0) {\n intensity = 0\n }\n\n let distance = 0\n if (lightAttribute.FarAttenuationEnd !== undefined) {\n if (lightAttribute.EnableFarAttenuation !== undefined && lightAttribute.EnableFarAttenuation.value === 0) {\n distance = 0\n } else {\n distance = lightAttribute.FarAttenuationEnd.value\n }\n }\n\n // TODO: could this be calculated linearly from FarAttenuationStart to FarAttenuationEnd?\n const decay = 1\n\n switch (type) {\n case 0: // Point\n model = new PointLight(color, intensity, distance, decay)\n break\n\n case 1: // Directional\n model = new DirectionalLight(color, intensity)\n break\n\n case 2: // Spot\n let angle = Math.PI / 3\n\n if (lightAttribute.InnerAngle !== undefined) {\n angle = MathUtils.degToRad(lightAttribute.InnerAngle.value)\n }\n\n let penumbra = 0\n if (lightAttribute.OuterAngle !== undefined) {\n // TODO: this is not correct - FBX calculates outer and inner angle in degrees\n // with OuterAngle > InnerAngle && OuterAngle <= Math.PI\n // while three.js uses a penumbra between (0, 1) to attenuate the inner angle\n penumbra = MathUtils.degToRad(lightAttribute.OuterAngle.value)\n penumbra = Math.max(penumbra, 1)\n }\n\n model = new SpotLight(color, intensity, distance, angle, penumbra, decay)\n break\n\n default:\n console.warn(\n 'THREE.FBXLoader: Unknown light type ' + lightAttribute.LightType.value + ', defaulting to a PointLight.',\n )\n model = new PointLight(color, intensity)\n break\n }\n\n if (lightAttribute.CastShadows !== undefined && lightAttribute.CastShadows.value === 1) {\n model.castShadow = true\n }\n }\n\n return model\n }\n\n createMesh(relationships, geometryMap, materialMap) {\n let model\n let geometry = null\n let material = null\n const materials = []\n\n // get geometry and materials(s) from connections\n relationships.children.forEach(function (child) {\n if (geometryMap.has(child.ID)) {\n geometry = geometryMap.get(child.ID)\n }\n\n if (materialMap.has(child.ID)) {\n materials.push(materialMap.get(child.ID))\n }\n })\n\n if (materials.length > 1) {\n material = materials\n } else if (materials.length > 0) {\n material = materials[0]\n } else {\n material = new MeshPhongMaterial({ color: 0xcccccc })\n materials.push(material)\n }\n\n if ('color' in geometry.attributes) {\n materials.forEach(function (material) {\n material.vertexColors = true\n })\n }\n\n if (geometry.FBX_Deformer) {\n model = new SkinnedMesh(geometry, material)\n model.normalizeSkinWeights()\n } else {\n model = new Mesh(geometry, material)\n }\n\n return model\n }\n\n createCurve(relationships, geometryMap) {\n const geometry = relationships.children.reduce(function (geo, child) {\n if (geometryMap.has(child.ID)) geo = geometryMap.get(child.ID)\n\n return geo\n }, null)\n\n // FBX does not list materials for Nurbs lines, so we'll just put our own in here.\n const material = new LineBasicMaterial({ color: 0x3300ff, linewidth: 1 })\n return new Line(geometry, material)\n }\n\n // parse the model node for transform data\n getTransformData(model, modelNode) {\n const transformData = {}\n\n if ('InheritType' in modelNode) transformData.inheritType = parseInt(modelNode.InheritType.value)\n\n if ('RotationOrder' in modelNode) transformData.eulerOrder = getEulerOrder(modelNode.RotationOrder.value)\n else transformData.eulerOrder = 'ZYX'\n\n if ('Lcl_Translation' in modelNode) transformData.translation = modelNode.Lcl_Translation.value\n\n if ('PreRotation' in modelNode) transformData.preRotation = modelNode.PreRotation.value\n if ('Lcl_Rotation' in modelNode) transformData.rotation = modelNode.Lcl_Rotation.value\n if ('PostRotation' in modelNode) transformData.postRotation = modelNode.PostRotation.value\n\n if ('Lcl_Scaling' in modelNode) transformData.scale = modelNode.Lcl_Scaling.value\n\n if ('ScalingOffset' in modelNode) transformData.scalingOffset = modelNode.ScalingOffset.value\n if ('ScalingPivot' in modelNode) transformData.scalingPivot = modelNode.ScalingPivot.value\n\n if ('RotationOffset' in modelNode) transformData.rotationOffset = modelNode.RotationOffset.value\n if ('RotationPivot' in modelNode) transformData.rotationPivot = modelNode.RotationPivot.value\n\n model.userData.transformData = transformData\n }\n\n setLookAtProperties(model, modelNode) {\n if ('LookAtProperty' in modelNode) {\n const children = connections.get(model.ID).children\n\n children.forEach(function (child) {\n if (child.relationship === 'LookAtProperty') {\n const lookAtTarget = fbxTree.Objects.Model[child.ID]\n\n if ('Lcl_Translation' in lookAtTarget) {\n const pos = lookAtTarget.Lcl_Translation.value\n\n // DirectionalLight, SpotLight\n if (model.target !== undefined) {\n model.target.position.fromArray(pos)\n sceneGraph.add(model.target)\n } else {\n // Cameras and other Object3Ds\n\n model.lookAt(new Vector3().fromArray(pos))\n }\n }\n }\n })\n }\n }\n\n bindSkeleton(skeletons, geometryMap, modelMap) {\n const bindMatrices = this.parsePoseNodes()\n\n for (const ID in skeletons) {\n const skeleton = skeletons[ID]\n\n const parents = connections.get(parseInt(skeleton.ID)).parents\n\n parents.forEach(function (parent) {\n if (geometryMap.has(parent.ID)) {\n const geoID = parent.ID\n const geoRelationships = connections.get(geoID)\n\n geoRelationships.parents.forEach(function (geoConnParent) {\n if (modelMap.has(geoConnParent.ID)) {\n const model = modelMap.get(geoConnParent.ID)\n\n model.bind(new Skeleton(skeleton.bones), bindMatrices[geoConnParent.ID])\n }\n })\n }\n })\n }\n }\n\n parsePoseNodes() {\n const bindMatrices = {}\n\n if ('Pose' in fbxTree.Objects) {\n const BindPoseNode = fbxTree.Objects.Pose\n\n for (const nodeID in BindPoseNode) {\n if (BindPoseNode[nodeID].attrType === 'BindPose' && BindPoseNode[nodeID].NbPoseNodes > 0) {\n const poseNodes = BindPoseNode[nodeID].PoseNode\n\n if (Array.isArray(poseNodes)) {\n poseNodes.forEach(function (poseNode) {\n bindMatrices[poseNode.Node] = new Matrix4().fromArray(poseNode.Matrix.a)\n })\n } else {\n bindMatrices[poseNodes.Node] = new Matrix4().fromArray(poseNodes.Matrix.a)\n }\n }\n }\n }\n\n return bindMatrices\n }\n\n // Parse ambient color in FBXTree.GlobalSettings - if it's not set to black (default), create an ambient light\n createAmbientLight() {\n if ('GlobalSettings' in fbxTree && 'AmbientColor' in fbxTree.GlobalSettings) {\n const ambientColor = fbxTree.GlobalSettings.AmbientColor.value\n const r = ambientColor[0]\n const g = ambientColor[1]\n const b = ambientColor[2]\n\n if (r !== 0 || g !== 0 || b !== 0) {\n const color = new Color(r, g, b)\n sceneGraph.add(new AmbientLight(color, 1))\n }\n }\n }\n}\n\n// parse Geometry data from FBXTree and return map of BufferGeometries\nclass GeometryParser {\n // Parse nodes in FBXTree.Objects.Geometry\n parse(deformers) {\n const geometryMap = new Map()\n\n if ('Geometry' in fbxTree.Objects) {\n const geoNodes = fbxTree.Objects.Geometry\n\n for (const nodeID in geoNodes) {\n const relationships = connections.get(parseInt(nodeID))\n const geo = this.parseGeometry(relationships, geoNodes[nodeID], deformers)\n\n geometryMap.set(parseInt(nodeID), geo)\n }\n }\n\n return geometryMap\n }\n\n // Parse single node in FBXTree.Objects.Geometry\n parseGeometry(relationships, geoNode, deformers) {\n switch (geoNode.attrType) {\n case 'Mesh':\n return this.parseMeshGeometry(relationships, geoNode, deformers)\n break\n\n case 'NurbsCurve':\n return this.parseNurbsGeometry(geoNode)\n break\n }\n }\n\n // Parse single node mesh geometry in FBXTree.Objects.Geometry\n parseMeshGeometry(relationships, geoNode, deformers) {\n const skeletons = deformers.skeletons\n const morphTargets = []\n\n const modelNodes = relationships.parents.map(function (parent) {\n return fbxTree.Objects.Model[parent.ID]\n })\n\n // don't create geometry if it is not associated with any models\n if (modelNodes.length === 0) return\n\n const skeleton = relationships.children.reduce(function (skeleton, child) {\n if (skeletons[child.ID] !== undefined) skeleton = skeletons[child.ID]\n\n return skeleton\n }, null)\n\n relationships.children.forEach(function (child) {\n if (deformers.morphTargets[child.ID] !== undefined) {\n morphTargets.push(deformers.morphTargets[child.ID])\n }\n })\n\n // Assume one model and get the preRotation from that\n // if there is more than one model associated with the geometry this may cause problems\n const modelNode = modelNodes[0]\n\n const transformData = {}\n\n if ('RotationOrder' in modelNode) transformData.eulerOrder = getEulerOrder(modelNode.RotationOrder.value)\n if ('InheritType' in modelNode) transformData.inheritType = parseInt(modelNode.InheritType.value)\n\n if ('GeometricTranslation' in modelNode) transformData.translation = modelNode.GeometricTranslation.value\n if ('GeometricRotation' in modelNode) transformData.rotation = modelNode.GeometricRotation.value\n if ('GeometricScaling' in modelNode) transformData.scale = modelNode.GeometricScaling.value\n\n const transform = generateTransform(transformData)\n\n return this.genGeometry(geoNode, skeleton, morphTargets, transform)\n }\n\n // Generate a BufferGeometry from a node in FBXTree.Objects.Geometry\n genGeometry(geoNode, skeleton, morphTargets, preTransform) {\n const geo = new BufferGeometry()\n if (geoNode.attrName) geo.name = geoNode.attrName\n\n const geoInfo = this.parseGeoNode(geoNode, skeleton)\n const buffers = this.genBuffers(geoInfo)\n\n const positionAttribute = new Float32BufferAttribute(buffers.vertex, 3)\n\n positionAttribute.applyMatrix4(preTransform)\n\n geo.setAttribute('position', positionAttribute)\n\n if (buffers.colors.length > 0) {\n geo.setAttribute('color', new Float32BufferAttribute(buffers.colors, 3))\n }\n\n if (skeleton) {\n geo.setAttribute('skinIndex', new Uint16BufferAttribute(buffers.weightsIndices, 4))\n\n geo.setAttribute('skinWeight', new Float32BufferAttribute(buffers.vertexWeights, 4))\n\n // used later to bind the skeleton to the model\n geo.FBX_Deformer = skeleton\n }\n\n if (buffers.normal.length > 0) {\n const normalMatrix = new Matrix3().getNormalMatrix(preTransform)\n\n const normalAttribute = new Float32BufferAttribute(buffers.normal, 3)\n normalAttribute.applyNormalMatrix(normalMatrix)\n\n geo.setAttribute('normal', normalAttribute)\n }\n\n buffers.uvs.forEach(function (uvBuffer, i) {\n // subsequent uv buffers are called 'uv1', 'uv2', ...\n let name = 'uv' + (i + 1).toString()\n\n // the first uv buffer is just called 'uv'\n if (i === 0) {\n name = 'uv'\n }\n\n geo.setAttribute(name, new Float32BufferAttribute(buffers.uvs[i], 2))\n })\n\n if (geoInfo.material && geoInfo.material.mappingType !== 'AllSame') {\n // Convert the material indices of each vertex into rendering groups on the geometry.\n let prevMaterialIndex = buffers.materialIndex[0]\n let startIndex = 0\n\n buffers.materialIndex.forEach(function (currentIndex, i) {\n if (currentIndex !== prevMaterialIndex) {\n geo.addGroup(startIndex, i - startIndex, prevMaterialIndex)\n\n prevMaterialIndex = currentIndex\n startIndex = i\n }\n })\n\n // the loop above doesn't add the last group, do that here.\n if (geo.groups.length > 0) {\n const lastGroup = geo.groups[geo.groups.length - 1]\n const lastIndex = lastGroup.start + lastGroup.count\n\n if (lastIndex !== buffers.materialIndex.length) {\n geo.addGroup(lastIndex, buffers.materialIndex.length - lastIndex, prevMaterialIndex)\n }\n }\n\n // case where there are multiple materials but the whole geometry is only\n // using one of them\n if (geo.groups.length === 0) {\n geo.addGroup(0, buffers.materialIndex.length, buffers.materialIndex[0])\n }\n }\n\n this.addMorphTargets(geo, geoNode, morphTargets, preTransform)\n\n return geo\n }\n\n parseGeoNode(geoNode, skeleton) {\n const geoInfo = {}\n\n geoInfo.vertexPositions = geoNode.Vertices !== undefined ? geoNode.Vertices.a : []\n geoInfo.vertexIndices = geoNode.PolygonVertexIndex !== undefined ? geoNode.PolygonVertexIndex.a : []\n\n if (geoNode.LayerElementColor) {\n geoInfo.color = this.parseVertexColors(geoNode.LayerElementColor[0])\n }\n\n if (geoNode.LayerElementMaterial) {\n geoInfo.material = this.parseMaterialIndices(geoNode.LayerElementMaterial[0])\n }\n\n if (geoNode.LayerElementNormal) {\n geoInfo.normal = this.parseNormals(geoNode.LayerElementNormal[0])\n }\n\n if (geoNode.LayerElementUV) {\n geoInfo.uv = []\n\n let i = 0\n while (geoNode.LayerElementUV[i]) {\n if (geoNode.LayerElementUV[i].UV) {\n geoInfo.uv.push(this.parseUVs(geoNode.LayerElementUV[i]))\n }\n\n i++\n }\n }\n\n geoInfo.weightTable = {}\n\n if (skeleton !== null) {\n geoInfo.skeleton = skeleton\n\n skeleton.rawBones.forEach(function (rawBone, i) {\n // loop over the bone's vertex indices and weights\n rawBone.indices.forEach(function (index, j) {\n if (geoInfo.weightTable[index] === undefined) geoInfo.weightTable[index] = []\n\n geoInfo.weightTable[index].push({\n id: i,\n weight: rawBone.weights[j],\n })\n })\n })\n }\n\n return geoInfo\n }\n\n genBuffers(geoInfo) {\n const buffers = {\n vertex: [],\n normal: [],\n colors: [],\n uvs: [],\n materialIndex: [],\n vertexWeights: [],\n weightsIndices: [],\n }\n\n let polygonIndex = 0\n let faceLength = 0\n let displayedWeightsWarning = false\n\n // these will hold data for a single face\n let facePositionIndexes = []\n let faceNormals = []\n let faceColors = []\n let faceUVs = []\n let faceWeights = []\n let faceWeightIndices = []\n\n const scope = this\n geoInfo.vertexIndices.forEach(function (vertexIndex, polygonVertexIndex) {\n let materialIndex\n let endOfFace = false\n\n // Face index and vertex index arrays are combined in a single array\n // A cube with quad faces looks like this:\n // PolygonVertexIndex: *24 {\n // a: 0, 1, 3, -3, 2, 3, 5, -5, 4, 5, 7, -7, 6, 7, 1, -1, 1, 7, 5, -4, 6, 0, 2, -5\n // }\n // Negative numbers mark the end of a face - first face here is 0, 1, 3, -3\n // to find index of last vertex bit shift the index: ^ - 1\n if (vertexIndex < 0) {\n vertexIndex = vertexIndex ^ -1 // equivalent to ( x * -1 ) - 1\n endOfFace = true\n }\n\n let weightIndices = []\n let weights = []\n\n facePositionIndexes.push(vertexIndex * 3, vertexIndex * 3 + 1, vertexIndex * 3 + 2)\n\n if (geoInfo.color) {\n const data = getData(polygonVertexIndex, polygonIndex, vertexIndex, geoInfo.color)\n\n faceColors.push(data[0], data[1], data[2])\n }\n\n if (geoInfo.skeleton) {\n if (geoInfo.weightTable[vertexIndex] !== undefined) {\n geoInfo.weightTable[vertexIndex].forEach(function (wt) {\n weights.push(wt.weight)\n weightIndices.push(wt.id)\n })\n }\n\n if (weights.length > 4) {\n if (!displayedWeightsWarning) {\n console.warn(\n 'THREE.FBXLoader: Vertex has more than 4 skinning weights assigned to vertex. Deleting additional weights.',\n )\n displayedWeightsWarning = true\n }\n\n const wIndex = [0, 0, 0, 0]\n const Weight = [0, 0, 0, 0]\n\n weights.forEach(function (weight, weightIndex) {\n let currentWeight = weight\n let currentIndex = weightIndices[weightIndex]\n\n Weight.forEach(function (comparedWeight, comparedWeightIndex, comparedWeightArray) {\n if (currentWeight > comparedWeight) {\n comparedWeightArray[comparedWeightIndex] = currentWeight\n currentWeight = comparedWeight\n\n const tmp = wIndex[comparedWeightIndex]\n wIndex[comparedWeightIndex] = currentIndex\n currentIndex = tmp\n }\n })\n })\n\n weightIndices = wIndex\n weights = Weight\n }\n\n // if the weight array is shorter than 4 pad with 0s\n while (weights.length < 4) {\n weights.push(0)\n weightIndices.push(0)\n }\n\n for (let i = 0; i < 4; ++i) {\n faceWeights.push(weights[i])\n faceWeightIndices.push(weightIndices[i])\n }\n }\n\n if (geoInfo.normal) {\n const data = getData(polygonVertexIndex, polygonIndex, vertexIndex, geoInfo.normal)\n\n faceNormals.push(data[0], data[1], data[2])\n }\n\n if (geoInfo.material && geoInfo.material.mappingType !== 'AllSame') {\n materialIndex = getData(polygonVertexIndex, polygonIndex, vertexIndex, geoInfo.material)[0]\n }\n\n if (geoInfo.uv) {\n geoInfo.uv.forEach(function (uv, i) {\n const data = getData(polygonVertexIndex, polygonIndex, vertexIndex, uv)\n\n if (faceUVs[i] === undefined) {\n faceUVs[i] = []\n }\n\n faceUVs[i].push(data[0])\n faceUVs[i].push(data[1])\n })\n }\n\n faceLength++\n\n if (endOfFace) {\n scope.genFace(\n buffers,\n geoInfo,\n facePositionIndexes,\n materialIndex,\n faceNormals,\n faceColors,\n faceUVs,\n faceWeights,\n faceWeightIndices,\n faceLength,\n )\n\n polygonIndex++\n faceLength = 0\n\n // reset arrays for the next face\n facePositionIndexes = []\n faceNormals = []\n faceColors = []\n faceUVs = []\n faceWeights = []\n faceWeightIndices = []\n }\n })\n\n return buffers\n }\n\n // Generate data for a single face in a geometry. If the face is a quad then split it into 2 tris\n genFace(\n buffers,\n geoInfo,\n facePositionIndexes,\n materialIndex,\n faceNormals,\n faceColors,\n faceUVs,\n faceWeights,\n faceWeightIndices,\n faceLength,\n ) {\n for (let i = 2; i < faceLength; i++) {\n buffers.vertex.push(geoInfo.vertexPositions[facePositionIndexes[0]])\n buffers.vertex.push(geoInfo.vertexPositions[facePositionIndexes[1]])\n buffers.vertex.push(geoInfo.vertexPositions[facePositionIndexes[2]])\n\n buffers.vertex.push(geoInfo.vertexPositions[facePositionIndexes[(i - 1) * 3]])\n buffers.vertex.push(geoInfo.vertexPositions[facePositionIndexes[(i - 1) * 3 + 1]])\n buffers.vertex.push(geoInfo.vertexPositions[facePositionIndexes[(i - 1) * 3 + 2]])\n\n buffers.vertex.push(geoInfo.vertexPositions[facePositionIndexes[i * 3]])\n buffers.vertex.push(geoInfo.vertexPositions[facePositionIndexes[i * 3 + 1]])\n buffers.vertex.push(geoInfo.vertexPositions[facePositionIndexes[i * 3 + 2]])\n\n if (geoInfo.skeleton) {\n buffers.vertexWeights.push(faceWeights[0])\n buffers.vertexWeights.push(faceWeights[1])\n buffers.vertexWeights.push(faceWeights[2])\n buffers.vertexWeights.push(faceWeights[3])\n\n buffers.vertexWeights.push(faceWeights[(i - 1) * 4])\n buffers.vertexWeights.push(faceWeights[(i - 1) * 4 + 1])\n buffers.vertexWeights.push(faceWeights[(i - 1) * 4 + 2])\n buffers.vertexWeights.push(faceWeights[(i - 1) * 4 + 3])\n\n buffers.vertexWeights.push(faceWeights[i * 4])\n buffers.vertexWeights.push(faceWeights[i * 4 + 1])\n buffers.vertexWeights.push(faceWeights[i * 4 + 2])\n buffers.vertexWeights.push(faceWeights[i * 4 + 3])\n\n buffers.weightsIndices.push(faceWeightIndices[0])\n buffers.weightsIndices.push(faceWeightIndices[1])\n buffers.weightsIndices.push(faceWeightIndices[2])\n buffers.weightsIndices.push(faceWeightIndices[3])\n\n buffers.weightsIndices.push(faceWeightIndices[(i - 1) * 4])\n buffers.weightsIndices.push(faceWeightIndices[(i - 1) * 4 + 1])\n buffers.weightsIndices.push(faceWeightIndices[(i - 1) * 4 + 2])\n buffers.weightsIndices.push(faceWeightIndices[(i - 1) * 4 + 3])\n\n buffers.weightsIndices.push(faceWeightIndices[i * 4])\n buffers.weightsIndices.push(faceWeightIndices[i * 4 + 1])\n buffers.weightsIndices.push(faceWeightIndices[i * 4 + 2])\n buffers.weightsIndices.push(faceWeightIndices[i * 4 + 3])\n }\n\n if (geoInfo.color) {\n buffers.colors.push(faceColors[0])\n buffers.colors.push(faceColors[1])\n buffers.colors.push(faceColors[2])\n\n buffers.colors.push(faceColors[(i - 1) * 3])\n buffers.colors.push(faceColors[(i - 1) * 3 + 1])\n buffers.colors.push(faceColors[(i - 1) * 3 + 2])\n\n buffers.colors.push(faceColors[i * 3])\n buffers.colors.push(faceColors[i * 3 + 1])\n buffers.colors.push(faceColors[i * 3 + 2])\n }\n\n if (geoInfo.material && geoInfo.material.mappingType !== 'AllSame') {\n buffers.materialIndex.push(materialIndex)\n buffers.materialIndex.push(materialIndex)\n buffers.materialIndex.push(materialIndex)\n }\n\n if (geoInfo.normal) {\n buffers.normal.push(faceNormals[0])\n buffers.normal.push(faceNormals[1])\n buffers.normal.push(faceNormals[2])\n\n buffers.normal.push(faceNormals[(i - 1) * 3])\n buffers.normal.push(faceNormals[(i - 1) * 3 + 1])\n buffers.normal.push(faceNormals[(i - 1) * 3 + 2])\n\n buffers.normal.push(faceNormals[i * 3])\n buffers.normal.push(faceNormals[i * 3 + 1])\n buffers.normal.push(faceNormals[i * 3 + 2])\n }\n\n if (geoInfo.uv) {\n geoInfo.uv.forEach(function (uv, j) {\n if (buffers.uvs[j] === undefined) buffers.uvs[j] = []\n\n buffers.uvs[j].push(faceUVs[j][0])\n buffers.uvs[j].push(faceUVs[j][1])\n\n buffers.uvs[j].push(faceUVs[j][(i - 1) * 2])\n buffers.uvs[j].push(faceUVs[j][(i - 1) * 2 + 1])\n\n buffers.uvs[j].push(faceUVs[j][i * 2])\n buffers.uvs[j].push(faceUVs[j][i * 2 + 1])\n })\n }\n }\n }\n\n addMorphTargets(parentGeo, parentGeoNode, morphTargets, preTransform) {\n if (morphTargets.length === 0) return\n\n parentGeo.morphTargetsRelative = true\n\n parentGeo.morphAttributes.position = []\n // parentGeo.morphAttributes.normal = []; // not implemented\n\n const scope = this\n morphTargets.forEach(function (morphTarget) {\n morphTarget.rawTargets.forEach(function (rawTarget) {\n const morphGeoNode = fbxTree.Objects.Geometry[rawTarget.geoID]\n\n if (morphGeoNode !== undefined) {\n scope.genMorphGeometry(parentGeo, parentGeoNode, morphGeoNode, preTransform, rawTarget.name)\n }\n })\n })\n }\n\n // a morph geometry node is similar to a standard node, and the node is also contained\n // in FBXTree.Objects.Geometry, however it can only have attributes for position, normal\n // and a special attribute Index defining which vertices of the original geometry are affected\n // Normal and position attributes only have data for the vertices that are affected by the morph\n genMorphGeometry(parentGeo, parentGeoNode, morphGeoNode, preTransform, name) {\n const vertexIndices = parentGeoNode.PolygonVertexIndex !== undefined ? parentGeoNode.PolygonVertexIndex.a : []\n\n const morphPositionsSparse = morphGeoNode.Vertices !== undefined ? morphGeoNode.Vertices.a : []\n const indices = morphGeoNode.Indexes !== undefined ? morphGeoNode.Indexes.a : []\n\n const length = parentGeo.attributes.position.count * 3\n const morphPositions = new Float32Array(length)\n\n for (let i = 0; i < indices.length; i++) {\n const morphIndex = indices[i] * 3\n\n morphPositions[morphIndex] = morphPositionsSparse[i * 3]\n morphPositions[morphIndex + 1] = morphPositionsSparse[i * 3 + 1]\n morphPositions[morphIndex + 2] = morphPositionsSparse[i * 3 + 2]\n }\n\n // TODO: add morph normal support\n const morphGeoInfo = {\n vertexIndices: vertexIndices,\n vertexPositions: morphPositions,\n }\n\n const morphBuffers = this.genBuffers(morphGeoInfo)\n\n const positionAttribute = new Float32BufferAttribute(morphBuffers.vertex, 3)\n positionAttribute.name = name || morphGeoNode.attrName\n\n positionAttribute.applyMatrix4(preTransform)\n\n parentGeo.morphAttributes.position.push(positionAttribute)\n }\n\n // Parse normal from FBXTree.Objects.Geometry.LayerElementNormal if it exists\n parseNormals(NormalNode) {\n const mappingType = NormalNode.MappingInformationType\n const referenceType = NormalNode.ReferenceInformationType\n const buffer = NormalNode.Normals.a\n let indexBuffer = []\n if (referenceType === 'IndexToDirect') {\n if ('NormalIndex' in NormalNode) {\n indexBuffer = NormalNode.NormalIndex.a\n } else if ('NormalsIndex' in NormalNode) {\n indexBuffer = NormalNode.NormalsIndex.a\n }\n }\n\n return {\n dataSize: 3,\n buffer: buffer,\n indices: indexBuffer,\n mappingType: mappingType,\n referenceType: referenceType,\n }\n }\n\n // Parse UVs from FBXTree.Objects.Geometry.LayerElementUV if it exists\n parseUVs(UVNode) {\n const mappingType = UVNode.MappingInformationType\n const referenceType = UVNode.ReferenceInformationType\n const buffer = UVNode.UV.a\n let indexBuffer = []\n if (referenceType === 'IndexToDirect') {\n indexBuffer = UVNode.UVIndex.a\n }\n\n return {\n dataSize: 2,\n buffer: buffer,\n indices: indexBuffer,\n mappingType: mappingType,\n referenceType: referenceType,\n }\n }\n\n // Parse Vertex Colors from FBXTree.Objects.Geometry.LayerElementColor if it exists\n parseVertexColors(ColorNode) {\n const mappingType = ColorNode.MappingInformationType\n const referenceType = ColorNode.ReferenceInformationType\n const buffer = ColorNode.Colors.a\n let indexBuffer = []\n if (referenceType === 'IndexToDirect') {\n indexBuffer = ColorNode.ColorIndex.a\n }\n\n return {\n dataSize: 4,\n buffer: buffer,\n indices: indexBuffer,\n mappingType: mappingType,\n referenceType: referenceType,\n }\n }\n\n // Parse mapping and material data in FBXTree.Objects.Geometry.LayerElementMaterial if it exists\n parseMaterialIndices(MaterialNode) {\n const mappingType = MaterialNode.MappingInformationType\n const referenceType = MaterialNode.ReferenceInformationType\n\n if (mappingType === 'NoMappingInformation') {\n return {\n dataSize: 1,\n buffer: [0],\n indices: [0],\n mappingType: 'AllSame',\n referenceType: referenceType,\n }\n }\n\n const materialIndexBuffer = MaterialNode.Materials.a\n\n // Since materials are stored as indices, there's a bit of a mismatch between FBX and what\n // we expect.So we create an intermediate buffer that points to the index in the buffer,\n // for conforming with the other functions we've written for other data.\n const materialIndices = []\n\n for (let i = 0; i < materialIndexBuffer.length; ++i) {\n materialIndices.push(i)\n }\n\n return {\n dataSize: 1,\n buffer: materialIndexBuffer,\n indices: materialIndices,\n mappingType: mappingType,\n referenceType: referenceType,\n }\n }\n\n // Generate a NurbGeometry from a node in FBXTree.Objects.Geometry\n parseNurbsGeometry(geoNode) {\n if (NURBSCurve === undefined) {\n console.error(\n 'THREE.FBXLoader: The loader relies on NURBSCurve for any nurbs present in the model. Nurbs will show up as empty geometry.',\n )\n return new BufferGeometry()\n }\n\n const order = parseInt(geoNode.Order)\n\n if (isNaN(order)) {\n console.error('THREE.FBXLoader: Invalid Order %s given for geometry ID: %s', geoNode.Order, geoNode.id)\n return new BufferGeometry()\n }\n\n const degree = order - 1\n\n const knots = geoNode.KnotVector.a\n const controlPoints = []\n const pointsValues = geoNode.Points.a\n\n for (let i = 0, l = pointsValues.length; i < l; i += 4) {\n controlPoints.push(new Vector4().fromArray(pointsValues, i))\n }\n\n let startKnot, endKnot\n\n if (geoNode.Form === 'Closed') {\n controlPoints.push(controlPoints[0])\n } else if (geoNode.Form === 'Periodic') {\n startKnot = degree\n endKnot = knots.length - 1 - startKnot\n\n for (let i = 0; i < degree; ++i) {\n controlPoints.push(controlPoints[i])\n }\n }\n\n const curve = new NURBSCurve(degree, knots, controlPoints, startKnot, endKnot)\n const points = curve.getPoints(controlPoints.length * 12)\n\n return new BufferGeometry().setFromPoints(points)\n }\n}\n\n// parse animation data from FBXTree\nclass AnimationParser {\n // take raw animation clips and turn them into three.js animation clips\n parse() {\n const animationClips = []\n\n const rawClips = this.parseClips()\n\n if (rawClips !== undefined) {\n for (const key in rawClips) {\n const rawClip = rawClips[key]\n\n const clip = this.addClip(rawClip)\n\n animationClips.push(clip)\n }\n }\n\n return animationClips\n }\n\n parseClips() {\n // since the actual transformation data is stored in FBXTree.Objects.AnimationCurve,\n // if this is undefined we can safely assume there are no animations\n if (fbxTree.Objects.AnimationCurve === undefined) return undefined\n\n const curveNodesMap = this.parseAnimationCurveNodes()\n\n this.parseAnimationCurves(curveNodesMap)\n\n const layersMap = this.parseAnimationLayers(curveNodesMap)\n const rawClips = this.parseAnimStacks(layersMap)\n\n return rawClips\n }\n\n // parse nodes in FBXTree.Objects.AnimationCurveNode\n // each AnimationCurveNode holds data for an animation transform for a model (e.g. left arm rotation )\n // and is referenced by an AnimationLayer\n parseAnimationCurveNodes() {\n const rawCurveNodes = fbxTree.Objects.AnimationCurveNode\n\n const curveNodesMap = new Map()\n\n for (const nodeID in rawCurveNodes) {\n const rawCurveNode = rawCurveNodes[nodeID]\n\n if (rawCurveNode.attrName.match(/S|R|T|DeformPercent/) !== null) {\n const curveNode = {\n id: rawCurveNode.id,\n attr: rawCurveNode.attrName,\n curves: {},\n }\n\n curveNodesMap.set(curveNode.id, curveNode)\n }\n }\n\n return curveNodesMap\n }\n\n // parse nodes in FBXTree.Objects.AnimationCurve and connect them up to\n // previously parsed AnimationCurveNodes. Each AnimationCurve holds data for a single animated\n // axis ( e.g. times and values of x rotation)\n parseAnimationCurves(curveNodesMap) {\n const rawCurves = fbxTree.Objects.AnimationCurve\n\n // TODO: Many values are identical up to roundoff error, but won't be optimised\n // e.g. position times: [0, 0.4, 0. 8]\n // position values: [7.23538335023477e-7, 93.67518615722656, -0.9982695579528809, 7.23538335023477e-7, 93.67518615722656, -0.9982695579528809, 7.235384487103147e-7, 93.67520904541016, -0.9982695579528809]\n // clearly, this should be optimised to\n // times: [0], positions [7.23538335023477e-7, 93.67518615722656, -0.9982695579528809]\n // this shows up in nearly every FBX file, and generally time array is length > 100\n\n for (const nodeID in rawCurves) {\n const animationCurve = {\n id: rawCurves[nodeID].id,\n times: rawCurves[nodeID].KeyTime.a.map(convertFBXTimeToSeconds),\n values: rawCurves[nodeID].KeyValueFloat.a,\n }\n\n const relationships = connections.get(animationCurve.id)\n\n if (relationships !== undefined) {\n const animationCurveID = relationships.parents[0].ID\n const animationCurveRelationship = relationships.parents[0].relationship\n\n if (animationCurveRelationship.match(/X/)) {\n curveNodesMap.get(animationCurveID).curves['x'] = animationCurve\n } else if (animationCurveRelationship.match(/Y/)) {\n curveNodesMap.get(animationCurveID).curves['y'] = animationCurve\n } else if (animationCurveRelationship.match(/Z/)) {\n curveNodesMap.get(animationCurveID).curves['z'] = animationCurve\n } else if (animationCurveRelationship.match(/d|DeformPercent/) && curveNodesMap.has(animationCurveID)) {\n curveNodesMap.get(animationCurveID).curves['morph'] = animationCurve\n }\n }\n }\n }\n\n // parse nodes in FBXTree.Objects.AnimationLayer. Each layers holds references\n // to various AnimationCurveNodes and is referenced by an AnimationStack node\n // note: theoretically a stack can have multiple layers, however in practice there always seems to be one per stack\n parseAnimationLayers(curveNodesMap) {\n const rawLayers = fbxTree.Objects.AnimationLayer\n\n const layersMap = new Map()\n\n for (const nodeID in rawLayers) {\n const layerCurveNodes = []\n\n const connection = connections.get(parseInt(nodeID))\n\n if (connection !== undefined) {\n // all the animationCurveNodes used in the layer\n const children = connection.children\n\n children.forEach(function (child, i) {\n if (curveNodesMap.has(child.ID)) {\n const curveNode = curveNodesMap.get(child.ID)\n\n // check that the curves are defined for at least one axis, otherwise ignore the curveNode\n if (\n curveNode.curves.x !== undefined ||\n curveNode.curves.y !== undefined ||\n curveNode.curves.z !== undefined\n ) {\n if (layerCurveNodes[i] === undefined) {\n const modelID = connections.get(child.ID).parents.filter(function (parent) {\n return parent.relationship !== undefined\n })[0].ID\n\n if (modelID !== undefined) {\n const rawModel = fbxTree.Objects.Model[modelID.toString()]\n\n if (rawModel === undefined) {\n console.warn('THREE.FBXLoader: Encountered a unused curve.', child)\n return\n }\n\n const node = {\n modelName: rawModel.attrName ? PropertyBinding.sanitizeNodeName(rawModel.attrName) : '',\n ID: rawModel.id,\n initialPosition: [0, 0, 0],\n initialRotation: [0, 0, 0],\n initialScale: [1, 1, 1],\n }\n\n sceneGraph.traverse(function (child) {\n if (child.ID === rawModel.id) {\n node.transform = child.matrix\n\n if (child.userData.transformData) node.eulerOrder = child.userData.transformData.eulerOrder\n }\n })\n\n if (!node.transform) node.transform = new Matrix4()\n\n // if the animated model is pre rotated, we'll have to apply the pre rotations to every\n // animation value as well\n if ('PreRotation' in rawModel) node.preRotation = rawModel.PreRotation.value\n if ('PostRotation' in rawModel) node.postRotation = rawModel.PostRotation.value\n\n layerCurveNodes[i] = node\n }\n }\n\n if (layerCurveNodes[i]) layerCurveNodes[i][curveNode.attr] = curveNode\n } else if (curveNode.curves.morph !== undefined) {\n if (layerCurveNodes[i] === undefined) {\n const deformerID = connections.get(child.ID).parents.filter(function (parent) {\n return parent.relationship !== undefined\n })[0].ID\n\n const morpherID = connections.get(deformerID).parents[0].ID\n const geoID = connections.get(morpherID).parents[0].ID\n\n // assuming geometry is not used in more than one model\n const modelID = connections.get(geoID).parents[0].ID\n\n const rawModel = fbxTree.Objects.Model[modelID]\n\n const node = {\n modelName: rawModel.attrName ? PropertyBinding.sanitizeNodeName(rawModel.attrName) : '',\n morphName: fbxTree.Objects.Deformer[deformerID].attrName,\n }\n\n layerCurveNodes[i] = node\n }\n\n layerCurveNodes[i][curveNode.attr] = curveNode\n }\n }\n })\n\n layersMap.set(parseInt(nodeID), layerCurveNodes)\n }\n }\n\n return layersMap\n }\n\n // parse nodes in FBXTree.Objects.AnimationStack. These are the top level node in the animation\n // hierarchy. Each Stack node will be used to create a AnimationClip\n parseAnimStacks(layersMap) {\n const rawStacks = fbxTree.Objects.AnimationStack\n\n // connect the stacks (clips) up to the layers\n const rawClips = {}\n\n for (const nodeID in rawStacks) {\n const children = connections.get(parseInt(nodeID)).children\n\n if (children.length > 1) {\n // it seems like stacks will always be associated with a single layer. But just in case there are files\n // where there are multiple layers per stack, we'll display a warning\n console.warn(\n 'THREE.FBXLoader: Encountered an animation stack with multiple layers, this is currently not supported. Ignoring subsequent layers.',\n )\n }\n\n const layer = layersMap.get(children[0].ID)\n\n rawClips[nodeID] = {\n name: rawStacks[nodeID].attrName,\n layer: layer,\n }\n }\n\n return rawClips\n }\n\n addClip(rawClip) {\n let tracks = []\n\n const scope = this\n rawClip.layer.forEach(function (rawTracks) {\n tracks = tracks.concat(scope.generateTracks(rawTracks))\n })\n\n return new AnimationClip(rawClip.name, -1, tracks)\n }\n\n generateTracks(rawTracks) {\n const tracks = []\n\n let initialPosition = new Vector3()\n let initialRotation = new Quaternion()\n let initialScale = new Vector3()\n\n if (rawTracks.transform) rawTracks.transform.decompose(initialPosition, initialRotation, initialScale)\n\n initialPosition = initialPosition.toArray()\n initialRotation = new Euler().setFromQuaternion(initialRotation, rawTracks.eulerOrder).toArray()\n initialScale = initialScale.toArray()\n\n if (rawTracks.T !== undefined && Object.keys(rawTracks.T.curves).length > 0) {\n const positionTrack = this.generateVectorTrack(\n rawTracks.modelName,\n rawTracks.T.curves,\n initialPosition,\n 'position',\n )\n if (positionTrack !== undefined) tracks.push(positionTrack)\n }\n\n if (rawTracks.R !== undefined && Object.keys(rawTracks.R.curves).length > 0) {\n const rotationTrack = this.generateRotationTrack(\n rawTracks.modelName,\n rawTracks.R.curves,\n initialRotation,\n rawTracks.preRotation,\n rawTracks.postRotation,\n rawTracks.eulerOrder,\n )\n if (rotationTrack !== undefined) tracks.push(rotationTrack)\n }\n\n if (rawTracks.S !== undefined && Object.keys(rawTracks.S.curves).length > 0) {\n const scaleTrack = this.generateVectorTrack(rawTracks.modelName, rawTracks.S.curves, initialScale, 'scale')\n if (scaleTrack !== undefined) tracks.push(scaleTrack)\n }\n\n if (rawTracks.DeformPercent !== undefined) {\n const morphTrack = this.generateMorphTrack(rawTracks)\n if (morphTrack !== undefined) tracks.push(morphTrack)\n }\n\n return tracks\n }\n\n generateVectorTrack(modelName, curves, initialValue, type) {\n const times = this.getTimesForAllAxes(curves)\n const values = this.getKeyframeTrackValues(times, curves, initialValue)\n\n return new VectorKeyframeTrack(modelName + '.' + type, times, values)\n }\n\n generateRotationTrack(modelName, curves, initialValue, preRotation, postRotation, eulerOrder) {\n if (curves.x !== undefined) {\n this.interpolateRotations(curves.x)\n curves.x.values = curves.x.values.map(MathUtils.degToRad)\n }\n\n if (curves.y !== undefined) {\n this.interpolateRotations(curves.y)\n curves.y.values = curves.y.values.map(MathUtils.degToRad)\n }\n\n if (curves.z !== undefined) {\n this.interpolateRotations(curves.z)\n curves.z.values = curves.z.values.map(MathUtils.degToRad)\n }\n\n const times = this.getTimesForAllAxes(curves)\n const values = this.getKeyframeTrackValues(times, curves, initialValue)\n\n if (preRotation !== undefined) {\n preRotation = preRotation.map(MathUtils.degToRad)\n preRotation.push(eulerOrder)\n\n preRotation = new Euler().fromArray(preRotation)\n preRotation = new Quaternion().setFromEuler(preRotation)\n }\n\n if (postRotation !== undefined) {\n postRotation = postRotation.map(MathUtils.degToRad)\n postRotation.push(eulerOrder)\n\n postRotation = new Euler().fromArray(postRotation)\n postRotation = new Quaternion().setFromEuler(postRotation).invert()\n }\n\n const quaternion = new Quaternion()\n const euler = new Euler()\n\n const quaternionValues = []\n\n for (let i = 0; i < values.length; i += 3) {\n euler.set(values[i], values[i + 1], values[i + 2], eulerOrder)\n\n quaternion.setFromEuler(euler)\n\n if (preRotation !== undefined) quaternion.premultiply(preRotation)\n if (postRotation !== undefined) quaternion.multiply(postRotation)\n\n quaternion.toArray(quaternionValues, (i / 3) * 4)\n }\n\n return new QuaternionKeyframeTrack(modelName + '.quaternion', times, quaternionValues)\n }\n\n generateMorphTrack(rawTracks) {\n const curves = rawTracks.DeformPercent.curves.morph\n const values = curves.values.map(function (val) {\n return val / 100\n })\n\n const morphNum = sceneGraph.getObjectByName(rawTracks.modelName).morphTargetDictionary[rawTracks.morphName]\n\n return new NumberKeyframeTrack(\n rawTracks.modelName + '.morphTargetInfluences[' + morphNum + ']',\n curves.times,\n values,\n )\n }\n\n // For all animated objects, times are defined separately for each axis\n // Here we'll combine the times into one sorted array without duplicates\n getTimesForAllAxes(curves) {\n let times = []\n\n // first join together the times for each axis, if defined\n if (curves.x !== undefined) times = times.concat(curves.x.times)\n if (curves.y !== undefined) times = times.concat(curves.y.times)\n if (curves.z !== undefined) times = times.concat(curves.z.times)\n\n // then sort them\n times = times.sort(function (a, b) {\n return a - b\n })\n\n // and remove duplicates\n if (times.length > 1) {\n let targetIndex = 1\n let lastValue = times[0]\n for (let i = 1; i < times.length; i++) {\n const currentValue = times[i]\n if (currentValue !== lastValue) {\n times[targetIndex] = currentValue\n lastValue = currentValue\n targetIndex++\n }\n }\n\n times = times.slice(0, targetIndex)\n }\n\n return times\n }\n\n getKeyframeTrackValues(times, curves, initialValue) {\n const prevValue = initialValue\n\n const values = []\n\n let xIndex = -1\n let yIndex = -1\n let zIndex = -1\n\n times.forEach(function (time) {\n if (curves.x) xIndex = curves.x.times.indexOf(time)\n if (curves.y) yIndex = curves.y.times.indexOf(time)\n if (curves.z) zIndex = curves.z.times.indexOf(time)\n\n // if there is an x value defined for this frame, use that\n if (xIndex !== -1) {\n const xValue = curves.x.values[xIndex]\n values.push(xValue)\n prevValue[0] = xValue\n } else {\n // otherwise use the x value from the previous frame\n values.push(prevValue[0])\n }\n\n if (yIndex !== -1) {\n const yValue = curves.y.values[yIndex]\n values.push(yValue)\n prevValue[1] = yValue\n } else {\n values.push(prevValue[1])\n }\n\n if (zIndex !== -1) {\n const zValue = curves.z.values[zIndex]\n values.push(zValue)\n prevValue[2] = zValue\n } else {\n values.push(prevValue[2])\n }\n })\n\n return values\n }\n\n // Rotations are defined as Euler angles which can have values of any size\n // These will be converted to quaternions which don't support values greater than\n // PI, so we'll interpolate large rotations\n interpolateRotations(curve) {\n for (let i = 1; i < curve.values.length; i++) {\n const initialValue = curve.values[i - 1]\n const valuesSpan = curve.values[i] - initialValue\n\n const absoluteSpan = Math.abs(valuesSpan)\n\n if (absoluteSpan >= 180) {\n const numSubIntervals = absoluteSpan / 180\n\n const step = valuesSpan / numSubIntervals\n let nextValue = initialValue + step\n\n const initialTime = curve.times[i - 1]\n const timeSpan = curve.times[i] - initialTime\n const interval = timeSpan / numSubIntervals\n let nextTime = initialTime + interval\n\n const interpolatedTimes = []\n const interpolatedValues = []\n\n while (nextTime < curve.times[i]) {\n interpolatedTimes.push(nextTime)\n nextTime += interval\n\n interpolatedValues.push(nextValue)\n nextValue += step\n }\n\n curve.times = inject(curve.times, i, interpolatedTimes)\n curve.values = inject(curve.values, i, interpolatedValues)\n }\n }\n }\n}\n\n// parse an FBX file in ASCII format\nclass TextParser {\n getPrevNode() {\n return this.nodeStack[this.currentIndent - 2]\n }\n\n getCurrentNode() {\n return this.nodeStack[this.currentIndent - 1]\n }\n\n getCurrentProp() {\n return this.currentProp\n }\n\n pushStack(node) {\n this.nodeStack.push(node)\n this.currentIndent += 1\n }\n\n popStack() {\n this.nodeStack.pop()\n this.currentIndent -= 1\n }\n\n setCurrentProp(val, name) {\n this.currentProp = val\n this.currentPropName = name\n }\n\n parse(text) {\n this.currentIndent = 0\n\n this.allNodes = new FBXTree()\n this.nodeStack = []\n this.currentProp = []\n this.currentPropName = ''\n\n const scope = this\n\n const split = text.split(/[\\r\\n]+/)\n\n split.forEach(function (line, i) {\n const matchComment = line.match(/^[\\s\\t]*;/)\n const matchEmpty = line.match(/^[\\s\\t]*$/)\n\n if (matchComment || matchEmpty) return\n\n const matchBeginning = line.match('^\\\\t{' + scope.currentIndent + '}(\\\\w+):(.*){', '')\n const matchProperty = line.match('^\\\\t{' + scope.currentIndent + '}(\\\\w+):[\\\\s\\\\t\\\\r\\\\n](.*)')\n const matchEnd = line.match('^\\\\t{' + (scope.currentIndent - 1) + '}}')\n\n if (matchBeginning) {\n scope.parseNodeBegin(line, matchBeginning)\n } else if (matchProperty) {\n scope.parseNodeProperty(line, matchProperty, split[++i])\n } else if (matchEnd) {\n scope.popStack()\n } else if (line.match(/^[^\\s\\t}]/)) {\n // large arrays are split over multiple lines terminated with a ',' character\n // if this is encountered the line needs to be joined to the previous line\n scope.parseNodePropertyContinued(line)\n }\n })\n\n return this.allNodes\n }\n\n parseNodeBegin(line, property) {\n const nodeName = property[1].trim().replace(/^\"/, '').replace(/\"$/, '')\n\n const nodeAttrs = property[2].split(',').map(function (attr) {\n return attr.trim().replace(/^\"/, '').replace(/\"$/, '')\n })\n\n const node = { name: nodeName }\n const attrs = this.parseNodeAttr(nodeAttrs)\n\n const currentNode = this.getCurrentNode()\n\n // a top node\n if (this.currentIndent === 0) {\n this.allNodes.add(nodeName, node)\n } else {\n // a subnode\n\n // if the subnode already exists, append it\n if (nodeName in currentNode) {\n // special case Pose needs PoseNodes as an array\n if (nodeName === 'PoseNode') {\n currentNode.PoseNode.push(node)\n } else if (currentNode[nodeName].id !== undefined) {\n currentNode[nodeName] = {}\n currentNode[nodeName][currentNode[nodeName].id] = currentNode[nodeName]\n }\n\n if (attrs.id !== '') currentNode[nodeName][attrs.id] = node\n } else if (typeof attrs.id === 'number') {\n currentNode[nodeName] = {}\n currentNode[nodeName][attrs.id] = node\n } else if (nodeName !== 'Properties70') {\n if (nodeName === 'PoseNode') currentNode[nodeName] = [node]\n else currentNode[nodeName] = node\n }\n }\n\n if (typeof attrs.id === 'number') node.id = attrs.id\n if (attrs.name !== '') node.attrName = attrs.name\n if (attrs.type !== '') node.attrType = attrs.type\n\n this.pushStack(node)\n }\n\n parseNodeAttr(attrs) {\n let id = attrs[0]\n\n if (attrs[0] !== '') {\n id = parseInt(attrs[0])\n\n if (isNaN(id)) {\n id = attrs[0]\n }\n }\n\n let name = '',\n type = ''\n\n if (attrs.length > 1) {\n name = attrs[1].replace(/^(\\w+)::/, '')\n type = attrs[2]\n }\n\n return { id: id, name: name, type: type }\n }\n\n parseNodeProperty(line, property, contentLine) {\n let propName = property[1].replace(/^\"/, '').replace(/\"$/, '').trim()\n let propValue = property[2].replace(/^\"/, '').replace(/\"$/, '').trim()\n\n // for special case: base64 image data follows \"Content: ,\" line\n //\tContent: ,\n //\t \"/9j/4RDaRXhpZgAATU0A...\"\n if (propName === 'Content' && propValue === ',') {\n propValue = contentLine.replace(/\"/g, '').replace(/,$/, '').trim()\n }\n\n const currentNode = this.getCurrentNode()\n const parentName = currentNode.name\n\n if (parentName === 'Properties70') {\n this.parseNodeSpecialProperty(line, propName, propValue)\n return\n }\n\n // Connections\n if (propName === 'C') {\n const connProps = propValue.split(',').slice(1)\n const from = parseInt(connProps[0])\n const to = parseInt(connProps[1])\n\n let rest = propValue.split(',').slice(3)\n\n rest = rest.map(function (elem) {\n return elem.trim().replace(/^\"/, '')\n })\n\n propName = 'connections'\n propValue = [from, to]\n append(propValue, rest)\n\n if (currentNode[propName] === undefined) {\n currentNode[propName] = []\n }\n }\n\n // Node\n if (propName === 'Node') currentNode.id = propValue\n\n // connections\n if (propName in currentNode && Array.isArray(currentNode[propName])) {\n currentNode[propName].push(propValue)\n } else {\n if (propName !== 'a') currentNode[propName] = propValue\n else currentNode.a = propValue\n }\n\n this.setCurrentProp(currentNode, propName)\n\n // convert string to array, unless it ends in ',' in which case more will be added to it\n if (propName === 'a' && propValue.slice(-1) !== ',') {\n currentNode.a = parseNumberArray(propValue)\n }\n }\n\n parseNodePropertyContinued(line) {\n const currentNode = this.getCurrentNode()\n\n currentNode.a += line\n\n // if the line doesn't end in ',' we have reached the end of the property value\n // so convert the string to an array\n if (line.slice(-1) !== ',') {\n currentNode.a = parseNumberArray(currentNode.a)\n }\n }\n\n // parse \"Property70\"\n parseNodeSpecialProperty(line, propName, propValue) {\n // split this\n // P: \"Lcl Scaling\", \"Lcl Scaling\", \"\", \"A\",1,1,1\n // into array like below\n // [\"Lcl Scaling\", \"Lcl Scaling\", \"\", \"A\", \"1,1,1\" ]\n const props = propValue.split('\",').map(function (prop) {\n return prop.trim().replace(/^\\\"/, '').replace(/\\s/, '_')\n })\n\n const innerPropName = props[0]\n const innerPropType1 = props[1]\n const innerPropType2 = props[2]\n const innerPropFlag = props[3]\n let innerPropValue = props[4]\n\n // cast values where needed, otherwise leave as strings\n switch (innerPropType1) {\n case 'int':\n case 'enum':\n case 'bool':\n case 'ULongLong':\n case 'double':\n case 'Number':\n case 'FieldOfView':\n innerPropValue = parseFloat(innerPropValue)\n break\n\n case 'Color':\n case 'ColorRGB':\n case 'Vector3D':\n case 'Lcl_Translation':\n case 'Lcl_Rotation':\n case 'Lcl_Scaling':\n innerPropValue = parseNumberArray(innerPropValue)\n break\n }\n\n // CAUTION: these props must append to parent's parent\n this.getPrevNode()[innerPropName] = {\n type: innerPropType1,\n type2: innerPropType2,\n flag: innerPropFlag,\n value: innerPropValue,\n }\n\n this.setCurrentProp(this.getPrevNode(), innerPropName)\n }\n}\n\n// Parse an FBX file in Binary format\nclass BinaryParser {\n parse(buffer) {\n const reader = new BinaryReader(buffer)\n reader.skip(23) // skip magic 23 bytes\n\n const version = reader.getUint32()\n\n if (version < 6400) {\n throw new Error('THREE.FBXLoader: FBX version not supported, FileVersion: ' + version)\n }\n\n const allNodes = new FBXTree()\n\n while (!this.endOfContent(reader)) {\n const node = this.parseNode(reader, version)\n if (node !== null) allNodes.add(node.name, node)\n }\n\n return allNodes\n }\n\n // Check if reader has reached the end of content.\n endOfContent(reader) {\n // footer size: 160bytes + 16-byte alignment padding\n // - 16bytes: magic\n // - padding til 16-byte alignment (at least 1byte?)\n //\t(seems like some exporters embed fixed 15 or 16bytes?)\n // - 4bytes: magic\n // - 4bytes: version\n // - 120bytes: zero\n // - 16bytes: magic\n if (reader.size() % 16 === 0) {\n return ((reader.getOffset() + 160 + 16) & ~0xf) >= reader.size()\n } else {\n return reader.getOffset() + 160 + 16 >= reader.size()\n }\n }\n\n // recursively parse nodes until the end of the file is reached\n parseNode(reader, version) {\n const node = {}\n\n // The first three data sizes depends on version.\n const endOffset = version >= 7500 ? reader.getUint64() : reader.getUint32()\n const numProperties = version >= 7500 ? reader.getUint64() : reader.getUint32()\n\n version >= 7500 ? reader.getUint64() : reader.getUint32() // the returned propertyListLen is not used\n\n const nameLen = reader.getUint8()\n const name = reader.getString(nameLen)\n\n // Regards this node as NULL-record if endOffset is zero\n if (endOffset === 0) return null\n\n const propertyList = []\n\n for (let i = 0; i < numProperties; i++) {\n propertyList.push(this.parseProperty(reader))\n }\n\n // Regards the first three elements in propertyList as id, attrName, and attrType\n const id = propertyList.length > 0 ? propertyList[0] : ''\n const attrName = propertyList.length > 1 ? propertyList[1] : ''\n const attrType = propertyList.length > 2 ? propertyList[2] : ''\n\n // check if this node represents just a single property\n // like (name, 0) set or (name2, [0, 1, 2]) set of {name: 0, name2: [0, 1, 2]}\n node.singleProperty = numProperties === 1 && reader.getOffset() === endOffset ? true : false\n\n while (endOffset > reader.getOffset()) {\n const subNode = this.parseNode(reader, version)\n\n if (subNode !== null) this.parseSubNode(name, node, subNode)\n }\n\n node.propertyList = propertyList // raw property list used by parent\n\n if (typeof id === 'number') node.id = id\n if (attrName !== '') node.attrName = attrName\n if (attrType !== '') node.attrType = attrType\n if (name !== '') node.name = name\n\n return node\n }\n\n parseSubNode(name, node, subNode) {\n // special case: child node is single property\n if (subNode.singleProperty === true) {\n const value = subNode.propertyList[0]\n\n if (Array.isArray(value)) {\n node[subNode.name] = subNode\n\n subNode.a = value\n } else {\n node[subNode.name] = value\n }\n } else if (name === 'Connections' && subNode.name === 'C') {\n const array = []\n\n subNode.propertyList.forEach(function (property, i) {\n // first Connection is FBX type (OO, OP, etc.). We'll discard these\n if (i !== 0) array.push(property)\n })\n\n if (node.connections === undefined) {\n node.connections = []\n }\n\n node.connections.push(array)\n } else if (subNode.name === 'Properties70') {\n const keys = Object.keys(subNode)\n\n keys.forEach(function (key) {\n node[key] = subNode[key]\n })\n } else if (name === 'Properties70' && subNode.name === 'P') {\n let innerPropName = subNode.propertyList[0]\n let innerPropType1 = subNode.propertyList[1]\n const innerPropType2 = subNode.propertyList[2]\n const innerPropFlag = subNode.propertyList[3]\n let innerPropValue\n\n if (innerPropName.indexOf('Lcl ') === 0) innerPropName = innerPropName.replace('Lcl ', 'Lcl_')\n if (innerPropType1.indexOf('Lcl ') === 0) innerPropType1 = innerPropType1.replace('Lcl ', 'Lcl_')\n\n if (\n innerPropType1 === 'Color' ||\n innerPropType1 === 'ColorRGB' ||\n innerPropType1 === 'Vector' ||\n innerPropType1 === 'Vector3D' ||\n innerPropType1.indexOf('Lcl_') === 0\n ) {\n innerPropValue = [subNode.propertyList[4], subNode.propertyList[5], subNode.propertyList[6]]\n } else {\n innerPropValue = subNode.propertyList[4]\n }\n\n // this will be copied to parent, see above\n node[innerPropName] = {\n type: innerPropType1,\n type2: innerPropType2,\n flag: innerPropFlag,\n value: innerPropValue,\n }\n } else if (node[subNode.name] === undefined) {\n if (typeof subNode.id === 'number') {\n node[subNode.name] = {}\n node[subNode.name][subNode.id] = subNode\n } else {\n node[subNode.name] = subNode\n }\n } else {\n if (subNode.name === 'PoseNode') {\n if (!Array.isArray(node[subNode.name])) {\n node[subNode.name] = [node[subNode.name]]\n }\n\n node[subNode.name].push(subNode)\n } else if (node[subNode.name][subNode.id] === undefined) {\n node[subNode.name][subNode.id] = subNode\n }\n }\n }\n\n parseProperty(reader) {\n const type = reader.getString(1)\n let length\n\n switch (type) {\n case 'C':\n return reader.getBoolean()\n\n case 'D':\n return reader.getFloat64()\n\n case 'F':\n return reader.getFloat32()\n\n case 'I':\n return reader.getInt32()\n\n case 'L':\n return reader.getInt64()\n\n case 'R':\n length = reader.getUint32()\n return reader.getArrayBuffer(length)\n\n case 'S':\n length = reader.getUint32()\n return reader.getString(length)\n\n case 'Y':\n return reader.getInt16()\n\n case 'b':\n case 'c':\n case 'd':\n case 'f':\n case 'i':\n case 'l':\n const arrayLength = reader.getUint32()\n const encoding = reader.getUint32() // 0: non-compressed, 1: compressed\n const compressedLength = reader.getUint32()\n\n if (encoding === 0) {\n switch (type) {\n case 'b':\n case 'c':\n return reader.getBooleanArray(arrayLength)\n\n case 'd':\n return reader.getFloat64Array(arrayLength)\n\n case 'f':\n return reader.getFloat32Array(arrayLength)\n\n case 'i':\n return reader.getInt32Array(arrayLength)\n\n case 'l':\n return reader.getInt64Array(arrayLength)\n }\n }\n\n const data = unzlibSync(new Uint8Array(reader.getArrayBuffer(compressedLength)))\n const reader2 = new BinaryReader(data.buffer)\n\n switch (type) {\n case 'b':\n case 'c':\n return reader2.getBooleanArray(arrayLength)\n\n case 'd':\n return reader2.getFloat64Array(arrayLength)\n\n case 'f':\n return reader2.getFloat32Array(arrayLength)\n\n case 'i':\n return reader2.getInt32Array(arrayLength)\n\n case 'l':\n return reader2.getInt64Array(arrayLength)\n }\n\n default:\n throw new Error('THREE.FBXLoader: Unknown property type ' + type)\n }\n }\n}\n\nclass BinaryReader {\n constructor(buffer, littleEndian) {\n this.dv = new DataView(buffer)\n this.offset = 0\n this.littleEndian = littleEndian !== undefined ? littleEndian : true\n }\n\n getOffset() {\n return this.offset\n }\n\n size() {\n return this.dv.buffer.byteLength\n }\n\n skip(length) {\n this.offset += length\n }\n\n // seems like true/false representation depends on exporter.\n // true: 1 or 'Y'(=0x59), false: 0 or 'T'(=0x54)\n // then sees LSB.\n getBoolean() {\n return (this.getUint8() & 1) === 1\n }\n\n getBooleanArray(size) {\n const a = []\n\n for (let i = 0; i < size; i++) {\n a.push(this.getBoolean())\n }\n\n return a\n }\n\n getUint8() {\n const value = this.dv.getUint8(this.offset)\n this.offset += 1\n return value\n }\n\n getInt16() {\n const value = this.dv.getInt16(this.offset, this.littleEndian)\n this.offset += 2\n return value\n }\n\n getInt32() {\n const value = this.dv.getInt32(this.offset, this.littleEndian)\n this.offset += 4\n return value\n }\n\n getInt32Array(size) {\n const a = []\n\n for (let i = 0; i < size; i++) {\n a.push(this.getInt32())\n }\n\n return a\n }\n\n getUint32() {\n const value = this.dv.getUint32(this.offset, this.littleEndian)\n this.offset += 4\n return value\n }\n\n // JavaScript doesn't support 64-bit integer so calculate this here\n // 1 << 32 will return 1 so using multiply operation instead here.\n // There's a possibility that this method returns wrong value if the value\n // is out of the range between Number.MAX_SAFE_INTEGER and Number.MIN_SAFE_INTEGER.\n // TODO: safely handle 64-bit integer\n getInt64() {\n let low, high\n\n if (this.littleEndian) {\n low = this.getUint32()\n high = this.getUint32()\n } else {\n high = this.getUint32()\n low = this.getUint32()\n }\n\n // calculate negative value\n if (high & 0x80000000) {\n high = ~high & 0xffffffff\n low = ~low & 0xffffffff\n\n if (low === 0xffffffff) high = (high + 1) & 0xffffffff\n\n low = (low + 1) & 0xffffffff\n\n return -(high * 0x100000000 + low)\n }\n\n return high * 0x100000000 + low\n }\n\n getInt64Array(size) {\n const a = []\n\n for (let i = 0; i < size; i++) {\n a.push(this.getInt64())\n }\n\n return a\n }\n\n // Note: see getInt64() comment\n getUint64() {\n let low, high\n\n if (this.littleEndian) {\n low = this.getUint32()\n high = this.getUint32()\n } else {\n high = this.getUint32()\n low = this.getUint32()\n }\n\n return high * 0x100000000 + low\n }\n\n getFloat32() {\n const value = this.dv.getFloat32(this.offset, this.littleEndian)\n this.offset += 4\n return value\n }\n\n getFloat32Array(size) {\n const a = []\n\n for (let i = 0; i < size; i++) {\n a.push(this.getFloat32())\n }\n\n return a\n }\n\n getFloat64() {\n const value = this.dv.getFloat64(this.offset, this.littleEndian)\n this.offset += 8\n return value\n }\n\n getFloat64Array(size) {\n const a = []\n\n for (let i = 0; i < size; i++) {\n a.push(this.getFloat64())\n }\n\n return a\n }\n\n getArrayBuffer(size) {\n const value = this.dv.buffer.slice(this.offset, this.offset + size)\n this.offset += size\n return value\n }\n\n getString(size) {\n // note: safari 9 doesn't support Uint8Array.indexOf; create intermediate array instead\n let a = []\n\n for (let i = 0; i < size; i++) {\n a[i] = this.getUint8()\n }\n\n const nullByte = a.indexOf(0)\n if (nullByte >= 0) a = a.slice(0, nullByte)\n\n return decodeText(new Uint8Array(a))\n }\n}\n\n// FBXTree holds a representation of the FBX data, returned by the TextParser ( FBX ASCII format)\n// and BinaryParser( FBX Binary format)\nclass FBXTree {\n add(key, val) {\n this[key] = val\n }\n}\n\n// ************** UTILITY FUNCTIONS **************\n\nfunction isFbxFormatBinary(buffer) {\n const CORRECT = 'Kaydara\\u0020FBX\\u0020Binary\\u0020\\u0020\\0'\n\n return buffer.byteLength >= CORRECT.length && CORRECT === convertArrayBufferToString(buffer, 0, CORRECT.length)\n}\n\nfunction isFbxFormatASCII(text) {\n const CORRECT = [\n 'K',\n 'a',\n 'y',\n 'd',\n 'a',\n 'r',\n 'a',\n '\\\\',\n 'F',\n 'B',\n 'X',\n '\\\\',\n 'B',\n 'i',\n 'n',\n 'a',\n 'r',\n 'y',\n '\\\\',\n '\\\\',\n ]\n\n let cursor = 0\n\n function read(offset) {\n const result = text[offset - 1]\n text = text.slice(cursor + offset)\n cursor++\n return result\n }\n\n for (let i = 0; i < CORRECT.length; ++i) {\n const num = read(1)\n if (num === CORRECT[i]) {\n return false\n }\n }\n\n return true\n}\n\nfunction getFbxVersion(text) {\n const versionRegExp = /FBXVersion: (\\d+)/\n const match = text.match(versionRegExp)\n\n if (match) {\n const version = parseInt(match[1])\n return version\n }\n\n throw new Error('THREE.FBXLoader: Cannot find the version number for the file given.')\n}\n\n// Converts FBX ticks into real time seconds.\nfunction convertFBXTimeToSeconds(time) {\n return time / 46186158000\n}\n\nconst dataArray = []\n\n// extracts the data from the correct position in the FBX array based on indexing type\nfunction getData(polygonVertexIndex, polygonIndex, vertexIndex, infoObject) {\n let index\n\n switch (infoObject.mappingType) {\n case 'ByPolygonVertex':\n index = polygonVertexIndex\n break\n case 'ByPolygon':\n index = polygonIndex\n break\n case 'ByVertice':\n index = vertexIndex\n break\n case 'AllSame':\n index = infoObject.indices[0]\n break\n default:\n console.warn('THREE.FBXLoader: unknown attribute mapping type ' + infoObject.mappingType)\n }\n\n if (infoObject.referenceType === 'IndexToDirect') index = infoObject.indices[index]\n\n const from = index * infoObject.dataSize\n const to = from + infoObject.dataSize\n\n return slice(dataArray, infoObject.buffer, from, to)\n}\n\nconst tempEuler = new Euler()\nconst tempVec = new Vector3()\n\n// generate transformation from FBX transform data\n// ref: https://help.autodesk.com/view/FBX/2017/ENU/?guid=__files_GUID_10CDD63C_79C1_4F2D_BB28_AD2BE65A02ED_htm\n// ref: http://docs.autodesk.com/FBX/2014/ENU/FBX-SDK-Documentation/index.html?url=cpp_ref/_transformations_2main_8cxx-example.html,topicNumber=cpp_ref__transformations_2main_8cxx_example_htmlfc10a1e1-b18d-4e72-9dc0-70d0f1959f5e\nfunction generateTransform(transformData) {\n const lTranslationM = new Matrix4()\n const lPreRotationM = new Matrix4()\n const lRotationM = new Matrix4()\n const lPostRotationM = new Matrix4()\n\n const lScalingM = new Matrix4()\n const lScalingPivotM = new Matrix4()\n const lScalingOffsetM = new Matrix4()\n const lRotationOffsetM = new Matrix4()\n const lRotationPivotM = new Matrix4()\n\n const lParentGX = new Matrix4()\n const lParentLX = new Matrix4()\n const lGlobalT = new Matrix4()\n\n const inheritType = transformData.inheritType ? transformData.inheritType : 0\n\n if (transformData.translation) lTranslationM.setPosition(tempVec.fromArray(transformData.translation))\n\n if (transformData.preRotation) {\n const array = transformData.preRotation.map(MathUtils.degToRad)\n array.push(transformData.eulerOrder)\n lPreRotationM.makeRotationFromEuler(tempEuler.fromArray(array))\n }\n\n if (transformData.rotation) {\n const array = transformData.rotation.map(MathUtils.degToRad)\n array.push(transformData.eulerOrder)\n lRotationM.makeRotationFromEuler(tempEuler.fromArray(array))\n }\n\n if (transformData.postRotation) {\n const array = transformData.postRotation.map(MathUtils.degToRad)\n array.push(transformData.eulerOrder)\n lPostRotationM.makeRotationFromEuler(tempEuler.fromArray(array))\n lPostRotationM.invert()\n }\n\n if (transformData.scale) lScalingM.scale(tempVec.fromArray(transformData.scale))\n\n // Pivots and offsets\n if (transformData.scalingOffset) lScalingOffsetM.setPosition(tempVec.fromArray(transformData.scalingOffset))\n if (transformData.scalingPivot) lScalingPivotM.setPosition(tempVec.fromArray(transformData.scalingPivot))\n if (transformData.rotationOffset) lRotationOffsetM.setPosition(tempVec.fromArray(transformData.rotationOffset))\n if (transformData.rotationPivot) lRotationPivotM.setPosition(tempVec.fromArray(transformData.rotationPivot))\n\n // parent transform\n if (transformData.parentMatrixWorld) {\n lParentLX.copy(transformData.parentMatrix)\n lParentGX.copy(transformData.parentMatrixWorld)\n }\n\n const lLRM = lPreRotationM.clone().multiply(lRotationM).multiply(lPostRotationM)\n // Global Rotation\n const lParentGRM = new Matrix4()\n lParentGRM.extractRotation(lParentGX)\n\n // Global Shear*Scaling\n const lParentTM = new Matrix4()\n lParentTM.copyPosition(lParentGX)\n\n const lParentGRSM = lParentTM.clone().invert().multiply(lParentGX)\n const lParentGSM = lParentGRM.clone().invert().multiply(lParentGRSM)\n const lLSM = lScalingM\n\n const lGlobalRS = new Matrix4()\n\n if (inheritType === 0) {\n lGlobalRS.copy(lParentGRM).multiply(lLRM).multiply(lParentGSM).multiply(lLSM)\n } else if (inheritType === 1) {\n lGlobalRS.copy(lParentGRM).multiply(lParentGSM).multiply(lLRM).multiply(lLSM)\n } else {\n const lParentLSM = new Matrix4().scale(new Vector3().setFromMatrixScale(lParentLX))\n const lParentLSM_inv = lParentLSM.clone().invert()\n const lParentGSM_noLocal = lParentGSM.clone().multiply(lParentLSM_inv)\n\n lGlobalRS.copy(lParentGRM).multiply(lLRM).multiply(lParentGSM_noLocal).multiply(lLSM)\n }\n\n const lRotationPivotM_inv = lRotationPivotM.clone().invert()\n const lScalingPivotM_inv = lScalingPivotM.clone().invert()\n // Calculate the local transform matrix\n let lTransform = lTranslationM\n .clone()\n .multiply(lRotationOffsetM)\n .multiply(lRotationPivotM)\n .multiply(lPreRotationM)\n .multiply(lRotationM)\n .multiply(lPostRotationM)\n .multiply(lRotationPivotM_inv)\n .multiply(lScalingOffsetM)\n .multiply(lScalingPivotM)\n .multiply(lScalingM)\n .multiply(lScalingPivotM_inv)\n\n const lLocalTWithAllPivotAndOffsetInfo = new Matrix4().copyPosition(lTransform)\n\n const lGlobalTranslation = lParentGX.clone().multiply(lLocalTWithAllPivotAndOffsetInfo)\n lGlobalT.copyPosition(lGlobalTranslation)\n\n lTransform = lGlobalT.clone().multiply(lGlobalRS)\n\n // from global to local\n lTransform.premultiply(lParentGX.invert())\n\n return lTransform\n}\n\n// Returns the three.js intrinsic Euler order corresponding to FBX extrinsic Euler order\n// ref: http://help.autodesk.com/view/FBX/2017/ENU/?guid=__cpp_ref_class_fbx_euler_html\nfunction getEulerOrder(order) {\n order = order || 0\n\n const enums = [\n 'ZYX', // -> XYZ extrinsic\n 'YZX', // -> XZY extrinsic\n 'XZY', // -> YZX extrinsic\n 'ZXY', // -> YXZ extrinsic\n 'YXZ', // -> ZXY extrinsic\n 'XYZ', // -> ZYX extrinsic\n //'SphericXYZ', // not possible to support\n ]\n\n if (order === 6) {\n console.warn('THREE.FBXLoader: unsupported Euler Order: Spherical XYZ. Animations and rotations may be incorrect.')\n return enums[0]\n }\n\n return enums[order]\n}\n\n// Parses comma separated list of numbers and returns them an array.\n// Used internally by the TextParser\nfunction parseNumberArray(value) {\n const array = value.split(',').map(function (val) {\n return parseFloat(val)\n })\n\n return array\n}\n\nfunction convertArrayBufferToString(buffer, from, to) {\n if (from === undefined) from = 0\n if (to === undefined) to = buffer.byteLength\n\n return decodeText(new Uint8Array(buffer, from, to))\n}\n\nfunction append(a, b) {\n for (let i = 0, j = a.length, l = b.length; i < l; i++, j++) {\n a[j] = b[i]\n }\n}\n\nfunction slice(a, b, from, to) {\n for (let i = from, j = 0; i < to; i++, j++) {\n a[j] = b[i]\n }\n\n return a\n}\n\n// inject array a2 into array a1 at index\nfunction inject(a1, index, a2) {\n return a1.slice(0, index).concat(a2).concat(a1.slice(index))\n}\n\nexport { FBXLoader }\n"],"names":["child","material","skeleton"],"mappings":"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"}
|
1
|
+
{"version":3,"file":"FBXLoader.js","sources":["../../src/loaders/FBXLoader.js"],"sourcesContent":["import {\n AmbientLight,\n AnimationClip,\n Bone,\n BufferGeometry,\n ClampToEdgeWrapping,\n Color,\n DirectionalLight,\n EquirectangularReflectionMapping,\n Euler,\n FileLoader,\n Float32BufferAttribute,\n Group,\n Line,\n LineBasicMaterial,\n Loader,\n LoaderUtils,\n MathUtils,\n Matrix3,\n Matrix4,\n Mesh,\n MeshLambertMaterial,\n MeshPhongMaterial,\n NumberKeyframeTrack,\n Object3D,\n OrthographicCamera,\n PerspectiveCamera,\n PointLight,\n PropertyBinding,\n Quaternion,\n QuaternionKeyframeTrack,\n RepeatWrapping,\n Skeleton,\n SkinnedMesh,\n SpotLight,\n Texture,\n TextureLoader,\n Uint16BufferAttribute,\n Vector3,\n Vector4,\n VectorKeyframeTrack,\n} from 'three'\nimport { unzlibSync } from 'fflate'\nimport { NURBSCurve } from '../curves/NURBSCurve'\nimport { decodeText } from '../_polyfill/LoaderUtils'\nimport { UV1 } from '../_polyfill/uv1'\n\n/**\n * Loader loads FBX file and generates Group representing FBX scene.\n * Requires FBX file to be >= 7.0 and in ASCII or >= 6400 in Binary format\n * Versions lower than this may load but will probably have errors\n *\n * Needs Support:\n * Morph normals / blend shape normals\n *\n * FBX format references:\n * \thttps://help.autodesk.com/view/FBX/2017/ENU/?guid=__cpp_ref_index_html (C++ SDK reference)\n *\n * Binary format specification:\n *\thttps://code.blender.org/2013/08/fbx-binary-file-format-specification/\n */\n\nlet fbxTree\nlet connections\nlet sceneGraph\n\nclass FBXLoader extends Loader {\n constructor(manager) {\n super(manager)\n }\n\n load(url, onLoad, onProgress, onError) {\n const scope = this\n\n const path = scope.path === '' ? LoaderUtils.extractUrlBase(url) : scope.path\n\n const loader = new FileLoader(this.manager)\n loader.setPath(scope.path)\n loader.setResponseType('arraybuffer')\n loader.setRequestHeader(scope.requestHeader)\n loader.setWithCredentials(scope.withCredentials)\n\n loader.load(\n url,\n function (buffer) {\n try {\n onLoad(scope.parse(buffer, path))\n } catch (e) {\n if (onError) {\n onError(e)\n } else {\n console.error(e)\n }\n\n scope.manager.itemError(url)\n }\n },\n onProgress,\n onError,\n )\n }\n\n parse(FBXBuffer, path) {\n if (isFbxFormatBinary(FBXBuffer)) {\n fbxTree = new BinaryParser().parse(FBXBuffer)\n } else {\n const FBXText = convertArrayBufferToString(FBXBuffer)\n\n if (!isFbxFormatASCII(FBXText)) {\n throw new Error('THREE.FBXLoader: Unknown format.')\n }\n\n if (getFbxVersion(FBXText) < 7000) {\n throw new Error('THREE.FBXLoader: FBX version not supported, FileVersion: ' + getFbxVersion(FBXText))\n }\n\n fbxTree = new TextParser().parse(FBXText)\n }\n\n // console.log( fbxTree );\n\n const textureLoader = new TextureLoader(this.manager)\n .setPath(this.resourcePath || path)\n .setCrossOrigin(this.crossOrigin)\n\n return new FBXTreeParser(textureLoader, this.manager).parse(fbxTree)\n }\n}\n\n// Parse the FBXTree object returned by the BinaryParser or TextParser and return a Group\nclass FBXTreeParser {\n constructor(textureLoader, manager) {\n this.textureLoader = textureLoader\n this.manager = manager\n }\n\n parse() {\n connections = this.parseConnections()\n\n const images = this.parseImages()\n const textures = this.parseTextures(images)\n const materials = this.parseMaterials(textures)\n const deformers = this.parseDeformers()\n const geometryMap = new GeometryParser().parse(deformers)\n\n this.parseScene(deformers, geometryMap, materials)\n\n return sceneGraph\n }\n\n // Parses FBXTree.Connections which holds parent-child connections between objects (e.g. material -> texture, model->geometry )\n // and details the connection type\n parseConnections() {\n const connectionMap = new Map()\n\n if ('Connections' in fbxTree) {\n const rawConnections = fbxTree.Connections.connections\n\n rawConnections.forEach(function (rawConnection) {\n const fromID = rawConnection[0]\n const toID = rawConnection[1]\n const relationship = rawConnection[2]\n\n if (!connectionMap.has(fromID)) {\n connectionMap.set(fromID, {\n parents: [],\n children: [],\n })\n }\n\n const parentRelationship = { ID: toID, relationship: relationship }\n connectionMap.get(fromID).parents.push(parentRelationship)\n\n if (!connectionMap.has(toID)) {\n connectionMap.set(toID, {\n parents: [],\n children: [],\n })\n }\n\n const childRelationship = { ID: fromID, relationship: relationship }\n connectionMap.get(toID).children.push(childRelationship)\n })\n }\n\n return connectionMap\n }\n\n // Parse FBXTree.Objects.Video for embedded image data\n // These images are connected to textures in FBXTree.Objects.Textures\n // via FBXTree.Connections.\n parseImages() {\n const images = {}\n const blobs = {}\n\n if ('Video' in fbxTree.Objects) {\n const videoNodes = fbxTree.Objects.Video\n\n for (const nodeID in videoNodes) {\n const videoNode = videoNodes[nodeID]\n\n const id = parseInt(nodeID)\n\n images[id] = videoNode.RelativeFilename || videoNode.Filename\n\n // raw image data is in videoNode.Content\n if ('Content' in videoNode) {\n const arrayBufferContent = videoNode.Content instanceof ArrayBuffer && videoNode.Content.byteLength > 0\n const base64Content = typeof videoNode.Content === 'string' && videoNode.Content !== ''\n\n if (arrayBufferContent || base64Content) {\n const image = this.parseImage(videoNodes[nodeID])\n\n blobs[videoNode.RelativeFilename || videoNode.Filename] = image\n }\n }\n }\n }\n\n for (const id in images) {\n const filename = images[id]\n\n if (blobs[filename] !== undefined) images[id] = blobs[filename]\n else images[id] = images[id].split('\\\\').pop()\n }\n\n return images\n }\n\n // Parse embedded image data in FBXTree.Video.Content\n parseImage(videoNode) {\n const content = videoNode.Content\n const fileName = videoNode.RelativeFilename || videoNode.Filename\n const extension = fileName.slice(fileName.lastIndexOf('.') + 1).toLowerCase()\n\n let type\n\n switch (extension) {\n case 'bmp':\n type = 'image/bmp'\n break\n\n case 'jpg':\n case 'jpeg':\n type = 'image/jpeg'\n break\n\n case 'png':\n type = 'image/png'\n break\n\n case 'tif':\n type = 'image/tiff'\n break\n\n case 'tga':\n if (this.manager.getHandler('.tga') === null) {\n console.warn('FBXLoader: TGA loader not found, skipping ', fileName)\n }\n\n type = 'image/tga'\n break\n\n default:\n console.warn('FBXLoader: Image type \"' + extension + '\" is not supported.')\n return\n }\n\n if (typeof content === 'string') {\n // ASCII format\n\n return 'data:' + type + ';base64,' + content\n } else {\n // Binary Format\n\n const array = new Uint8Array(content)\n return window.URL.createObjectURL(new Blob([array], { type: type }))\n }\n }\n\n // Parse nodes in FBXTree.Objects.Texture\n // These contain details such as UV scaling, cropping, rotation etc and are connected\n // to images in FBXTree.Objects.Video\n parseTextures(images) {\n const textureMap = new Map()\n\n if ('Texture' in fbxTree.Objects) {\n const textureNodes = fbxTree.Objects.Texture\n for (const nodeID in textureNodes) {\n const texture = this.parseTexture(textureNodes[nodeID], images)\n textureMap.set(parseInt(nodeID), texture)\n }\n }\n\n return textureMap\n }\n\n // Parse individual node in FBXTree.Objects.Texture\n parseTexture(textureNode, images) {\n const texture = this.loadTexture(textureNode, images)\n\n texture.ID = textureNode.id\n\n texture.name = textureNode.attrName\n\n const wrapModeU = textureNode.WrapModeU\n const wrapModeV = textureNode.WrapModeV\n\n const valueU = wrapModeU !== undefined ? wrapModeU.value : 0\n const valueV = wrapModeV !== undefined ? wrapModeV.value : 0\n\n // http://download.autodesk.com/us/fbx/SDKdocs/FBX_SDK_Help/files/fbxsdkref/class_k_fbx_texture.html#889640e63e2e681259ea81061b85143a\n // 0: repeat(default), 1: clamp\n\n texture.wrapS = valueU === 0 ? RepeatWrapping : ClampToEdgeWrapping\n texture.wrapT = valueV === 0 ? RepeatWrapping : ClampToEdgeWrapping\n\n if ('Scaling' in textureNode) {\n const values = textureNode.Scaling.value\n\n texture.repeat.x = values[0]\n texture.repeat.y = values[1]\n }\n\n return texture\n }\n\n // load a texture specified as a blob or data URI, or via an external URL using TextureLoader\n loadTexture(textureNode, images) {\n let fileName\n\n const currentPath = this.textureLoader.path\n\n const children = connections.get(textureNode.id).children\n\n if (children !== undefined && children.length > 0 && images[children[0].ID] !== undefined) {\n fileName = images[children[0].ID]\n\n if (fileName.indexOf('blob:') === 0 || fileName.indexOf('data:') === 0) {\n this.textureLoader.setPath(undefined)\n }\n }\n\n let texture\n\n const extension = textureNode.FileName.slice(-3).toLowerCase()\n\n if (extension === 'tga') {\n const loader = this.manager.getHandler('.tga')\n\n if (loader === null) {\n console.warn('FBXLoader: TGA loader not found, creating placeholder texture for', textureNode.RelativeFilename)\n texture = new Texture()\n } else {\n loader.setPath(this.textureLoader.path)\n texture = loader.load(fileName)\n }\n } else if (extension === 'psd') {\n console.warn(\n 'FBXLoader: PSD textures are not supported, creating placeholder texture for',\n textureNode.RelativeFilename,\n )\n texture = new Texture()\n } else {\n texture = this.textureLoader.load(fileName)\n }\n\n this.textureLoader.setPath(currentPath)\n\n return texture\n }\n\n // Parse nodes in FBXTree.Objects.Material\n parseMaterials(textureMap) {\n const materialMap = new Map()\n\n if ('Material' in fbxTree.Objects) {\n const materialNodes = fbxTree.Objects.Material\n\n for (const nodeID in materialNodes) {\n const material = this.parseMaterial(materialNodes[nodeID], textureMap)\n\n if (material !== null) materialMap.set(parseInt(nodeID), material)\n }\n }\n\n return materialMap\n }\n\n // Parse single node in FBXTree.Objects.Material\n // Materials are connected to texture maps in FBXTree.Objects.Textures\n // FBX format currently only supports Lambert and Phong shading models\n parseMaterial(materialNode, textureMap) {\n const ID = materialNode.id\n const name = materialNode.attrName\n let type = materialNode.ShadingModel\n\n // Case where FBX wraps shading model in property object.\n if (typeof type === 'object') {\n type = type.value\n }\n\n // Ignore unused materials which don't have any connections.\n if (!connections.has(ID)) return null\n\n const parameters = this.parseParameters(materialNode, textureMap, ID)\n\n let material\n\n switch (type.toLowerCase()) {\n case 'phong':\n material = new MeshPhongMaterial()\n break\n case 'lambert':\n material = new MeshLambertMaterial()\n break\n default:\n console.warn('THREE.FBXLoader: unknown material type \"%s\". Defaulting to MeshPhongMaterial.', type)\n material = new MeshPhongMaterial()\n break\n }\n\n material.setValues(parameters)\n material.name = name\n\n return material\n }\n\n // Parse FBX material and return parameters suitable for a three.js material\n // Also parse the texture map and return any textures associated with the material\n parseParameters(materialNode, textureMap, ID) {\n const parameters = {}\n\n if (materialNode.BumpFactor) {\n parameters.bumpScale = materialNode.BumpFactor.value\n }\n\n if (materialNode.Diffuse) {\n parameters.color = new Color().fromArray(materialNode.Diffuse.value)\n } else if (\n materialNode.DiffuseColor &&\n (materialNode.DiffuseColor.type === 'Color' || materialNode.DiffuseColor.type === 'ColorRGB')\n ) {\n // The blender exporter exports diffuse here instead of in materialNode.Diffuse\n parameters.color = new Color().fromArray(materialNode.DiffuseColor.value)\n }\n\n if (materialNode.DisplacementFactor) {\n parameters.displacementScale = materialNode.DisplacementFactor.value\n }\n\n if (materialNode.Emissive) {\n parameters.emissive = new Color().fromArray(materialNode.Emissive.value)\n } else if (\n materialNode.EmissiveColor &&\n (materialNode.EmissiveColor.type === 'Color' || materialNode.EmissiveColor.type === 'ColorRGB')\n ) {\n // The blender exporter exports emissive color here instead of in materialNode.Emissive\n parameters.emissive = new Color().fromArray(materialNode.EmissiveColor.value)\n }\n\n if (materialNode.EmissiveFactor) {\n parameters.emissiveIntensity = parseFloat(materialNode.EmissiveFactor.value)\n }\n\n if (materialNode.Opacity) {\n parameters.opacity = parseFloat(materialNode.Opacity.value)\n }\n\n if (parameters.opacity < 1.0) {\n parameters.transparent = true\n }\n\n if (materialNode.ReflectionFactor) {\n parameters.reflectivity = materialNode.ReflectionFactor.value\n }\n\n if (materialNode.Shininess) {\n parameters.shininess = materialNode.Shininess.value\n }\n\n if (materialNode.Specular) {\n parameters.specular = new Color().fromArray(materialNode.Specular.value)\n } else if (materialNode.SpecularColor && materialNode.SpecularColor.type === 'Color') {\n // The blender exporter exports specular color here instead of in materialNode.Specular\n parameters.specular = new Color().fromArray(materialNode.SpecularColor.value)\n }\n\n const scope = this\n connections.get(ID).children.forEach(function (child) {\n const type = child.relationship\n\n switch (type) {\n case 'Bump':\n parameters.bumpMap = scope.getTexture(textureMap, child.ID)\n break\n\n case 'Maya|TEX_ao_map':\n parameters.aoMap = scope.getTexture(textureMap, child.ID)\n break\n\n case 'DiffuseColor':\n case 'Maya|TEX_color_map':\n parameters.map = scope.getTexture(textureMap, child.ID)\n if (parameters.map !== undefined) {\n if ('colorSpace' in parameters.map) parameters.map.colorSpace = 'srgb'\n else parameters.map.encoding = 3001 // sRGBEncoding\n }\n\n break\n\n case 'DisplacementColor':\n parameters.displacementMap = scope.getTexture(textureMap, child.ID)\n break\n\n case 'EmissiveColor':\n parameters.emissiveMap = scope.getTexture(textureMap, child.ID)\n if (parameters.emissiveMap !== undefined) {\n if ('colorSpace' in parameters.emissiveMap) parameters.emissiveMap.colorSpace = 'srgb'\n else parameters.emissiveMap.encoding = 3001 // sRGBEncoding\n }\n\n break\n\n case 'NormalMap':\n case 'Maya|TEX_normal_map':\n parameters.normalMap = scope.getTexture(textureMap, child.ID)\n break\n\n case 'ReflectionColor':\n parameters.envMap = scope.getTexture(textureMap, child.ID)\n if (parameters.envMap !== undefined) {\n parameters.envMap.mapping = EquirectangularReflectionMapping\n\n if ('colorSpace' in parameters.envMap) parameters.envMap.colorSpace = 'srgb'\n else parameters.envMap.encoding = 3001 // sRGBEncoding\n }\n\n break\n\n case 'SpecularColor':\n parameters.specularMap = scope.getTexture(textureMap, child.ID)\n if (parameters.specularMap !== undefined) {\n if ('colorSpace' in parameters.specularMap) parameters.specularMap.colorSpace = 'srgb'\n else parameters.specularMap.encoding = 3001 // sRGBEncoding\n }\n\n break\n\n case 'TransparentColor':\n case 'TransparencyFactor':\n parameters.alphaMap = scope.getTexture(textureMap, child.ID)\n parameters.transparent = true\n break\n\n case 'AmbientColor':\n case 'ShininessExponent': // AKA glossiness map\n case 'SpecularFactor': // AKA specularLevel\n case 'VectorDisplacementColor': // NOTE: Seems to be a copy of DisplacementColor\n default:\n console.warn('THREE.FBXLoader: %s map is not supported in three.js, skipping texture.', type)\n break\n }\n })\n\n return parameters\n }\n\n // get a texture from the textureMap for use by a material.\n getTexture(textureMap, id) {\n // if the texture is a layered texture, just use the first layer and issue a warning\n if ('LayeredTexture' in fbxTree.Objects && id in fbxTree.Objects.LayeredTexture) {\n console.warn('THREE.FBXLoader: layered textures are not supported in three.js. Discarding all but first layer.')\n id = connections.get(id).children[0].ID\n }\n\n return textureMap.get(id)\n }\n\n // Parse nodes in FBXTree.Objects.Deformer\n // Deformer node can contain skinning or Vertex Cache animation data, however only skinning is supported here\n // Generates map of Skeleton-like objects for use later when generating and binding skeletons.\n parseDeformers() {\n const skeletons = {}\n const morphTargets = {}\n\n if ('Deformer' in fbxTree.Objects) {\n const DeformerNodes = fbxTree.Objects.Deformer\n\n for (const nodeID in DeformerNodes) {\n const deformerNode = DeformerNodes[nodeID]\n\n const relationships = connections.get(parseInt(nodeID))\n\n if (deformerNode.attrType === 'Skin') {\n const skeleton = this.parseSkeleton(relationships, DeformerNodes)\n skeleton.ID = nodeID\n\n if (relationships.parents.length > 1) {\n console.warn('THREE.FBXLoader: skeleton attached to more than one geometry is not supported.')\n }\n skeleton.geometryID = relationships.parents[0].ID\n\n skeletons[nodeID] = skeleton\n } else if (deformerNode.attrType === 'BlendShape') {\n const morphTarget = {\n id: nodeID,\n }\n\n morphTarget.rawTargets = this.parseMorphTargets(relationships, DeformerNodes)\n morphTarget.id = nodeID\n\n if (relationships.parents.length > 1) {\n console.warn('THREE.FBXLoader: morph target attached to more than one geometry is not supported.')\n }\n\n morphTargets[nodeID] = morphTarget\n }\n }\n }\n\n return {\n skeletons: skeletons,\n morphTargets: morphTargets,\n }\n }\n\n // Parse single nodes in FBXTree.Objects.Deformer\n // The top level skeleton node has type 'Skin' and sub nodes have type 'Cluster'\n // Each skin node represents a skeleton and each cluster node represents a bone\n parseSkeleton(relationships, deformerNodes) {\n const rawBones = []\n\n relationships.children.forEach(function (child) {\n const boneNode = deformerNodes[child.ID]\n\n if (boneNode.attrType !== 'Cluster') return\n\n const rawBone = {\n ID: child.ID,\n indices: [],\n weights: [],\n transformLink: new Matrix4().fromArray(boneNode.TransformLink.a),\n // transform: new Matrix4().fromArray( boneNode.Transform.a ),\n // linkMode: boneNode.Mode,\n }\n\n if ('Indexes' in boneNode) {\n rawBone.indices = boneNode.Indexes.a\n rawBone.weights = boneNode.Weights.a\n }\n\n rawBones.push(rawBone)\n })\n\n return {\n rawBones: rawBones,\n bones: [],\n }\n }\n\n // The top level morph deformer node has type \"BlendShape\" and sub nodes have type \"BlendShapeChannel\"\n parseMorphTargets(relationships, deformerNodes) {\n const rawMorphTargets = []\n\n for (let i = 0; i < relationships.children.length; i++) {\n const child = relationships.children[i]\n\n const morphTargetNode = deformerNodes[child.ID]\n\n const rawMorphTarget = {\n name: morphTargetNode.attrName,\n initialWeight: morphTargetNode.DeformPercent,\n id: morphTargetNode.id,\n fullWeights: morphTargetNode.FullWeights.a,\n }\n\n if (morphTargetNode.attrType !== 'BlendShapeChannel') return\n\n rawMorphTarget.geoID = connections.get(parseInt(child.ID)).children.filter(function (child) {\n return child.relationship === undefined\n })[0].ID\n\n rawMorphTargets.push(rawMorphTarget)\n }\n\n return rawMorphTargets\n }\n\n // create the main Group() to be returned by the loader\n parseScene(deformers, geometryMap, materialMap) {\n sceneGraph = new Group()\n\n const modelMap = this.parseModels(deformers.skeletons, geometryMap, materialMap)\n\n const modelNodes = fbxTree.Objects.Model\n\n const scope = this\n modelMap.forEach(function (model) {\n const modelNode = modelNodes[model.ID]\n scope.setLookAtProperties(model, modelNode)\n\n const parentConnections = connections.get(model.ID).parents\n\n parentConnections.forEach(function (connection) {\n const parent = modelMap.get(connection.ID)\n if (parent !== undefined) parent.add(model)\n })\n\n if (model.parent === null) {\n sceneGraph.add(model)\n }\n })\n\n this.bindSkeleton(deformers.skeletons, geometryMap, modelMap)\n\n this.createAmbientLight()\n\n sceneGraph.traverse(function (node) {\n if (node.userData.transformData) {\n if (node.parent) {\n node.userData.transformData.parentMatrix = node.parent.matrix\n node.userData.transformData.parentMatrixWorld = node.parent.matrixWorld\n }\n\n const transform = generateTransform(node.userData.transformData)\n\n node.applyMatrix4(transform)\n node.updateWorldMatrix()\n }\n })\n\n const animations = new AnimationParser().parse()\n\n // if all the models where already combined in a single group, just return that\n if (sceneGraph.children.length === 1 && sceneGraph.children[0].isGroup) {\n sceneGraph.children[0].animations = animations\n sceneGraph = sceneGraph.children[0]\n }\n\n sceneGraph.animations = animations\n }\n\n // parse nodes in FBXTree.Objects.Model\n parseModels(skeletons, geometryMap, materialMap) {\n const modelMap = new Map()\n const modelNodes = fbxTree.Objects.Model\n\n for (const nodeID in modelNodes) {\n const id = parseInt(nodeID)\n const node = modelNodes[nodeID]\n const relationships = connections.get(id)\n\n let model = this.buildSkeleton(relationships, skeletons, id, node.attrName)\n\n if (!model) {\n switch (node.attrType) {\n case 'Camera':\n model = this.createCamera(relationships)\n break\n case 'Light':\n model = this.createLight(relationships)\n break\n case 'Mesh':\n model = this.createMesh(relationships, geometryMap, materialMap)\n break\n case 'NurbsCurve':\n model = this.createCurve(relationships, geometryMap)\n break\n case 'LimbNode':\n case 'Root':\n model = new Bone()\n break\n case 'Null':\n default:\n model = new Group()\n break\n }\n\n model.name = node.attrName ? PropertyBinding.sanitizeNodeName(node.attrName) : ''\n\n model.ID = id\n }\n\n this.getTransformData(model, node)\n modelMap.set(id, model)\n }\n\n return modelMap\n }\n\n buildSkeleton(relationships, skeletons, id, name) {\n let bone = null\n\n relationships.parents.forEach(function (parent) {\n for (const ID in skeletons) {\n const skeleton = skeletons[ID]\n\n skeleton.rawBones.forEach(function (rawBone, i) {\n if (rawBone.ID === parent.ID) {\n const subBone = bone\n bone = new Bone()\n\n bone.matrixWorld.copy(rawBone.transformLink)\n\n // set name and id here - otherwise in cases where \"subBone\" is created it will not have a name / id\n\n bone.name = name ? PropertyBinding.sanitizeNodeName(name) : ''\n bone.ID = id\n\n skeleton.bones[i] = bone\n\n // In cases where a bone is shared between multiple meshes\n // duplicate the bone here and and it as a child of the first bone\n if (subBone !== null) {\n bone.add(subBone)\n }\n }\n })\n }\n })\n\n return bone\n }\n\n // create a PerspectiveCamera or OrthographicCamera\n createCamera(relationships) {\n let model\n let cameraAttribute\n\n relationships.children.forEach(function (child) {\n const attr = fbxTree.Objects.NodeAttribute[child.ID]\n\n if (attr !== undefined) {\n cameraAttribute = attr\n }\n })\n\n if (cameraAttribute === undefined) {\n model = new Object3D()\n } else {\n let type = 0\n if (cameraAttribute.CameraProjectionType !== undefined && cameraAttribute.CameraProjectionType.value === 1) {\n type = 1\n }\n\n let nearClippingPlane = 1\n if (cameraAttribute.NearPlane !== undefined) {\n nearClippingPlane = cameraAttribute.NearPlane.value / 1000\n }\n\n let farClippingPlane = 1000\n if (cameraAttribute.FarPlane !== undefined) {\n farClippingPlane = cameraAttribute.FarPlane.value / 1000\n }\n\n let width = window.innerWidth\n let height = window.innerHeight\n\n if (cameraAttribute.AspectWidth !== undefined && cameraAttribute.AspectHeight !== undefined) {\n width = cameraAttribute.AspectWidth.value\n height = cameraAttribute.AspectHeight.value\n }\n\n const aspect = width / height\n\n let fov = 45\n if (cameraAttribute.FieldOfView !== undefined) {\n fov = cameraAttribute.FieldOfView.value\n }\n\n const focalLength = cameraAttribute.FocalLength ? cameraAttribute.FocalLength.value : null\n\n switch (type) {\n case 0: // Perspective\n model = new PerspectiveCamera(fov, aspect, nearClippingPlane, farClippingPlane)\n if (focalLength !== null) model.setFocalLength(focalLength)\n break\n\n case 1: // Orthographic\n model = new OrthographicCamera(\n -width / 2,\n width / 2,\n height / 2,\n -height / 2,\n nearClippingPlane,\n farClippingPlane,\n )\n break\n\n default:\n console.warn('THREE.FBXLoader: Unknown camera type ' + type + '.')\n model = new Object3D()\n break\n }\n }\n\n return model\n }\n\n // Create a DirectionalLight, PointLight or SpotLight\n createLight(relationships) {\n let model\n let lightAttribute\n\n relationships.children.forEach(function (child) {\n const attr = fbxTree.Objects.NodeAttribute[child.ID]\n\n if (attr !== undefined) {\n lightAttribute = attr\n }\n })\n\n if (lightAttribute === undefined) {\n model = new Object3D()\n } else {\n let type\n\n // LightType can be undefined for Point lights\n if (lightAttribute.LightType === undefined) {\n type = 0\n } else {\n type = lightAttribute.LightType.value\n }\n\n let color = 0xffffff\n\n if (lightAttribute.Color !== undefined) {\n color = new Color().fromArray(lightAttribute.Color.value)\n }\n\n let intensity = lightAttribute.Intensity === undefined ? 1 : lightAttribute.Intensity.value / 100\n\n // light disabled\n if (lightAttribute.CastLightOnObject !== undefined && lightAttribute.CastLightOnObject.value === 0) {\n intensity = 0\n }\n\n let distance = 0\n if (lightAttribute.FarAttenuationEnd !== undefined) {\n if (lightAttribute.EnableFarAttenuation !== undefined && lightAttribute.EnableFarAttenuation.value === 0) {\n distance = 0\n } else {\n distance = lightAttribute.FarAttenuationEnd.value\n }\n }\n\n // TODO: could this be calculated linearly from FarAttenuationStart to FarAttenuationEnd?\n const decay = 1\n\n switch (type) {\n case 0: // Point\n model = new PointLight(color, intensity, distance, decay)\n break\n\n case 1: // Directional\n model = new DirectionalLight(color, intensity)\n break\n\n case 2: // Spot\n let angle = Math.PI / 3\n\n if (lightAttribute.InnerAngle !== undefined) {\n angle = MathUtils.degToRad(lightAttribute.InnerAngle.value)\n }\n\n let penumbra = 0\n if (lightAttribute.OuterAngle !== undefined) {\n // TODO: this is not correct - FBX calculates outer and inner angle in degrees\n // with OuterAngle > InnerAngle && OuterAngle <= Math.PI\n // while three.js uses a penumbra between (0, 1) to attenuate the inner angle\n penumbra = MathUtils.degToRad(lightAttribute.OuterAngle.value)\n penumbra = Math.max(penumbra, 1)\n }\n\n model = new SpotLight(color, intensity, distance, angle, penumbra, decay)\n break\n\n default:\n console.warn(\n 'THREE.FBXLoader: Unknown light type ' + lightAttribute.LightType.value + ', defaulting to a PointLight.',\n )\n model = new PointLight(color, intensity)\n break\n }\n\n if (lightAttribute.CastShadows !== undefined && lightAttribute.CastShadows.value === 1) {\n model.castShadow = true\n }\n }\n\n return model\n }\n\n createMesh(relationships, geometryMap, materialMap) {\n let model\n let geometry = null\n let material = null\n const materials = []\n\n // get geometry and materials(s) from connections\n relationships.children.forEach(function (child) {\n if (geometryMap.has(child.ID)) {\n geometry = geometryMap.get(child.ID)\n }\n\n if (materialMap.has(child.ID)) {\n materials.push(materialMap.get(child.ID))\n }\n })\n\n if (materials.length > 1) {\n material = materials\n } else if (materials.length > 0) {\n material = materials[0]\n } else {\n material = new MeshPhongMaterial({ color: 0xcccccc })\n materials.push(material)\n }\n\n if ('color' in geometry.attributes) {\n materials.forEach(function (material) {\n material.vertexColors = true\n })\n }\n\n if (geometry.FBX_Deformer) {\n model = new SkinnedMesh(geometry, material)\n model.normalizeSkinWeights()\n } else {\n model = new Mesh(geometry, material)\n }\n\n return model\n }\n\n createCurve(relationships, geometryMap) {\n const geometry = relationships.children.reduce(function (geo, child) {\n if (geometryMap.has(child.ID)) geo = geometryMap.get(child.ID)\n\n return geo\n }, null)\n\n // FBX does not list materials for Nurbs lines, so we'll just put our own in here.\n const material = new LineBasicMaterial({ color: 0x3300ff, linewidth: 1 })\n return new Line(geometry, material)\n }\n\n // parse the model node for transform data\n getTransformData(model, modelNode) {\n const transformData = {}\n\n if ('InheritType' in modelNode) transformData.inheritType = parseInt(modelNode.InheritType.value)\n\n if ('RotationOrder' in modelNode) transformData.eulerOrder = getEulerOrder(modelNode.RotationOrder.value)\n else transformData.eulerOrder = 'ZYX'\n\n if ('Lcl_Translation' in modelNode) transformData.translation = modelNode.Lcl_Translation.value\n\n if ('PreRotation' in modelNode) transformData.preRotation = modelNode.PreRotation.value\n if ('Lcl_Rotation' in modelNode) transformData.rotation = modelNode.Lcl_Rotation.value\n if ('PostRotation' in modelNode) transformData.postRotation = modelNode.PostRotation.value\n\n if ('Lcl_Scaling' in modelNode) transformData.scale = modelNode.Lcl_Scaling.value\n\n if ('ScalingOffset' in modelNode) transformData.scalingOffset = modelNode.ScalingOffset.value\n if ('ScalingPivot' in modelNode) transformData.scalingPivot = modelNode.ScalingPivot.value\n\n if ('RotationOffset' in modelNode) transformData.rotationOffset = modelNode.RotationOffset.value\n if ('RotationPivot' in modelNode) transformData.rotationPivot = modelNode.RotationPivot.value\n\n model.userData.transformData = transformData\n }\n\n setLookAtProperties(model, modelNode) {\n if ('LookAtProperty' in modelNode) {\n const children = connections.get(model.ID).children\n\n children.forEach(function (child) {\n if (child.relationship === 'LookAtProperty') {\n const lookAtTarget = fbxTree.Objects.Model[child.ID]\n\n if ('Lcl_Translation' in lookAtTarget) {\n const pos = lookAtTarget.Lcl_Translation.value\n\n // DirectionalLight, SpotLight\n if (model.target !== undefined) {\n model.target.position.fromArray(pos)\n sceneGraph.add(model.target)\n } else {\n // Cameras and other Object3Ds\n\n model.lookAt(new Vector3().fromArray(pos))\n }\n }\n }\n })\n }\n }\n\n bindSkeleton(skeletons, geometryMap, modelMap) {\n const bindMatrices = this.parsePoseNodes()\n\n for (const ID in skeletons) {\n const skeleton = skeletons[ID]\n\n const parents = connections.get(parseInt(skeleton.ID)).parents\n\n parents.forEach(function (parent) {\n if (geometryMap.has(parent.ID)) {\n const geoID = parent.ID\n const geoRelationships = connections.get(geoID)\n\n geoRelationships.parents.forEach(function (geoConnParent) {\n if (modelMap.has(geoConnParent.ID)) {\n const model = modelMap.get(geoConnParent.ID)\n\n model.bind(new Skeleton(skeleton.bones), bindMatrices[geoConnParent.ID])\n }\n })\n }\n })\n }\n }\n\n parsePoseNodes() {\n const bindMatrices = {}\n\n if ('Pose' in fbxTree.Objects) {\n const BindPoseNode = fbxTree.Objects.Pose\n\n for (const nodeID in BindPoseNode) {\n if (BindPoseNode[nodeID].attrType === 'BindPose' && BindPoseNode[nodeID].NbPoseNodes > 0) {\n const poseNodes = BindPoseNode[nodeID].PoseNode\n\n if (Array.isArray(poseNodes)) {\n poseNodes.forEach(function (poseNode) {\n bindMatrices[poseNode.Node] = new Matrix4().fromArray(poseNode.Matrix.a)\n })\n } else {\n bindMatrices[poseNodes.Node] = new Matrix4().fromArray(poseNodes.Matrix.a)\n }\n }\n }\n }\n\n return bindMatrices\n }\n\n // Parse ambient color in FBXTree.GlobalSettings - if it's not set to black (default), create an ambient light\n createAmbientLight() {\n if ('GlobalSettings' in fbxTree && 'AmbientColor' in fbxTree.GlobalSettings) {\n const ambientColor = fbxTree.GlobalSettings.AmbientColor.value\n const r = ambientColor[0]\n const g = ambientColor[1]\n const b = ambientColor[2]\n\n if (r !== 0 || g !== 0 || b !== 0) {\n const color = new Color(r, g, b)\n sceneGraph.add(new AmbientLight(color, 1))\n }\n }\n }\n}\n\n// parse Geometry data from FBXTree and return map of BufferGeometries\nclass GeometryParser {\n // Parse nodes in FBXTree.Objects.Geometry\n parse(deformers) {\n const geometryMap = new Map()\n\n if ('Geometry' in fbxTree.Objects) {\n const geoNodes = fbxTree.Objects.Geometry\n\n for (const nodeID in geoNodes) {\n const relationships = connections.get(parseInt(nodeID))\n const geo = this.parseGeometry(relationships, geoNodes[nodeID], deformers)\n\n geometryMap.set(parseInt(nodeID), geo)\n }\n }\n\n return geometryMap\n }\n\n // Parse single node in FBXTree.Objects.Geometry\n parseGeometry(relationships, geoNode, deformers) {\n switch (geoNode.attrType) {\n case 'Mesh':\n return this.parseMeshGeometry(relationships, geoNode, deformers)\n break\n\n case 'NurbsCurve':\n return this.parseNurbsGeometry(geoNode)\n break\n }\n }\n\n // Parse single node mesh geometry in FBXTree.Objects.Geometry\n parseMeshGeometry(relationships, geoNode, deformers) {\n const skeletons = deformers.skeletons\n const morphTargets = []\n\n const modelNodes = relationships.parents.map(function (parent) {\n return fbxTree.Objects.Model[parent.ID]\n })\n\n // don't create geometry if it is not associated with any models\n if (modelNodes.length === 0) return\n\n const skeleton = relationships.children.reduce(function (skeleton, child) {\n if (skeletons[child.ID] !== undefined) skeleton = skeletons[child.ID]\n\n return skeleton\n }, null)\n\n relationships.children.forEach(function (child) {\n if (deformers.morphTargets[child.ID] !== undefined) {\n morphTargets.push(deformers.morphTargets[child.ID])\n }\n })\n\n // Assume one model and get the preRotation from that\n // if there is more than one model associated with the geometry this may cause problems\n const modelNode = modelNodes[0]\n\n const transformData = {}\n\n if ('RotationOrder' in modelNode) transformData.eulerOrder = getEulerOrder(modelNode.RotationOrder.value)\n if ('InheritType' in modelNode) transformData.inheritType = parseInt(modelNode.InheritType.value)\n\n if ('GeometricTranslation' in modelNode) transformData.translation = modelNode.GeometricTranslation.value\n if ('GeometricRotation' in modelNode) transformData.rotation = modelNode.GeometricRotation.value\n if ('GeometricScaling' in modelNode) transformData.scale = modelNode.GeometricScaling.value\n\n const transform = generateTransform(transformData)\n\n return this.genGeometry(geoNode, skeleton, morphTargets, transform)\n }\n\n // Generate a BufferGeometry from a node in FBXTree.Objects.Geometry\n genGeometry(geoNode, skeleton, morphTargets, preTransform) {\n const geo = new BufferGeometry()\n if (geoNode.attrName) geo.name = geoNode.attrName\n\n const geoInfo = this.parseGeoNode(geoNode, skeleton)\n const buffers = this.genBuffers(geoInfo)\n\n const positionAttribute = new Float32BufferAttribute(buffers.vertex, 3)\n\n positionAttribute.applyMatrix4(preTransform)\n\n geo.setAttribute('position', positionAttribute)\n\n if (buffers.colors.length > 0) {\n geo.setAttribute('color', new Float32BufferAttribute(buffers.colors, 3))\n }\n\n if (skeleton) {\n geo.setAttribute('skinIndex', new Uint16BufferAttribute(buffers.weightsIndices, 4))\n\n geo.setAttribute('skinWeight', new Float32BufferAttribute(buffers.vertexWeights, 4))\n\n // used later to bind the skeleton to the model\n geo.FBX_Deformer = skeleton\n }\n\n if (buffers.normal.length > 0) {\n const normalMatrix = new Matrix3().getNormalMatrix(preTransform)\n\n const normalAttribute = new Float32BufferAttribute(buffers.normal, 3)\n normalAttribute.applyNormalMatrix(normalMatrix)\n\n geo.setAttribute('normal', normalAttribute)\n }\n\n buffers.uvs.forEach(function (uvBuffer, i) {\n if (UV1 === 'uv2') i++;\n const name = i === 0 ? 'uv' : `uv${i}`;\n\n geo.setAttribute(name, new Float32BufferAttribute(buffers.uvs[i], 2))\n })\n\n if (geoInfo.material && geoInfo.material.mappingType !== 'AllSame') {\n // Convert the material indices of each vertex into rendering groups on the geometry.\n let prevMaterialIndex = buffers.materialIndex[0]\n let startIndex = 0\n\n buffers.materialIndex.forEach(function (currentIndex, i) {\n if (currentIndex !== prevMaterialIndex) {\n geo.addGroup(startIndex, i - startIndex, prevMaterialIndex)\n\n prevMaterialIndex = currentIndex\n startIndex = i\n }\n })\n\n // the loop above doesn't add the last group, do that here.\n if (geo.groups.length > 0) {\n const lastGroup = geo.groups[geo.groups.length - 1]\n const lastIndex = lastGroup.start + lastGroup.count\n\n if (lastIndex !== buffers.materialIndex.length) {\n geo.addGroup(lastIndex, buffers.materialIndex.length - lastIndex, prevMaterialIndex)\n }\n }\n\n // case where there are multiple materials but the whole geometry is only\n // using one of them\n if (geo.groups.length === 0) {\n geo.addGroup(0, buffers.materialIndex.length, buffers.materialIndex[0])\n }\n }\n\n this.addMorphTargets(geo, geoNode, morphTargets, preTransform)\n\n return geo\n }\n\n parseGeoNode(geoNode, skeleton) {\n const geoInfo = {}\n\n geoInfo.vertexPositions = geoNode.Vertices !== undefined ? geoNode.Vertices.a : []\n geoInfo.vertexIndices = geoNode.PolygonVertexIndex !== undefined ? geoNode.PolygonVertexIndex.a : []\n\n if (geoNode.LayerElementColor) {\n geoInfo.color = this.parseVertexColors(geoNode.LayerElementColor[0])\n }\n\n if (geoNode.LayerElementMaterial) {\n geoInfo.material = this.parseMaterialIndices(geoNode.LayerElementMaterial[0])\n }\n\n if (geoNode.LayerElementNormal) {\n geoInfo.normal = this.parseNormals(geoNode.LayerElementNormal[0])\n }\n\n if (geoNode.LayerElementUV) {\n geoInfo.uv = []\n\n let i = 0\n while (geoNode.LayerElementUV[i]) {\n if (geoNode.LayerElementUV[i].UV) {\n geoInfo.uv.push(this.parseUVs(geoNode.LayerElementUV[i]))\n }\n\n i++\n }\n }\n\n geoInfo.weightTable = {}\n\n if (skeleton !== null) {\n geoInfo.skeleton = skeleton\n\n skeleton.rawBones.forEach(function (rawBone, i) {\n // loop over the bone's vertex indices and weights\n rawBone.indices.forEach(function (index, j) {\n if (geoInfo.weightTable[index] === undefined) geoInfo.weightTable[index] = []\n\n geoInfo.weightTable[index].push({\n id: i,\n weight: rawBone.weights[j],\n })\n })\n })\n }\n\n return geoInfo\n }\n\n genBuffers(geoInfo) {\n const buffers = {\n vertex: [],\n normal: [],\n colors: [],\n uvs: [],\n materialIndex: [],\n vertexWeights: [],\n weightsIndices: [],\n }\n\n let polygonIndex = 0\n let faceLength = 0\n let displayedWeightsWarning = false\n\n // these will hold data for a single face\n let facePositionIndexes = []\n let faceNormals = []\n let faceColors = []\n let faceUVs = []\n let faceWeights = []\n let faceWeightIndices = []\n\n const scope = this\n geoInfo.vertexIndices.forEach(function (vertexIndex, polygonVertexIndex) {\n let materialIndex\n let endOfFace = false\n\n // Face index and vertex index arrays are combined in a single array\n // A cube with quad faces looks like this:\n // PolygonVertexIndex: *24 {\n // a: 0, 1, 3, -3, 2, 3, 5, -5, 4, 5, 7, -7, 6, 7, 1, -1, 1, 7, 5, -4, 6, 0, 2, -5\n // }\n // Negative numbers mark the end of a face - first face here is 0, 1, 3, -3\n // to find index of last vertex bit shift the index: ^ - 1\n if (vertexIndex < 0) {\n vertexIndex = vertexIndex ^ -1 // equivalent to ( x * -1 ) - 1\n endOfFace = true\n }\n\n let weightIndices = []\n let weights = []\n\n facePositionIndexes.push(vertexIndex * 3, vertexIndex * 3 + 1, vertexIndex * 3 + 2)\n\n if (geoInfo.color) {\n const data = getData(polygonVertexIndex, polygonIndex, vertexIndex, geoInfo.color)\n\n faceColors.push(data[0], data[1], data[2])\n }\n\n if (geoInfo.skeleton) {\n if (geoInfo.weightTable[vertexIndex] !== undefined) {\n geoInfo.weightTable[vertexIndex].forEach(function (wt) {\n weights.push(wt.weight)\n weightIndices.push(wt.id)\n })\n }\n\n if (weights.length > 4) {\n if (!displayedWeightsWarning) {\n console.warn(\n 'THREE.FBXLoader: Vertex has more than 4 skinning weights assigned to vertex. Deleting additional weights.',\n )\n displayedWeightsWarning = true\n }\n\n const wIndex = [0, 0, 0, 0]\n const Weight = [0, 0, 0, 0]\n\n weights.forEach(function (weight, weightIndex) {\n let currentWeight = weight\n let currentIndex = weightIndices[weightIndex]\n\n Weight.forEach(function (comparedWeight, comparedWeightIndex, comparedWeightArray) {\n if (currentWeight > comparedWeight) {\n comparedWeightArray[comparedWeightIndex] = currentWeight\n currentWeight = comparedWeight\n\n const tmp = wIndex[comparedWeightIndex]\n wIndex[comparedWeightIndex] = currentIndex\n currentIndex = tmp\n }\n })\n })\n\n weightIndices = wIndex\n weights = Weight\n }\n\n // if the weight array is shorter than 4 pad with 0s\n while (weights.length < 4) {\n weights.push(0)\n weightIndices.push(0)\n }\n\n for (let i = 0; i < 4; ++i) {\n faceWeights.push(weights[i])\n faceWeightIndices.push(weightIndices[i])\n }\n }\n\n if (geoInfo.normal) {\n const data = getData(polygonVertexIndex, polygonIndex, vertexIndex, geoInfo.normal)\n\n faceNormals.push(data[0], data[1], data[2])\n }\n\n if (geoInfo.material && geoInfo.material.mappingType !== 'AllSame') {\n materialIndex = getData(polygonVertexIndex, polygonIndex, vertexIndex, geoInfo.material)[0]\n }\n\n if (geoInfo.uv) {\n geoInfo.uv.forEach(function (uv, i) {\n const data = getData(polygonVertexIndex, polygonIndex, vertexIndex, uv)\n\n if (faceUVs[i] === undefined) {\n faceUVs[i] = []\n }\n\n faceUVs[i].push(data[0])\n faceUVs[i].push(data[1])\n })\n }\n\n faceLength++\n\n if (endOfFace) {\n scope.genFace(\n buffers,\n geoInfo,\n facePositionIndexes,\n materialIndex,\n faceNormals,\n faceColors,\n faceUVs,\n faceWeights,\n faceWeightIndices,\n faceLength,\n )\n\n polygonIndex++\n faceLength = 0\n\n // reset arrays for the next face\n facePositionIndexes = []\n faceNormals = []\n faceColors = []\n faceUVs = []\n faceWeights = []\n faceWeightIndices = []\n }\n })\n\n return buffers\n }\n\n // Generate data for a single face in a geometry. If the face is a quad then split it into 2 tris\n genFace(\n buffers,\n geoInfo,\n facePositionIndexes,\n materialIndex,\n faceNormals,\n faceColors,\n faceUVs,\n faceWeights,\n faceWeightIndices,\n faceLength,\n ) {\n for (let i = 2; i < faceLength; i++) {\n buffers.vertex.push(geoInfo.vertexPositions[facePositionIndexes[0]])\n buffers.vertex.push(geoInfo.vertexPositions[facePositionIndexes[1]])\n buffers.vertex.push(geoInfo.vertexPositions[facePositionIndexes[2]])\n\n buffers.vertex.push(geoInfo.vertexPositions[facePositionIndexes[(i - 1) * 3]])\n buffers.vertex.push(geoInfo.vertexPositions[facePositionIndexes[(i - 1) * 3 + 1]])\n buffers.vertex.push(geoInfo.vertexPositions[facePositionIndexes[(i - 1) * 3 + 2]])\n\n buffers.vertex.push(geoInfo.vertexPositions[facePositionIndexes[i * 3]])\n buffers.vertex.push(geoInfo.vertexPositions[facePositionIndexes[i * 3 + 1]])\n buffers.vertex.push(geoInfo.vertexPositions[facePositionIndexes[i * 3 + 2]])\n\n if (geoInfo.skeleton) {\n buffers.vertexWeights.push(faceWeights[0])\n buffers.vertexWeights.push(faceWeights[1])\n buffers.vertexWeights.push(faceWeights[2])\n buffers.vertexWeights.push(faceWeights[3])\n\n buffers.vertexWeights.push(faceWeights[(i - 1) * 4])\n buffers.vertexWeights.push(faceWeights[(i - 1) * 4 + 1])\n buffers.vertexWeights.push(faceWeights[(i - 1) * 4 + 2])\n buffers.vertexWeights.push(faceWeights[(i - 1) * 4 + 3])\n\n buffers.vertexWeights.push(faceWeights[i * 4])\n buffers.vertexWeights.push(faceWeights[i * 4 + 1])\n buffers.vertexWeights.push(faceWeights[i * 4 + 2])\n buffers.vertexWeights.push(faceWeights[i * 4 + 3])\n\n buffers.weightsIndices.push(faceWeightIndices[0])\n buffers.weightsIndices.push(faceWeightIndices[1])\n buffers.weightsIndices.push(faceWeightIndices[2])\n buffers.weightsIndices.push(faceWeightIndices[3])\n\n buffers.weightsIndices.push(faceWeightIndices[(i - 1) * 4])\n buffers.weightsIndices.push(faceWeightIndices[(i - 1) * 4 + 1])\n buffers.weightsIndices.push(faceWeightIndices[(i - 1) * 4 + 2])\n buffers.weightsIndices.push(faceWeightIndices[(i - 1) * 4 + 3])\n\n buffers.weightsIndices.push(faceWeightIndices[i * 4])\n buffers.weightsIndices.push(faceWeightIndices[i * 4 + 1])\n buffers.weightsIndices.push(faceWeightIndices[i * 4 + 2])\n buffers.weightsIndices.push(faceWeightIndices[i * 4 + 3])\n }\n\n if (geoInfo.color) {\n buffers.colors.push(faceColors[0])\n buffers.colors.push(faceColors[1])\n buffers.colors.push(faceColors[2])\n\n buffers.colors.push(faceColors[(i - 1) * 3])\n buffers.colors.push(faceColors[(i - 1) * 3 + 1])\n buffers.colors.push(faceColors[(i - 1) * 3 + 2])\n\n buffers.colors.push(faceColors[i * 3])\n buffers.colors.push(faceColors[i * 3 + 1])\n buffers.colors.push(faceColors[i * 3 + 2])\n }\n\n if (geoInfo.material && geoInfo.material.mappingType !== 'AllSame') {\n buffers.materialIndex.push(materialIndex)\n buffers.materialIndex.push(materialIndex)\n buffers.materialIndex.push(materialIndex)\n }\n\n if (geoInfo.normal) {\n buffers.normal.push(faceNormals[0])\n buffers.normal.push(faceNormals[1])\n buffers.normal.push(faceNormals[2])\n\n buffers.normal.push(faceNormals[(i - 1) * 3])\n buffers.normal.push(faceNormals[(i - 1) * 3 + 1])\n buffers.normal.push(faceNormals[(i - 1) * 3 + 2])\n\n buffers.normal.push(faceNormals[i * 3])\n buffers.normal.push(faceNormals[i * 3 + 1])\n buffers.normal.push(faceNormals[i * 3 + 2])\n }\n\n if (geoInfo.uv) {\n geoInfo.uv.forEach(function (uv, j) {\n if (buffers.uvs[j] === undefined) buffers.uvs[j] = []\n\n buffers.uvs[j].push(faceUVs[j][0])\n buffers.uvs[j].push(faceUVs[j][1])\n\n buffers.uvs[j].push(faceUVs[j][(i - 1) * 2])\n buffers.uvs[j].push(faceUVs[j][(i - 1) * 2 + 1])\n\n buffers.uvs[j].push(faceUVs[j][i * 2])\n buffers.uvs[j].push(faceUVs[j][i * 2 + 1])\n })\n }\n }\n }\n\n addMorphTargets(parentGeo, parentGeoNode, morphTargets, preTransform) {\n if (morphTargets.length === 0) return\n\n parentGeo.morphTargetsRelative = true\n\n parentGeo.morphAttributes.position = []\n // parentGeo.morphAttributes.normal = []; // not implemented\n\n const scope = this\n morphTargets.forEach(function (morphTarget) {\n morphTarget.rawTargets.forEach(function (rawTarget) {\n const morphGeoNode = fbxTree.Objects.Geometry[rawTarget.geoID]\n\n if (morphGeoNode !== undefined) {\n scope.genMorphGeometry(parentGeo, parentGeoNode, morphGeoNode, preTransform, rawTarget.name)\n }\n })\n })\n }\n\n // a morph geometry node is similar to a standard node, and the node is also contained\n // in FBXTree.Objects.Geometry, however it can only have attributes for position, normal\n // and a special attribute Index defining which vertices of the original geometry are affected\n // Normal and position attributes only have data for the vertices that are affected by the morph\n genMorphGeometry(parentGeo, parentGeoNode, morphGeoNode, preTransform, name) {\n const vertexIndices = parentGeoNode.PolygonVertexIndex !== undefined ? parentGeoNode.PolygonVertexIndex.a : []\n\n const morphPositionsSparse = morphGeoNode.Vertices !== undefined ? morphGeoNode.Vertices.a : []\n const indices = morphGeoNode.Indexes !== undefined ? morphGeoNode.Indexes.a : []\n\n const length = parentGeo.attributes.position.count * 3\n const morphPositions = new Float32Array(length)\n\n for (let i = 0; i < indices.length; i++) {\n const morphIndex = indices[i] * 3\n\n morphPositions[morphIndex] = morphPositionsSparse[i * 3]\n morphPositions[morphIndex + 1] = morphPositionsSparse[i * 3 + 1]\n morphPositions[morphIndex + 2] = morphPositionsSparse[i * 3 + 2]\n }\n\n // TODO: add morph normal support\n const morphGeoInfo = {\n vertexIndices: vertexIndices,\n vertexPositions: morphPositions,\n }\n\n const morphBuffers = this.genBuffers(morphGeoInfo)\n\n const positionAttribute = new Float32BufferAttribute(morphBuffers.vertex, 3)\n positionAttribute.name = name || morphGeoNode.attrName\n\n positionAttribute.applyMatrix4(preTransform)\n\n parentGeo.morphAttributes.position.push(positionAttribute)\n }\n\n // Parse normal from FBXTree.Objects.Geometry.LayerElementNormal if it exists\n parseNormals(NormalNode) {\n const mappingType = NormalNode.MappingInformationType\n const referenceType = NormalNode.ReferenceInformationType\n const buffer = NormalNode.Normals.a\n let indexBuffer = []\n if (referenceType === 'IndexToDirect') {\n if ('NormalIndex' in NormalNode) {\n indexBuffer = NormalNode.NormalIndex.a\n } else if ('NormalsIndex' in NormalNode) {\n indexBuffer = NormalNode.NormalsIndex.a\n }\n }\n\n return {\n dataSize: 3,\n buffer: buffer,\n indices: indexBuffer,\n mappingType: mappingType,\n referenceType: referenceType,\n }\n }\n\n // Parse UVs from FBXTree.Objects.Geometry.LayerElementUV if it exists\n parseUVs(UVNode) {\n const mappingType = UVNode.MappingInformationType\n const referenceType = UVNode.ReferenceInformationType\n const buffer = UVNode.UV.a\n let indexBuffer = []\n if (referenceType === 'IndexToDirect') {\n indexBuffer = UVNode.UVIndex.a\n }\n\n return {\n dataSize: 2,\n buffer: buffer,\n indices: indexBuffer,\n mappingType: mappingType,\n referenceType: referenceType,\n }\n }\n\n // Parse Vertex Colors from FBXTree.Objects.Geometry.LayerElementColor if it exists\n parseVertexColors(ColorNode) {\n const mappingType = ColorNode.MappingInformationType\n const referenceType = ColorNode.ReferenceInformationType\n const buffer = ColorNode.Colors.a\n let indexBuffer = []\n if (referenceType === 'IndexToDirect') {\n indexBuffer = ColorNode.ColorIndex.a\n }\n\n return {\n dataSize: 4,\n buffer: buffer,\n indices: indexBuffer,\n mappingType: mappingType,\n referenceType: referenceType,\n }\n }\n\n // Parse mapping and material data in FBXTree.Objects.Geometry.LayerElementMaterial if it exists\n parseMaterialIndices(MaterialNode) {\n const mappingType = MaterialNode.MappingInformationType\n const referenceType = MaterialNode.ReferenceInformationType\n\n if (mappingType === 'NoMappingInformation') {\n return {\n dataSize: 1,\n buffer: [0],\n indices: [0],\n mappingType: 'AllSame',\n referenceType: referenceType,\n }\n }\n\n const materialIndexBuffer = MaterialNode.Materials.a\n\n // Since materials are stored as indices, there's a bit of a mismatch between FBX and what\n // we expect.So we create an intermediate buffer that points to the index in the buffer,\n // for conforming with the other functions we've written for other data.\n const materialIndices = []\n\n for (let i = 0; i < materialIndexBuffer.length; ++i) {\n materialIndices.push(i)\n }\n\n return {\n dataSize: 1,\n buffer: materialIndexBuffer,\n indices: materialIndices,\n mappingType: mappingType,\n referenceType: referenceType,\n }\n }\n\n // Generate a NurbGeometry from a node in FBXTree.Objects.Geometry\n parseNurbsGeometry(geoNode) {\n if (NURBSCurve === undefined) {\n console.error(\n 'THREE.FBXLoader: The loader relies on NURBSCurve for any nurbs present in the model. Nurbs will show up as empty geometry.',\n )\n return new BufferGeometry()\n }\n\n const order = parseInt(geoNode.Order)\n\n if (isNaN(order)) {\n console.error('THREE.FBXLoader: Invalid Order %s given for geometry ID: %s', geoNode.Order, geoNode.id)\n return new BufferGeometry()\n }\n\n const degree = order - 1\n\n const knots = geoNode.KnotVector.a\n const controlPoints = []\n const pointsValues = geoNode.Points.a\n\n for (let i = 0, l = pointsValues.length; i < l; i += 4) {\n controlPoints.push(new Vector4().fromArray(pointsValues, i))\n }\n\n let startKnot, endKnot\n\n if (geoNode.Form === 'Closed') {\n controlPoints.push(controlPoints[0])\n } else if (geoNode.Form === 'Periodic') {\n startKnot = degree\n endKnot = knots.length - 1 - startKnot\n\n for (let i = 0; i < degree; ++i) {\n controlPoints.push(controlPoints[i])\n }\n }\n\n const curve = new NURBSCurve(degree, knots, controlPoints, startKnot, endKnot)\n const points = curve.getPoints(controlPoints.length * 12)\n\n return new BufferGeometry().setFromPoints(points)\n }\n}\n\n// parse animation data from FBXTree\nclass AnimationParser {\n // take raw animation clips and turn them into three.js animation clips\n parse() {\n const animationClips = []\n\n const rawClips = this.parseClips()\n\n if (rawClips !== undefined) {\n for (const key in rawClips) {\n const rawClip = rawClips[key]\n\n const clip = this.addClip(rawClip)\n\n animationClips.push(clip)\n }\n }\n\n return animationClips\n }\n\n parseClips() {\n // since the actual transformation data is stored in FBXTree.Objects.AnimationCurve,\n // if this is undefined we can safely assume there are no animations\n if (fbxTree.Objects.AnimationCurve === undefined) return undefined\n\n const curveNodesMap = this.parseAnimationCurveNodes()\n\n this.parseAnimationCurves(curveNodesMap)\n\n const layersMap = this.parseAnimationLayers(curveNodesMap)\n const rawClips = this.parseAnimStacks(layersMap)\n\n return rawClips\n }\n\n // parse nodes in FBXTree.Objects.AnimationCurveNode\n // each AnimationCurveNode holds data for an animation transform for a model (e.g. left arm rotation )\n // and is referenced by an AnimationLayer\n parseAnimationCurveNodes() {\n const rawCurveNodes = fbxTree.Objects.AnimationCurveNode\n\n const curveNodesMap = new Map()\n\n for (const nodeID in rawCurveNodes) {\n const rawCurveNode = rawCurveNodes[nodeID]\n\n if (rawCurveNode.attrName.match(/S|R|T|DeformPercent/) !== null) {\n const curveNode = {\n id: rawCurveNode.id,\n attr: rawCurveNode.attrName,\n curves: {},\n }\n\n curveNodesMap.set(curveNode.id, curveNode)\n }\n }\n\n return curveNodesMap\n }\n\n // parse nodes in FBXTree.Objects.AnimationCurve and connect them up to\n // previously parsed AnimationCurveNodes. Each AnimationCurve holds data for a single animated\n // axis ( e.g. times and values of x rotation)\n parseAnimationCurves(curveNodesMap) {\n const rawCurves = fbxTree.Objects.AnimationCurve\n\n // TODO: Many values are identical up to roundoff error, but won't be optimised\n // e.g. position times: [0, 0.4, 0. 8]\n // position values: [7.23538335023477e-7, 93.67518615722656, -0.9982695579528809, 7.23538335023477e-7, 93.67518615722656, -0.9982695579528809, 7.235384487103147e-7, 93.67520904541016, -0.9982695579528809]\n // clearly, this should be optimised to\n // times: [0], positions [7.23538335023477e-7, 93.67518615722656, -0.9982695579528809]\n // this shows up in nearly every FBX file, and generally time array is length > 100\n\n for (const nodeID in rawCurves) {\n const animationCurve = {\n id: rawCurves[nodeID].id,\n times: rawCurves[nodeID].KeyTime.a.map(convertFBXTimeToSeconds),\n values: rawCurves[nodeID].KeyValueFloat.a,\n }\n\n const relationships = connections.get(animationCurve.id)\n\n if (relationships !== undefined) {\n const animationCurveID = relationships.parents[0].ID\n const animationCurveRelationship = relationships.parents[0].relationship\n\n if (animationCurveRelationship.match(/X/)) {\n curveNodesMap.get(animationCurveID).curves['x'] = animationCurve\n } else if (animationCurveRelationship.match(/Y/)) {\n curveNodesMap.get(animationCurveID).curves['y'] = animationCurve\n } else if (animationCurveRelationship.match(/Z/)) {\n curveNodesMap.get(animationCurveID).curves['z'] = animationCurve\n } else if (animationCurveRelationship.match(/d|DeformPercent/) && curveNodesMap.has(animationCurveID)) {\n curveNodesMap.get(animationCurveID).curves['morph'] = animationCurve\n }\n }\n }\n }\n\n // parse nodes in FBXTree.Objects.AnimationLayer. Each layers holds references\n // to various AnimationCurveNodes and is referenced by an AnimationStack node\n // note: theoretically a stack can have multiple layers, however in practice there always seems to be one per stack\n parseAnimationLayers(curveNodesMap) {\n const rawLayers = fbxTree.Objects.AnimationLayer\n\n const layersMap = new Map()\n\n for (const nodeID in rawLayers) {\n const layerCurveNodes = []\n\n const connection = connections.get(parseInt(nodeID))\n\n if (connection !== undefined) {\n // all the animationCurveNodes used in the layer\n const children = connection.children\n\n children.forEach(function (child, i) {\n if (curveNodesMap.has(child.ID)) {\n const curveNode = curveNodesMap.get(child.ID)\n\n // check that the curves are defined for at least one axis, otherwise ignore the curveNode\n if (\n curveNode.curves.x !== undefined ||\n curveNode.curves.y !== undefined ||\n curveNode.curves.z !== undefined\n ) {\n if (layerCurveNodes[i] === undefined) {\n const modelID = connections.get(child.ID).parents.filter(function (parent) {\n return parent.relationship !== undefined\n })[0].ID\n\n if (modelID !== undefined) {\n const rawModel = fbxTree.Objects.Model[modelID.toString()]\n\n if (rawModel === undefined) {\n console.warn('THREE.FBXLoader: Encountered a unused curve.', child)\n return\n }\n\n const node = {\n modelName: rawModel.attrName ? PropertyBinding.sanitizeNodeName(rawModel.attrName) : '',\n ID: rawModel.id,\n initialPosition: [0, 0, 0],\n initialRotation: [0, 0, 0],\n initialScale: [1, 1, 1],\n }\n\n sceneGraph.traverse(function (child) {\n if (child.ID === rawModel.id) {\n node.transform = child.matrix\n\n if (child.userData.transformData) node.eulerOrder = child.userData.transformData.eulerOrder\n }\n })\n\n if (!node.transform) node.transform = new Matrix4()\n\n // if the animated model is pre rotated, we'll have to apply the pre rotations to every\n // animation value as well\n if ('PreRotation' in rawModel) node.preRotation = rawModel.PreRotation.value\n if ('PostRotation' in rawModel) node.postRotation = rawModel.PostRotation.value\n\n layerCurveNodes[i] = node\n }\n }\n\n if (layerCurveNodes[i]) layerCurveNodes[i][curveNode.attr] = curveNode\n } else if (curveNode.curves.morph !== undefined) {\n if (layerCurveNodes[i] === undefined) {\n const deformerID = connections.get(child.ID).parents.filter(function (parent) {\n return parent.relationship !== undefined\n })[0].ID\n\n const morpherID = connections.get(deformerID).parents[0].ID\n const geoID = connections.get(morpherID).parents[0].ID\n\n // assuming geometry is not used in more than one model\n const modelID = connections.get(geoID).parents[0].ID\n\n const rawModel = fbxTree.Objects.Model[modelID]\n\n const node = {\n modelName: rawModel.attrName ? PropertyBinding.sanitizeNodeName(rawModel.attrName) : '',\n morphName: fbxTree.Objects.Deformer[deformerID].attrName,\n }\n\n layerCurveNodes[i] = node\n }\n\n layerCurveNodes[i][curveNode.attr] = curveNode\n }\n }\n })\n\n layersMap.set(parseInt(nodeID), layerCurveNodes)\n }\n }\n\n return layersMap\n }\n\n // parse nodes in FBXTree.Objects.AnimationStack. These are the top level node in the animation\n // hierarchy. Each Stack node will be used to create a AnimationClip\n parseAnimStacks(layersMap) {\n const rawStacks = fbxTree.Objects.AnimationStack\n\n // connect the stacks (clips) up to the layers\n const rawClips = {}\n\n for (const nodeID in rawStacks) {\n const children = connections.get(parseInt(nodeID)).children\n\n if (children.length > 1) {\n // it seems like stacks will always be associated with a single layer. But just in case there are files\n // where there are multiple layers per stack, we'll display a warning\n console.warn(\n 'THREE.FBXLoader: Encountered an animation stack with multiple layers, this is currently not supported. Ignoring subsequent layers.',\n )\n }\n\n const layer = layersMap.get(children[0].ID)\n\n rawClips[nodeID] = {\n name: rawStacks[nodeID].attrName,\n layer: layer,\n }\n }\n\n return rawClips\n }\n\n addClip(rawClip) {\n let tracks = []\n\n const scope = this\n rawClip.layer.forEach(function (rawTracks) {\n tracks = tracks.concat(scope.generateTracks(rawTracks))\n })\n\n return new AnimationClip(rawClip.name, -1, tracks)\n }\n\n generateTracks(rawTracks) {\n const tracks = []\n\n let initialPosition = new Vector3()\n let initialRotation = new Quaternion()\n let initialScale = new Vector3()\n\n if (rawTracks.transform) rawTracks.transform.decompose(initialPosition, initialRotation, initialScale)\n\n initialPosition = initialPosition.toArray()\n initialRotation = new Euler().setFromQuaternion(initialRotation, rawTracks.eulerOrder).toArray()\n initialScale = initialScale.toArray()\n\n if (rawTracks.T !== undefined && Object.keys(rawTracks.T.curves).length > 0) {\n const positionTrack = this.generateVectorTrack(\n rawTracks.modelName,\n rawTracks.T.curves,\n initialPosition,\n 'position',\n )\n if (positionTrack !== undefined) tracks.push(positionTrack)\n }\n\n if (rawTracks.R !== undefined && Object.keys(rawTracks.R.curves).length > 0) {\n const rotationTrack = this.generateRotationTrack(\n rawTracks.modelName,\n rawTracks.R.curves,\n initialRotation,\n rawTracks.preRotation,\n rawTracks.postRotation,\n rawTracks.eulerOrder,\n )\n if (rotationTrack !== undefined) tracks.push(rotationTrack)\n }\n\n if (rawTracks.S !== undefined && Object.keys(rawTracks.S.curves).length > 0) {\n const scaleTrack = this.generateVectorTrack(rawTracks.modelName, rawTracks.S.curves, initialScale, 'scale')\n if (scaleTrack !== undefined) tracks.push(scaleTrack)\n }\n\n if (rawTracks.DeformPercent !== undefined) {\n const morphTrack = this.generateMorphTrack(rawTracks)\n if (morphTrack !== undefined) tracks.push(morphTrack)\n }\n\n return tracks\n }\n\n generateVectorTrack(modelName, curves, initialValue, type) {\n const times = this.getTimesForAllAxes(curves)\n const values = this.getKeyframeTrackValues(times, curves, initialValue)\n\n return new VectorKeyframeTrack(modelName + '.' + type, times, values)\n }\n\n generateRotationTrack(modelName, curves, initialValue, preRotation, postRotation, eulerOrder) {\n if (curves.x !== undefined) {\n this.interpolateRotations(curves.x)\n curves.x.values = curves.x.values.map(MathUtils.degToRad)\n }\n\n if (curves.y !== undefined) {\n this.interpolateRotations(curves.y)\n curves.y.values = curves.y.values.map(MathUtils.degToRad)\n }\n\n if (curves.z !== undefined) {\n this.interpolateRotations(curves.z)\n curves.z.values = curves.z.values.map(MathUtils.degToRad)\n }\n\n const times = this.getTimesForAllAxes(curves)\n const values = this.getKeyframeTrackValues(times, curves, initialValue)\n\n if (preRotation !== undefined) {\n preRotation = preRotation.map(MathUtils.degToRad)\n preRotation.push(eulerOrder)\n\n preRotation = new Euler().fromArray(preRotation)\n preRotation = new Quaternion().setFromEuler(preRotation)\n }\n\n if (postRotation !== undefined) {\n postRotation = postRotation.map(MathUtils.degToRad)\n postRotation.push(eulerOrder)\n\n postRotation = new Euler().fromArray(postRotation)\n postRotation = new Quaternion().setFromEuler(postRotation).invert()\n }\n\n const quaternion = new Quaternion()\n const euler = new Euler()\n\n const quaternionValues = []\n\n for (let i = 0; i < values.length; i += 3) {\n euler.set(values[i], values[i + 1], values[i + 2], eulerOrder)\n\n quaternion.setFromEuler(euler)\n\n if (preRotation !== undefined) quaternion.premultiply(preRotation)\n if (postRotation !== undefined) quaternion.multiply(postRotation)\n\n quaternion.toArray(quaternionValues, (i / 3) * 4)\n }\n\n return new QuaternionKeyframeTrack(modelName + '.quaternion', times, quaternionValues)\n }\n\n generateMorphTrack(rawTracks) {\n const curves = rawTracks.DeformPercent.curves.morph\n const values = curves.values.map(function (val) {\n return val / 100\n })\n\n const morphNum = sceneGraph.getObjectByName(rawTracks.modelName).morphTargetDictionary[rawTracks.morphName]\n\n return new NumberKeyframeTrack(\n rawTracks.modelName + '.morphTargetInfluences[' + morphNum + ']',\n curves.times,\n values,\n )\n }\n\n // For all animated objects, times are defined separately for each axis\n // Here we'll combine the times into one sorted array without duplicates\n getTimesForAllAxes(curves) {\n let times = []\n\n // first join together the times for each axis, if defined\n if (curves.x !== undefined) times = times.concat(curves.x.times)\n if (curves.y !== undefined) times = times.concat(curves.y.times)\n if (curves.z !== undefined) times = times.concat(curves.z.times)\n\n // then sort them\n times = times.sort(function (a, b) {\n return a - b\n })\n\n // and remove duplicates\n if (times.length > 1) {\n let targetIndex = 1\n let lastValue = times[0]\n for (let i = 1; i < times.length; i++) {\n const currentValue = times[i]\n if (currentValue !== lastValue) {\n times[targetIndex] = currentValue\n lastValue = currentValue\n targetIndex++\n }\n }\n\n times = times.slice(0, targetIndex)\n }\n\n return times\n }\n\n getKeyframeTrackValues(times, curves, initialValue) {\n const prevValue = initialValue\n\n const values = []\n\n let xIndex = -1\n let yIndex = -1\n let zIndex = -1\n\n times.forEach(function (time) {\n if (curves.x) xIndex = curves.x.times.indexOf(time)\n if (curves.y) yIndex = curves.y.times.indexOf(time)\n if (curves.z) zIndex = curves.z.times.indexOf(time)\n\n // if there is an x value defined for this frame, use that\n if (xIndex !== -1) {\n const xValue = curves.x.values[xIndex]\n values.push(xValue)\n prevValue[0] = xValue\n } else {\n // otherwise use the x value from the previous frame\n values.push(prevValue[0])\n }\n\n if (yIndex !== -1) {\n const yValue = curves.y.values[yIndex]\n values.push(yValue)\n prevValue[1] = yValue\n } else {\n values.push(prevValue[1])\n }\n\n if (zIndex !== -1) {\n const zValue = curves.z.values[zIndex]\n values.push(zValue)\n prevValue[2] = zValue\n } else {\n values.push(prevValue[2])\n }\n })\n\n return values\n }\n\n // Rotations are defined as Euler angles which can have values of any size\n // These will be converted to quaternions which don't support values greater than\n // PI, so we'll interpolate large rotations\n interpolateRotations(curve) {\n for (let i = 1; i < curve.values.length; i++) {\n const initialValue = curve.values[i - 1]\n const valuesSpan = curve.values[i] - initialValue\n\n const absoluteSpan = Math.abs(valuesSpan)\n\n if (absoluteSpan >= 180) {\n const numSubIntervals = absoluteSpan / 180\n\n const step = valuesSpan / numSubIntervals\n let nextValue = initialValue + step\n\n const initialTime = curve.times[i - 1]\n const timeSpan = curve.times[i] - initialTime\n const interval = timeSpan / numSubIntervals\n let nextTime = initialTime + interval\n\n const interpolatedTimes = []\n const interpolatedValues = []\n\n while (nextTime < curve.times[i]) {\n interpolatedTimes.push(nextTime)\n nextTime += interval\n\n interpolatedValues.push(nextValue)\n nextValue += step\n }\n\n curve.times = inject(curve.times, i, interpolatedTimes)\n curve.values = inject(curve.values, i, interpolatedValues)\n }\n }\n }\n}\n\n// parse an FBX file in ASCII format\nclass TextParser {\n getPrevNode() {\n return this.nodeStack[this.currentIndent - 2]\n }\n\n getCurrentNode() {\n return this.nodeStack[this.currentIndent - 1]\n }\n\n getCurrentProp() {\n return this.currentProp\n }\n\n pushStack(node) {\n this.nodeStack.push(node)\n this.currentIndent += 1\n }\n\n popStack() {\n this.nodeStack.pop()\n this.currentIndent -= 1\n }\n\n setCurrentProp(val, name) {\n this.currentProp = val\n this.currentPropName = name\n }\n\n parse(text) {\n this.currentIndent = 0\n\n this.allNodes = new FBXTree()\n this.nodeStack = []\n this.currentProp = []\n this.currentPropName = ''\n\n const scope = this\n\n const split = text.split(/[\\r\\n]+/)\n\n split.forEach(function (line, i) {\n const matchComment = line.match(/^[\\s\\t]*;/)\n const matchEmpty = line.match(/^[\\s\\t]*$/)\n\n if (matchComment || matchEmpty) return\n\n const matchBeginning = line.match('^\\\\t{' + scope.currentIndent + '}(\\\\w+):(.*){', '')\n const matchProperty = line.match('^\\\\t{' + scope.currentIndent + '}(\\\\w+):[\\\\s\\\\t\\\\r\\\\n](.*)')\n const matchEnd = line.match('^\\\\t{' + (scope.currentIndent - 1) + '}}')\n\n if (matchBeginning) {\n scope.parseNodeBegin(line, matchBeginning)\n } else if (matchProperty) {\n scope.parseNodeProperty(line, matchProperty, split[++i])\n } else if (matchEnd) {\n scope.popStack()\n } else if (line.match(/^[^\\s\\t}]/)) {\n // large arrays are split over multiple lines terminated with a ',' character\n // if this is encountered the line needs to be joined to the previous line\n scope.parseNodePropertyContinued(line)\n }\n })\n\n return this.allNodes\n }\n\n parseNodeBegin(line, property) {\n const nodeName = property[1].trim().replace(/^\"/, '').replace(/\"$/, '')\n\n const nodeAttrs = property[2].split(',').map(function (attr) {\n return attr.trim().replace(/^\"/, '').replace(/\"$/, '')\n })\n\n const node = { name: nodeName }\n const attrs = this.parseNodeAttr(nodeAttrs)\n\n const currentNode = this.getCurrentNode()\n\n // a top node\n if (this.currentIndent === 0) {\n this.allNodes.add(nodeName, node)\n } else {\n // a subnode\n\n // if the subnode already exists, append it\n if (nodeName in currentNode) {\n // special case Pose needs PoseNodes as an array\n if (nodeName === 'PoseNode') {\n currentNode.PoseNode.push(node)\n } else if (currentNode[nodeName].id !== undefined) {\n currentNode[nodeName] = {}\n currentNode[nodeName][currentNode[nodeName].id] = currentNode[nodeName]\n }\n\n if (attrs.id !== '') currentNode[nodeName][attrs.id] = node\n } else if (typeof attrs.id === 'number') {\n currentNode[nodeName] = {}\n currentNode[nodeName][attrs.id] = node\n } else if (nodeName !== 'Properties70') {\n if (nodeName === 'PoseNode') currentNode[nodeName] = [node]\n else currentNode[nodeName] = node\n }\n }\n\n if (typeof attrs.id === 'number') node.id = attrs.id\n if (attrs.name !== '') node.attrName = attrs.name\n if (attrs.type !== '') node.attrType = attrs.type\n\n this.pushStack(node)\n }\n\n parseNodeAttr(attrs) {\n let id = attrs[0]\n\n if (attrs[0] !== '') {\n id = parseInt(attrs[0])\n\n if (isNaN(id)) {\n id = attrs[0]\n }\n }\n\n let name = '',\n type = ''\n\n if (attrs.length > 1) {\n name = attrs[1].replace(/^(\\w+)::/, '')\n type = attrs[2]\n }\n\n return { id: id, name: name, type: type }\n }\n\n parseNodeProperty(line, property, contentLine) {\n let propName = property[1].replace(/^\"/, '').replace(/\"$/, '').trim()\n let propValue = property[2].replace(/^\"/, '').replace(/\"$/, '').trim()\n\n // for special case: base64 image data follows \"Content: ,\" line\n //\tContent: ,\n //\t \"/9j/4RDaRXhpZgAATU0A...\"\n if (propName === 'Content' && propValue === ',') {\n propValue = contentLine.replace(/\"/g, '').replace(/,$/, '').trim()\n }\n\n const currentNode = this.getCurrentNode()\n const parentName = currentNode.name\n\n if (parentName === 'Properties70') {\n this.parseNodeSpecialProperty(line, propName, propValue)\n return\n }\n\n // Connections\n if (propName === 'C') {\n const connProps = propValue.split(',').slice(1)\n const from = parseInt(connProps[0])\n const to = parseInt(connProps[1])\n\n let rest = propValue.split(',').slice(3)\n\n rest = rest.map(function (elem) {\n return elem.trim().replace(/^\"/, '')\n })\n\n propName = 'connections'\n propValue = [from, to]\n append(propValue, rest)\n\n if (currentNode[propName] === undefined) {\n currentNode[propName] = []\n }\n }\n\n // Node\n if (propName === 'Node') currentNode.id = propValue\n\n // connections\n if (propName in currentNode && Array.isArray(currentNode[propName])) {\n currentNode[propName].push(propValue)\n } else {\n if (propName !== 'a') currentNode[propName] = propValue\n else currentNode.a = propValue\n }\n\n this.setCurrentProp(currentNode, propName)\n\n // convert string to array, unless it ends in ',' in which case more will be added to it\n if (propName === 'a' && propValue.slice(-1) !== ',') {\n currentNode.a = parseNumberArray(propValue)\n }\n }\n\n parseNodePropertyContinued(line) {\n const currentNode = this.getCurrentNode()\n\n currentNode.a += line\n\n // if the line doesn't end in ',' we have reached the end of the property value\n // so convert the string to an array\n if (line.slice(-1) !== ',') {\n currentNode.a = parseNumberArray(currentNode.a)\n }\n }\n\n // parse \"Property70\"\n parseNodeSpecialProperty(line, propName, propValue) {\n // split this\n // P: \"Lcl Scaling\", \"Lcl Scaling\", \"\", \"A\",1,1,1\n // into array like below\n // [\"Lcl Scaling\", \"Lcl Scaling\", \"\", \"A\", \"1,1,1\" ]\n const props = propValue.split('\",').map(function (prop) {\n return prop.trim().replace(/^\\\"/, '').replace(/\\s/, '_')\n })\n\n const innerPropName = props[0]\n const innerPropType1 = props[1]\n const innerPropType2 = props[2]\n const innerPropFlag = props[3]\n let innerPropValue = props[4]\n\n // cast values where needed, otherwise leave as strings\n switch (innerPropType1) {\n case 'int':\n case 'enum':\n case 'bool':\n case 'ULongLong':\n case 'double':\n case 'Number':\n case 'FieldOfView':\n innerPropValue = parseFloat(innerPropValue)\n break\n\n case 'Color':\n case 'ColorRGB':\n case 'Vector3D':\n case 'Lcl_Translation':\n case 'Lcl_Rotation':\n case 'Lcl_Scaling':\n innerPropValue = parseNumberArray(innerPropValue)\n break\n }\n\n // CAUTION: these props must append to parent's parent\n this.getPrevNode()[innerPropName] = {\n type: innerPropType1,\n type2: innerPropType2,\n flag: innerPropFlag,\n value: innerPropValue,\n }\n\n this.setCurrentProp(this.getPrevNode(), innerPropName)\n }\n}\n\n// Parse an FBX file in Binary format\nclass BinaryParser {\n parse(buffer) {\n const reader = new BinaryReader(buffer)\n reader.skip(23) // skip magic 23 bytes\n\n const version = reader.getUint32()\n\n if (version < 6400) {\n throw new Error('THREE.FBXLoader: FBX version not supported, FileVersion: ' + version)\n }\n\n const allNodes = new FBXTree()\n\n while (!this.endOfContent(reader)) {\n const node = this.parseNode(reader, version)\n if (node !== null) allNodes.add(node.name, node)\n }\n\n return allNodes\n }\n\n // Check if reader has reached the end of content.\n endOfContent(reader) {\n // footer size: 160bytes + 16-byte alignment padding\n // - 16bytes: magic\n // - padding til 16-byte alignment (at least 1byte?)\n //\t(seems like some exporters embed fixed 15 or 16bytes?)\n // - 4bytes: magic\n // - 4bytes: version\n // - 120bytes: zero\n // - 16bytes: magic\n if (reader.size() % 16 === 0) {\n return ((reader.getOffset() + 160 + 16) & ~0xf) >= reader.size()\n } else {\n return reader.getOffset() + 160 + 16 >= reader.size()\n }\n }\n\n // recursively parse nodes until the end of the file is reached\n parseNode(reader, version) {\n const node = {}\n\n // The first three data sizes depends on version.\n const endOffset = version >= 7500 ? reader.getUint64() : reader.getUint32()\n const numProperties = version >= 7500 ? reader.getUint64() : reader.getUint32()\n\n version >= 7500 ? reader.getUint64() : reader.getUint32() // the returned propertyListLen is not used\n\n const nameLen = reader.getUint8()\n const name = reader.getString(nameLen)\n\n // Regards this node as NULL-record if endOffset is zero\n if (endOffset === 0) return null\n\n const propertyList = []\n\n for (let i = 0; i < numProperties; i++) {\n propertyList.push(this.parseProperty(reader))\n }\n\n // Regards the first three elements in propertyList as id, attrName, and attrType\n const id = propertyList.length > 0 ? propertyList[0] : ''\n const attrName = propertyList.length > 1 ? propertyList[1] : ''\n const attrType = propertyList.length > 2 ? propertyList[2] : ''\n\n // check if this node represents just a single property\n // like (name, 0) set or (name2, [0, 1, 2]) set of {name: 0, name2: [0, 1, 2]}\n node.singleProperty = numProperties === 1 && reader.getOffset() === endOffset ? true : false\n\n while (endOffset > reader.getOffset()) {\n const subNode = this.parseNode(reader, version)\n\n if (subNode !== null) this.parseSubNode(name, node, subNode)\n }\n\n node.propertyList = propertyList // raw property list used by parent\n\n if (typeof id === 'number') node.id = id\n if (attrName !== '') node.attrName = attrName\n if (attrType !== '') node.attrType = attrType\n if (name !== '') node.name = name\n\n return node\n }\n\n parseSubNode(name, node, subNode) {\n // special case: child node is single property\n if (subNode.singleProperty === true) {\n const value = subNode.propertyList[0]\n\n if (Array.isArray(value)) {\n node[subNode.name] = subNode\n\n subNode.a = value\n } else {\n node[subNode.name] = value\n }\n } else if (name === 'Connections' && subNode.name === 'C') {\n const array = []\n\n subNode.propertyList.forEach(function (property, i) {\n // first Connection is FBX type (OO, OP, etc.). We'll discard these\n if (i !== 0) array.push(property)\n })\n\n if (node.connections === undefined) {\n node.connections = []\n }\n\n node.connections.push(array)\n } else if (subNode.name === 'Properties70') {\n const keys = Object.keys(subNode)\n\n keys.forEach(function (key) {\n node[key] = subNode[key]\n })\n } else if (name === 'Properties70' && subNode.name === 'P') {\n let innerPropName = subNode.propertyList[0]\n let innerPropType1 = subNode.propertyList[1]\n const innerPropType2 = subNode.propertyList[2]\n const innerPropFlag = subNode.propertyList[3]\n let innerPropValue\n\n if (innerPropName.indexOf('Lcl ') === 0) innerPropName = innerPropName.replace('Lcl ', 'Lcl_')\n if (innerPropType1.indexOf('Lcl ') === 0) innerPropType1 = innerPropType1.replace('Lcl ', 'Lcl_')\n\n if (\n innerPropType1 === 'Color' ||\n innerPropType1 === 'ColorRGB' ||\n innerPropType1 === 'Vector' ||\n innerPropType1 === 'Vector3D' ||\n innerPropType1.indexOf('Lcl_') === 0\n ) {\n innerPropValue = [subNode.propertyList[4], subNode.propertyList[5], subNode.propertyList[6]]\n } else {\n innerPropValue = subNode.propertyList[4]\n }\n\n // this will be copied to parent, see above\n node[innerPropName] = {\n type: innerPropType1,\n type2: innerPropType2,\n flag: innerPropFlag,\n value: innerPropValue,\n }\n } else if (node[subNode.name] === undefined) {\n if (typeof subNode.id === 'number') {\n node[subNode.name] = {}\n node[subNode.name][subNode.id] = subNode\n } else {\n node[subNode.name] = subNode\n }\n } else {\n if (subNode.name === 'PoseNode') {\n if (!Array.isArray(node[subNode.name])) {\n node[subNode.name] = [node[subNode.name]]\n }\n\n node[subNode.name].push(subNode)\n } else if (node[subNode.name][subNode.id] === undefined) {\n node[subNode.name][subNode.id] = subNode\n }\n }\n }\n\n parseProperty(reader) {\n const type = reader.getString(1)\n let length\n\n switch (type) {\n case 'C':\n return reader.getBoolean()\n\n case 'D':\n return reader.getFloat64()\n\n case 'F':\n return reader.getFloat32()\n\n case 'I':\n return reader.getInt32()\n\n case 'L':\n return reader.getInt64()\n\n case 'R':\n length = reader.getUint32()\n return reader.getArrayBuffer(length)\n\n case 'S':\n length = reader.getUint32()\n return reader.getString(length)\n\n case 'Y':\n return reader.getInt16()\n\n case 'b':\n case 'c':\n case 'd':\n case 'f':\n case 'i':\n case 'l':\n const arrayLength = reader.getUint32()\n const encoding = reader.getUint32() // 0: non-compressed, 1: compressed\n const compressedLength = reader.getUint32()\n\n if (encoding === 0) {\n switch (type) {\n case 'b':\n case 'c':\n return reader.getBooleanArray(arrayLength)\n\n case 'd':\n return reader.getFloat64Array(arrayLength)\n\n case 'f':\n return reader.getFloat32Array(arrayLength)\n\n case 'i':\n return reader.getInt32Array(arrayLength)\n\n case 'l':\n return reader.getInt64Array(arrayLength)\n }\n }\n\n const data = unzlibSync(new Uint8Array(reader.getArrayBuffer(compressedLength)))\n const reader2 = new BinaryReader(data.buffer)\n\n switch (type) {\n case 'b':\n case 'c':\n return reader2.getBooleanArray(arrayLength)\n\n case 'd':\n return reader2.getFloat64Array(arrayLength)\n\n case 'f':\n return reader2.getFloat32Array(arrayLength)\n\n case 'i':\n return reader2.getInt32Array(arrayLength)\n\n case 'l':\n return reader2.getInt64Array(arrayLength)\n }\n\n default:\n throw new Error('THREE.FBXLoader: Unknown property type ' + type)\n }\n }\n}\n\nclass BinaryReader {\n constructor(buffer, littleEndian) {\n this.dv = new DataView(buffer)\n this.offset = 0\n this.littleEndian = littleEndian !== undefined ? littleEndian : true\n }\n\n getOffset() {\n return this.offset\n }\n\n size() {\n return this.dv.buffer.byteLength\n }\n\n skip(length) {\n this.offset += length\n }\n\n // seems like true/false representation depends on exporter.\n // true: 1 or 'Y'(=0x59), false: 0 or 'T'(=0x54)\n // then sees LSB.\n getBoolean() {\n return (this.getUint8() & 1) === 1\n }\n\n getBooleanArray(size) {\n const a = []\n\n for (let i = 0; i < size; i++) {\n a.push(this.getBoolean())\n }\n\n return a\n }\n\n getUint8() {\n const value = this.dv.getUint8(this.offset)\n this.offset += 1\n return value\n }\n\n getInt16() {\n const value = this.dv.getInt16(this.offset, this.littleEndian)\n this.offset += 2\n return value\n }\n\n getInt32() {\n const value = this.dv.getInt32(this.offset, this.littleEndian)\n this.offset += 4\n return value\n }\n\n getInt32Array(size) {\n const a = []\n\n for (let i = 0; i < size; i++) {\n a.push(this.getInt32())\n }\n\n return a\n }\n\n getUint32() {\n const value = this.dv.getUint32(this.offset, this.littleEndian)\n this.offset += 4\n return value\n }\n\n // JavaScript doesn't support 64-bit integer so calculate this here\n // 1 << 32 will return 1 so using multiply operation instead here.\n // There's a possibility that this method returns wrong value if the value\n // is out of the range between Number.MAX_SAFE_INTEGER and Number.MIN_SAFE_INTEGER.\n // TODO: safely handle 64-bit integer\n getInt64() {\n let low, high\n\n if (this.littleEndian) {\n low = this.getUint32()\n high = this.getUint32()\n } else {\n high = this.getUint32()\n low = this.getUint32()\n }\n\n // calculate negative value\n if (high & 0x80000000) {\n high = ~high & 0xffffffff\n low = ~low & 0xffffffff\n\n if (low === 0xffffffff) high = (high + 1) & 0xffffffff\n\n low = (low + 1) & 0xffffffff\n\n return -(high * 0x100000000 + low)\n }\n\n return high * 0x100000000 + low\n }\n\n getInt64Array(size) {\n const a = []\n\n for (let i = 0; i < size; i++) {\n a.push(this.getInt64())\n }\n\n return a\n }\n\n // Note: see getInt64() comment\n getUint64() {\n let low, high\n\n if (this.littleEndian) {\n low = this.getUint32()\n high = this.getUint32()\n } else {\n high = this.getUint32()\n low = this.getUint32()\n }\n\n return high * 0x100000000 + low\n }\n\n getFloat32() {\n const value = this.dv.getFloat32(this.offset, this.littleEndian)\n this.offset += 4\n return value\n }\n\n getFloat32Array(size) {\n const a = []\n\n for (let i = 0; i < size; i++) {\n a.push(this.getFloat32())\n }\n\n return a\n }\n\n getFloat64() {\n const value = this.dv.getFloat64(this.offset, this.littleEndian)\n this.offset += 8\n return value\n }\n\n getFloat64Array(size) {\n const a = []\n\n for (let i = 0; i < size; i++) {\n a.push(this.getFloat64())\n }\n\n return a\n }\n\n getArrayBuffer(size) {\n const value = this.dv.buffer.slice(this.offset, this.offset + size)\n this.offset += size\n return value\n }\n\n getString(size) {\n // note: safari 9 doesn't support Uint8Array.indexOf; create intermediate array instead\n let a = []\n\n for (let i = 0; i < size; i++) {\n a[i] = this.getUint8()\n }\n\n const nullByte = a.indexOf(0)\n if (nullByte >= 0) a = a.slice(0, nullByte)\n\n return decodeText(new Uint8Array(a))\n }\n}\n\n// FBXTree holds a representation of the FBX data, returned by the TextParser ( FBX ASCII format)\n// and BinaryParser( FBX Binary format)\nclass FBXTree {\n add(key, val) {\n this[key] = val\n }\n}\n\n// ************** UTILITY FUNCTIONS **************\n\nfunction isFbxFormatBinary(buffer) {\n const CORRECT = 'Kaydara\\u0020FBX\\u0020Binary\\u0020\\u0020\\0'\n\n return buffer.byteLength >= CORRECT.length && CORRECT === convertArrayBufferToString(buffer, 0, CORRECT.length)\n}\n\nfunction isFbxFormatASCII(text) {\n const CORRECT = [\n 'K',\n 'a',\n 'y',\n 'd',\n 'a',\n 'r',\n 'a',\n '\\\\',\n 'F',\n 'B',\n 'X',\n '\\\\',\n 'B',\n 'i',\n 'n',\n 'a',\n 'r',\n 'y',\n '\\\\',\n '\\\\',\n ]\n\n let cursor = 0\n\n function read(offset) {\n const result = text[offset - 1]\n text = text.slice(cursor + offset)\n cursor++\n return result\n }\n\n for (let i = 0; i < CORRECT.length; ++i) {\n const num = read(1)\n if (num === CORRECT[i]) {\n return false\n }\n }\n\n return true\n}\n\nfunction getFbxVersion(text) {\n const versionRegExp = /FBXVersion: (\\d+)/\n const match = text.match(versionRegExp)\n\n if (match) {\n const version = parseInt(match[1])\n return version\n }\n\n throw new Error('THREE.FBXLoader: Cannot find the version number for the file given.')\n}\n\n// Converts FBX ticks into real time seconds.\nfunction convertFBXTimeToSeconds(time) {\n return time / 46186158000\n}\n\nconst dataArray = []\n\n// extracts the data from the correct position in the FBX array based on indexing type\nfunction getData(polygonVertexIndex, polygonIndex, vertexIndex, infoObject) {\n let index\n\n switch (infoObject.mappingType) {\n case 'ByPolygonVertex':\n index = polygonVertexIndex\n break\n case 'ByPolygon':\n index = polygonIndex\n break\n case 'ByVertice':\n index = vertexIndex\n break\n case 'AllSame':\n index = infoObject.indices[0]\n break\n default:\n console.warn('THREE.FBXLoader: unknown attribute mapping type ' + infoObject.mappingType)\n }\n\n if (infoObject.referenceType === 'IndexToDirect') index = infoObject.indices[index]\n\n const from = index * infoObject.dataSize\n const to = from + infoObject.dataSize\n\n return slice(dataArray, infoObject.buffer, from, to)\n}\n\nconst tempEuler = new Euler()\nconst tempVec = new Vector3()\n\n// generate transformation from FBX transform data\n// ref: https://help.autodesk.com/view/FBX/2017/ENU/?guid=__files_GUID_10CDD63C_79C1_4F2D_BB28_AD2BE65A02ED_htm\n// ref: http://docs.autodesk.com/FBX/2014/ENU/FBX-SDK-Documentation/index.html?url=cpp_ref/_transformations_2main_8cxx-example.html,topicNumber=cpp_ref__transformations_2main_8cxx_example_htmlfc10a1e1-b18d-4e72-9dc0-70d0f1959f5e\nfunction generateTransform(transformData) {\n const lTranslationM = new Matrix4()\n const lPreRotationM = new Matrix4()\n const lRotationM = new Matrix4()\n const lPostRotationM = new Matrix4()\n\n const lScalingM = new Matrix4()\n const lScalingPivotM = new Matrix4()\n const lScalingOffsetM = new Matrix4()\n const lRotationOffsetM = new Matrix4()\n const lRotationPivotM = new Matrix4()\n\n const lParentGX = new Matrix4()\n const lParentLX = new Matrix4()\n const lGlobalT = new Matrix4()\n\n const inheritType = transformData.inheritType ? transformData.inheritType : 0\n\n if (transformData.translation) lTranslationM.setPosition(tempVec.fromArray(transformData.translation))\n\n if (transformData.preRotation) {\n const array = transformData.preRotation.map(MathUtils.degToRad)\n array.push(transformData.eulerOrder)\n lPreRotationM.makeRotationFromEuler(tempEuler.fromArray(array))\n }\n\n if (transformData.rotation) {\n const array = transformData.rotation.map(MathUtils.degToRad)\n array.push(transformData.eulerOrder)\n lRotationM.makeRotationFromEuler(tempEuler.fromArray(array))\n }\n\n if (transformData.postRotation) {\n const array = transformData.postRotation.map(MathUtils.degToRad)\n array.push(transformData.eulerOrder)\n lPostRotationM.makeRotationFromEuler(tempEuler.fromArray(array))\n lPostRotationM.invert()\n }\n\n if (transformData.scale) lScalingM.scale(tempVec.fromArray(transformData.scale))\n\n // Pivots and offsets\n if (transformData.scalingOffset) lScalingOffsetM.setPosition(tempVec.fromArray(transformData.scalingOffset))\n if (transformData.scalingPivot) lScalingPivotM.setPosition(tempVec.fromArray(transformData.scalingPivot))\n if (transformData.rotationOffset) lRotationOffsetM.setPosition(tempVec.fromArray(transformData.rotationOffset))\n if (transformData.rotationPivot) lRotationPivotM.setPosition(tempVec.fromArray(transformData.rotationPivot))\n\n // parent transform\n if (transformData.parentMatrixWorld) {\n lParentLX.copy(transformData.parentMatrix)\n lParentGX.copy(transformData.parentMatrixWorld)\n }\n\n const lLRM = lPreRotationM.clone().multiply(lRotationM).multiply(lPostRotationM)\n // Global Rotation\n const lParentGRM = new Matrix4()\n lParentGRM.extractRotation(lParentGX)\n\n // Global Shear*Scaling\n const lParentTM = new Matrix4()\n lParentTM.copyPosition(lParentGX)\n\n const lParentGRSM = lParentTM.clone().invert().multiply(lParentGX)\n const lParentGSM = lParentGRM.clone().invert().multiply(lParentGRSM)\n const lLSM = lScalingM\n\n const lGlobalRS = new Matrix4()\n\n if (inheritType === 0) {\n lGlobalRS.copy(lParentGRM).multiply(lLRM).multiply(lParentGSM).multiply(lLSM)\n } else if (inheritType === 1) {\n lGlobalRS.copy(lParentGRM).multiply(lParentGSM).multiply(lLRM).multiply(lLSM)\n } else {\n const lParentLSM = new Matrix4().scale(new Vector3().setFromMatrixScale(lParentLX))\n const lParentLSM_inv = lParentLSM.clone().invert()\n const lParentGSM_noLocal = lParentGSM.clone().multiply(lParentLSM_inv)\n\n lGlobalRS.copy(lParentGRM).multiply(lLRM).multiply(lParentGSM_noLocal).multiply(lLSM)\n }\n\n const lRotationPivotM_inv = lRotationPivotM.clone().invert()\n const lScalingPivotM_inv = lScalingPivotM.clone().invert()\n // Calculate the local transform matrix\n let lTransform = lTranslationM\n .clone()\n .multiply(lRotationOffsetM)\n .multiply(lRotationPivotM)\n .multiply(lPreRotationM)\n .multiply(lRotationM)\n .multiply(lPostRotationM)\n .multiply(lRotationPivotM_inv)\n .multiply(lScalingOffsetM)\n .multiply(lScalingPivotM)\n .multiply(lScalingM)\n .multiply(lScalingPivotM_inv)\n\n const lLocalTWithAllPivotAndOffsetInfo = new Matrix4().copyPosition(lTransform)\n\n const lGlobalTranslation = lParentGX.clone().multiply(lLocalTWithAllPivotAndOffsetInfo)\n lGlobalT.copyPosition(lGlobalTranslation)\n\n lTransform = lGlobalT.clone().multiply(lGlobalRS)\n\n // from global to local\n lTransform.premultiply(lParentGX.invert())\n\n return lTransform\n}\n\n// Returns the three.js intrinsic Euler order corresponding to FBX extrinsic Euler order\n// ref: http://help.autodesk.com/view/FBX/2017/ENU/?guid=__cpp_ref_class_fbx_euler_html\nfunction getEulerOrder(order) {\n order = order || 0\n\n const enums = [\n 'ZYX', // -> XYZ extrinsic\n 'YZX', // -> XZY extrinsic\n 'XZY', // -> YZX extrinsic\n 'ZXY', // -> YXZ extrinsic\n 'YXZ', // -> ZXY extrinsic\n 'XYZ', // -> ZYX extrinsic\n //'SphericXYZ', // not possible to support\n ]\n\n if (order === 6) {\n console.warn('THREE.FBXLoader: unsupported Euler Order: Spherical XYZ. Animations and rotations may be incorrect.')\n return enums[0]\n }\n\n return enums[order]\n}\n\n// Parses comma separated list of numbers and returns them an array.\n// Used internally by the TextParser\nfunction parseNumberArray(value) {\n const array = value.split(',').map(function (val) {\n return parseFloat(val)\n })\n\n return array\n}\n\nfunction convertArrayBufferToString(buffer, from, to) {\n if (from === undefined) from = 0\n if (to === undefined) to = buffer.byteLength\n\n return decodeText(new Uint8Array(buffer, from, to))\n}\n\nfunction append(a, b) {\n for (let i = 0, j = a.length, l = b.length; i < l; i++, j++) {\n a[j] = b[i]\n }\n}\n\nfunction slice(a, b, from, to) {\n for (let i = from, j = 0; i < to; i++, j++) {\n a[j] = b[i]\n }\n\n return a\n}\n\n// inject array a2 into array a1 at index\nfunction inject(a1, index, a2) {\n return a1.slice(0, index).concat(a2).concat(a1.slice(index))\n}\n\nexport { FBXLoader }\n"],"names":["child","material","skeleton"],"mappings":"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"}
|