three-meshlet is a Three.js meshlet library for GLTF and GLB assets. It loads source models, builds meshlets, and generates multi-LOD data you can use in a custom renderer or content pipeline.
The package is focused on mesh optimization for real-time rendering: triangle reduction by LOD, meshlet clustering, and compact payloads for large scenes. If you are working on WebGPU rendering, threejs performance tuning, or Nanite-style experiments, this gives you reusable preprocessing logic instead of one-off scripts.
This repository contains two parts: the reusable library in src/ and a separate WebGPU demo app in demo/. Use the library in production code, and use the demo to inspect rendering behavior with the same model workflow.
- A reusable three meshlet API for browser-based model processing.
- GLTFLoader setup with Draco and meshopt support.
- Meshlet payload generation with multiple LOD levels.
- Utilities to merge meshlet assets and build vertex/material textures.
Try in-browser demo at: https://seanhlewis.github.io/three-meshlet-demo/
git clone https://github.com/seanhlewis/three-meshlet.git
cd three-meshletnpm install three
npm install github:seanhlewis/three-meshletFor local development against your clone:
npm install /absolute/path/to/three-meshlet- Load one or more models (
.gltfor.glb). - Build meshlet + LOD payloads.
- Send that data into your renderer or export step.
import {
buildThreeMeshletAssetFromUrls,
getThreeMeshletDracoDecoderPath
} from 'three-meshlet';
const { sources, meshlets } = await buildThreeMeshletAssetFromUrls(
[
{ name: 'DamagedHelmet', url: '/models/DamagedHelmet.gltf' },
{ name: 'CoffeeMug', url: '/models/coffeeMug.glb' }
],
{
loaderOptions: {
dracoDecoderPath: getThreeMeshletDracoDecoderPath()
},
onProgress: (message, progress) => {
console.log(message, Math.round(progress * 100) + '%');
}
}
);
console.log(sources.length, meshlets.totalChunks);import { buildThreeMeshletAssetFromArrayBuffers } from 'three-meshlet';
const entry = {
name: 'UploadedModel',
buffer: await file.arrayBuffer()
};
const { meshlets } = await buildThreeMeshletAssetFromArrayBuffers([entry]);
console.log(meshlets.meshletTopologyStats);meshlets includes data commonly needed for a meshlet renderer:
lods: per-LOD ranges and error values.meshletData: packed meshlet metadata.meshletStreamDataandmeshletDecodeData: compressed meshlet decode payloads.chunkBoundsData: bounds used for culling.totalChunksandmaxMeshletsPerLod: sizing information for runtime buffers.
createThreeMeshletGLTFLoader(options?)loadSourceModelFromUrl(options)loadSourceModelFromArrayBuffer(options)loadSourceModelsFromUrls(entries, options?)assignSourceMaterialIds(sources)buildThreeMeshletAsset(sources, options?)buildThreeMeshletAssetFromUrls(entries, options?)buildThreeMeshletAssetFromArrayBuffers(entries, options?)mergeMeshletAssets(base, next, vertexBase)buildVertexGeometry(sources)getThreeMeshletDracoDecoderPath()getThreeMeshletDemoUrl(path?)
From the repository root:
npm run demoOpen:
If port 8787 is in use:
$env:PORT='8790'; npm run demoCredit: Nanite-style renderer for threejs by @sea3dformat.