fbx-test

The status of loading and viewing FBX models using different WebGL libraries.

Samples

FBX Models

Test environment: Windows 11 + Chrome 147

Legend:

Model Three.js r184 Babylon.js custom loader Notes
Samba Dancing :white_check_mark: Sample :white_check_mark: Sample Skinned animation model.
morph_test :white_check_mark: Sample :white_check_mark: Sample Morph targets. Adjust influence in the Morphs folder of the GUI.
monkey :white_check_mark: Sample :white_check_mark: Sample Static mesh.
monkey_embedded_texture :white_check_mark: Sample :white_check_mark: Sample Embedded texture.
vCube :white_check_mark: Sample :white_check_mark: Sample Static mesh.
archer/ArcherRi01 :white_check_mark: Sample :white_check_mark: Sample Static mesh with geometric transform.
warrior/Warrior :white_check_mark: Sample :warning: Sample Skinned animation model. ByVertice UV/normal mapping fix applied.
stanford-bunny :white_check_mark: Sample :white_check_mark: Sample Large static mesh (ASCII FBX format).
mixamo :white_check_mark: Sample :white_check_mark: Sample Skinned animation model.
RotationTest :white_check_mark: Sample :warning: Sample Rotation-order coverage is still being verified.
exampleWindow :white_check_mark: Sample :white_check_mark: Sample Static mesh.
Head_69 :white_check_mark: Sample :white_check_mark: Sample Static mesh with multi-material support.
morph-translation :white_check_mark: Sample :white_check_mark: Sample Morph targets (8 meshes). Adjust influence in the Morphs folder of the GUI.

fbx-loader.js Usage

A standalone binary and ASCII FBX parser and Babylon.js mesh builder. No build step or npm install required — just include it as a <script> tag.

Installation

<script src="example/babylonjs/fbx-loader.js"></script>

API

FBXLoader.loadFBX(url, scene, options) — Load from URL

const nodes = await FBXLoader.loadFBX(url, scene, options);
Parameter Type Description
url string URL of the .fbx file to load
scene BABYLON.Scene Target Babylon.js scene
options object Optional settings (see below)

Returns: Promise<BABYLON.Node[]> — all created nodes (meshes and transform nodes).

FBXLoader.loadFBXFromBuffer(buffer, baseDir, scene, options) — Load from ArrayBuffer

const nodes = await FBXLoader.loadFBXFromBuffer(buffer, baseDir, scene, options);
Parameter Type Description
buffer ArrayBuffer Raw FBX file data
baseDir string Base URL for resolving relative texture paths (e.g. "assets/models/")
scene BABYLON.Scene Target Babylon.js scene
options object Optional settings (see below)

Options

Option Type Default Description
animation boolean true Start animation playback automatically
animationTime number 0 Initial animation time in seconds

Babylon.js Scene Loader Plugin

fbx-loader.js automatically registers itself as a Babylon.js Scene Loader Plugin when included, enabling the standard scene loader API for .fbx files.

// Babylon.js v9+: pass a single full URL
const result = await BABYLON.ImportMeshAsync('https://example.com/assets/model.fbx', scene);
console.log(result.meshes);      // BABYLON.Mesh[]
console.log(result.skeletons);   // BABYLON.Skeleton[]

// Load into an AssetContainer (can be added/removed from scene later)
const container = await BABYLON.LoadAssetContainerAsync('https://example.com/assets/model.fbx', scene);
container.addAllToScene();

Loader options can be passed via pluginOptions:

const result = await BABYLON.ImportMeshAsync('https://example.com/assets/model.fbx', scene, {
    pluginOptions: { fbx: { animation: false, animationTime: 2.0 } },
});

To register manually, use FBXLoader.createPlugin():

BABYLON.RegisterSceneLoaderPlugin({
    name: 'fbx',
    extensions: '.fbx',
    createPlugin: (opts) => FBXLoader.createPlugin(opts?.fbx ?? {}),
});

Babylon.js v8 and earlier

For Babylon.js v8 and earlier, use the SceneLoader class methods with a split rootUrl + fileName:

const result = await BABYLON.SceneLoader.ImportMeshAsync('', 'https://example.com/assets/', 'model.fbx', scene);

Animation Control

When a skinned animation is present, the root node’s metadata.fbxAnimationControls contains an array of animation control objects.

const nodes = await FBXLoader.loadFBX(url, scene);

// Find the root node (__root__)
const root = nodes.find(n => n.name === '__root__');
const controls = root?.metadata?.fbxAnimationControls ?? [];

// Each control exposes:
const ctrl = controls[0];
ctrl.name;              // animation stack name (string)
ctrl.duration;          // total duration in seconds (number)
ctrl.time;              // current playback time (number)
ctrl.playing;           // true if playing (boolean)
ctrl.setTime(t);        // seek to time t (seconds)
ctrl.setPlaying(bool);  // play or pause
ctrl.dispose();         // clean up observer when done

The root node’s metadata.fbxSkeletons contains an array of BABYLON.Skeleton objects for the loaded model.

Basic Example

<!DOCTYPE html>
<html>
<head>
  <script src="https://cdn.babylonjs.com/babylon.js"></script>
  <script src="fbx-loader.js"></script>
</head>
<body>
  <canvas id="c" style="width:100%;height:100vh"></canvas>
  <script>
    const canvas = document.getElementById('c');
    const engine = new BABYLON.Engine(canvas, true);
    const scene = new BABYLON.Scene(engine);

    const camera = new BABYLON.ArcRotateCamera('cam', -Math.PI / 2, Math.PI / 2.5, 5, BABYLON.Vector3.Zero(), scene);
    camera.attachControl(canvas, true);
    new BABYLON.HemisphericLight('light', new BABYLON.Vector3(0, 1, 0), scene);

    // Direct load via FBXLoader.loadFBX
    FBXLoader.loadFBX('model.fbx', scene, { animation: true }).then(nodes => {
        console.log('Loaded nodes:', nodes.length);
    });

    // Or via the Scene Loader Plugin (auto-registered when fbx-loader.js is included)
    // await BABYLON.ImportMeshAsync('https://example.com/model.fbx', scene);  // v9+
    // await BABYLON.SceneLoader.ImportMeshAsync('', '', 'model.fbx', scene);  // v8

    engine.runRenderLoop(() => scene.render());
    window.addEventListener('resize', () => engine.resize());
  </script>
</body>
</html>

URL Query Parameters (example viewer)

The example viewer also accepts these query parameters:

Parameter Example Description
model ?model=monkey Select a bundled model by name
url ?url=https://…/model.fbx Load an arbitrary FBX URL
scale ?scale=0.01 Override the model scale
animation ?animation=0 Disable auto-play (0 / false / off)
time ?time=1.5 Set the initial animation time (seconds)

Current Babylon.js Loader Scope

The Babylon.js sample uses a custom FBX parser supporting both binary and ASCII formats. It currently focuses on static mesh loading, transform hierarchy validation, basic skinning data, and sampled skeleton animation.

Supported or partially supported: