Product configurators, data visualizations, browser games and WebXR experiences all run on ordinary web pages now, and Three.js is behind a lot of them. It’s a JavaScript 3D graphics library that renders interactive scenes in the browser through a scene-graph API on top of WebGL and WebGPU. Developers arrange cameras, meshes, materials and lights, and the library issues the GPU calls.

The renderer draws each frame to an HTML canvas, so none of it needs a plugin.

For a sense of scale, the npm registry’s own download API recorded 20,521,334 downloads of the library’s package, named three, between October 3 and October 9, 2026 (npm, 2026).

What Is Three.js?

Mostly, it saves you from writing GPU code. You describe a scene with cameras, meshes, materials and lights, and Three.js turns that description into draw calls. Nobody has to write vertex buffers or shader plumbing by hand.

Because it’s plain JavaScript, a scene runs on a normal page with no browser plugin. It’s a library and not a framework, so it has no opinion about how the rest of your app gets built. It also sits above WebGL and WebGPU instead of replacing either one. What comes out is a frame drawn to an HTML canvas, redrawn on every animation tick.

The project README keeps the goal modest: a lightweight 3D library for general use that’s easy to pick up and works across browsers.

Who Created Three.js and What License Does It Use?

Ricardo Cabello, who goes by mrdoob, first released Three.js on GitHub in April 2010 (Wikipedia). It ships under the MIT License, which allows commercial use, modification and redistribution. The only condition is keeping the copyright and license notice with the code.

The code actually started life in ActionScript for Adobe Flash and moved to JavaScript in 2009. Cabello’s reasons, per Wikipedia’s history section, were platform independence and no compile step.

Early contributor Paul Brunt added the first WebGL renderer with little friction, since the rendering code lived in a module instead of the core. That same modular design is why SVG, CSS3D and WebGPU renderers sit next to the WebGL one today.

Development is community-run under the name Three.js Authors, not a company. The repository still lives under Cabello’s GitHub account, but release publishing is shared. r171, for one, was published by contributor Mugen87.

The numbers, with where each one comes from.

  • The first release landed on April 24, 2010 (Wikipedia, citing the first GitHub commit).
  • The GitHub repository lists the MIT license.
  • Stars sit at about 116k (GitHub, October 2026), and Wikipedia counts more than 2000 contributors (February 2026).
  • The npm download API shows 20,521,334 weekly downloads for October 3 to October 9, 2026.

You’ll see lower weekly figures elsewhere. LogRocket gives about 1.8 million and Socket package pages show about 10 million, most likely from older snapshots. For a current count, cite the npm API figure.

What is shaping UX design today?

Uncover the newest UX design statistics: user behavior, design trends, ROI data, and insights driving better digital experiences.

Check Them Out →

How Does Three.js Relate to WebGL and WebGPU?

It sits above both. WebGL and WebGPU talk to the GPU, and Three.js supplies the scene, camera, material and light objects developers actually write against. The Three.js manual points out that people often confuse the library with the WebGL graphics API, which on its own only draws points, lines and triangles.

RendererDraws toStatus
WebGLRendererWebGL 2 canvasCore build, manual’s pick for pure WebGL 2 apps
WebGPURendererWebGPU, with WebGL 2 fallbackCore build via the three/webgpu import
SVGRendererSVG elementsAdd-on
CSS3DRendererDOM elements via CSS 3D transformsAdd-on

Three.js vs raw WebGL

Raw WebGL has you writing shader programs and managing buffers, with the 3D math on top of that. Three.js ships scenes, lights, shadows, materials, textures and the math utilities so you don’t have to.

Since r118, Three.js uses WebGL 2.0 by default (Wikipedia). Raw WebGL only makes sense when a project needs control over every GPU call and can’t carry any library weight.

Renderer status as of October 2026

WebGPU reached Chrome, Edge, Firefox and Safari by November 25, 2025, according to a web.dev announcement. Chrome and Edge have had it since version 113. Firefox added Windows support in 141. Safari covers macOS, iOS and iPadOS 26.

Coverage was still uneven at that point. Firefox support for Linux, Android and Intel Macs was in progress, which is why WebGPURenderer keeps a WebGL 2 backend as its fallback.

Sources disagree on how mature the renderer is. The README lists WebGPU as one of two renderers in current builds. Wikipedia’s feature list still labels it experimental. The official manual, meanwhile, keeps recommending WebGLRenderer for pure WebGL 2 applications.

Each one is answering a slightly different question (capability, a maturity label, a recommendation), so the disagreement is smaller than it looks. The r171 release notes on GitHub show where the split happened, with separate WebGL and WebGPU entry points and a new three.tsl.js file.

Speed isn’t guaranteed either. ics.media reported that, as of r176 in May 2025, WebGLRenderer can run faster than WebGPURenderer in some scenes.

Shaders change with the backend. TSL, the node-based Three.js shading language, replaces hand-written GLSL on WebGPURenderer, and the API reference lists both a WGSLNodeBuilder and a GLSLNodeBuilder, so one node graph targets WebGPU or the fallback. The manual also documents a forceWebGL option that forces the WebGL 2 backend.

WebGLRenderer is the safer pick when the project has to ship to every device right now or leans on existing GLSL ShaderMaterial code. WebGPURenderer makes more sense for a project that needs compute shaders or will be maintained for years, as long as the team is happy writing materials in TSL.

What Are the Core Parts of a Three.js Scene?

See the Pen
Interactive 3D Galaxy Simulation
by Voxelo (@VoXelo)
on CodePen.

A renderer, a scene and a camera are the minimum for getting an image out of Three.js. The renderer draws the portion of the scene inside the camera’s view onto a canvas. Everything else (meshes, lights, textures) attaches to the scene, which the manual describes as the root of a tree called the scene graph.

  • The scene is the root and holds the background color and fog.
  • A mesh pairs a geometry (the vertex data) with a material (the surface look), and has its own position, rotation and scale.
  • Textures come from an image file, a canvas or another rendered scene.
  • AmbientLight, DirectionalLight and PointLight are the common lights, with a few more besides.

One geometry and one material can serve many meshes. Two blue cubes need two meshes but only one of each.

Whether lights matter depends on the material. MeshBasicMaterial ignores them, while MeshPhongMaterial and MeshStandardMaterial react to them.

Children inherit their parent’s transform, so wheels placed under a car object follow the car when it moves.

PerspectiveCamera takes a field of view, an aspect ratio, and near and far limits. Anything outside that frustum isn’t drawn, and OrthographicCamera drops perspective foreshortening. Most angles in Three.js are radians, but PerspectiveCamera takes its field of view in degrees (Three.js manual).

The render loop with requestAnimationFrame

Nothing moves in a Three.js scene until a loop redraws it.

The manual’s example calls requestAnimationFrame and converts the elapsed time it receives from milliseconds to seconds. It then sets each cube’s rotation from that value, calls renderer.render(scene, camera) and schedules the next frame.

Game developers will know it as the game loop, where you update state, draw, repeat.

The current README example uses renderer.setAnimationLoop(animate) instead, which hands the loop to the renderer. Both styles show up in official material.

Camera controls

See the Pen
CPChallenge: Bugs (butterflies with threejs-toy)
by Tommy Ho (@tommyho)
on CodePen.

OrbitControls lets users rotate, pan and zoom around a target with mouse or touch. It’s an add-on imported from three/addons/controls/OrbitControls.js, not part of the core build.

The add-ons folder has other schemes too.

  • MapControls
  • FlyControls
  • FirstPersonControls
  • TrackballControls
  • PointerLockControls

OrbitControls suits product viewers and model inspection. The others are for map-style cameras and for flight or first-person movement.

Which 3D Formats and Assets Does Three.js Load?

The manual recommends glTF wherever possible, in either .glb or .gltf form. It’s built for runtime delivery, so files are compact to transmit and fast to load.

One glTF file carries meshes, materials, textures, skins, skeletons, morph targets, animations, lights and cameras. Khronos released glTF 2.0 as the ISO/IEC 12113:2022 International Standard.

  • GLTFLoader handles glTF and GLB, and it’s the default choice.
  • FBXLoader covers FBX, the fallback when glTF export isn’t offered.
  • OBJ goes through OBJLoader, with MTLLoader for the separate material file.
  • ColladaLoader reads COLLADA.

Only a few loaders, such as ObjectLoader, ship in the core build. GLTFLoader and the rest are add-ons, imported from three/addons/loaders/.

Compressed glTF files need extra decoders, each attached through a setter on GLTFLoader (GLTFLoader documentation). DRACOLoader covers Draco mesh compression and KTX2Loader covers KTX2 textures. A meshopt decoder is what you need for EXT_meshopt_compression.

When a model doesn’t show up, check the scale first, since models arrive in different units and a factor of 1000 is worth trying (Three.js manual). A missing light can also leave it sitting in the dark. Texture paths cause trouble now and then as well, because absolute paths from the authoring machine have to become relative to the model file.

Memory is the other documented trap. Image bitmaps created while loading aren’t garbage-collected when unreferenced, and they need explicit disposal, per the GLTFLoader documentation.

How to Install Three.js and Render a First Scene

The Three.js manual calls npm with a build tool such as Vite the recommended route for most users, because a build tool resolves imports without an import map.

  1. Install Node.js, which manages dependencies and runs the build tool.
  2. Run npm install –save three, then npm install –save-dev vite.
  3. Create index.html with a module script pointing to /main.js, and start main.js with import * as THREE from ‘three’.
  4. Run npx vite and open the localhost address it prints (the manual’s example shows port 5173).
  5. In main.js, create a renderer, a PerspectiveCamera and a Scene, then add a Mesh built from a BoxGeometry and a lit material.
  6. Add a DirectionalLight, call renderer.render(scene, camera) inside a loop, and rotate the mesh on every frame.
  7. Run npx vite build for production and host the dist folder.

You can skip the build tool and put an import map in the page head that points “three” and “three/addons/” at a CDN such as jsDelivr, pinned to one version. Without that map the browser doesn’t know what ‘three’ means. Double-clicking the HTML file doesn’t work either, so the manual has you run a local server such as npx serve.

As of r147, the manual treats ES modules as the only proper way to load the library.

The CDN route has a documented risk. An outage takes the site down with it, and every dependency has to come from the same Three.js version and the same CDN, since mixed sources can duplicate code or break the app (Three.js manual).

What Can You Build With Three.js?

Anything that needs interactive 3D inside a web page. Data visualization, product viewers, creative sites, browser games and WebXR experiences are the usual cases.

GitHub’s homepage globe ran in a WebGL context powered by three.js, and the team said cross-device performance pushed them into heavy optimization (GitHub Engineering, 2020).

Product viewers and configurators lean on MeshStandardMaterial and MeshPhysicalMaterial for physically based shading, with OrbitControls for inspection and GLTFLoader to bring the model in.

Creative sites and games get shader effects, post-processing such as bloom and depth of field, and InstancedMesh for thousands of repeated objects. The game logic is still written by the team.

Conversion-lift claims for configurators circulate widely, but they come from vendors and secondary roundups, not controlled studies of Three.js. No figure is quoted here.

WebXR in Three.js

Three.js switches on WebXR through renderer.xr.enabled, and the VRButton and ARButton add-ons start the session. The session runs on the WebXR Device API, so the headset supplies camera direction, field of view and aspect instead of the page.

renderer.setAnimationLoop replaces requestAnimationFrame in VR, because Three.js has to own the loop. Units are meters, so a camera at 1.6 sits at standing eye height. And if the headset isn’t the development machine, you need HTTPS.

The manual’s VR article references r112 and May 2019 device support. Check its device advice against current documentation before copying it.

React Three Fiber and the wider ecosystem

React Three Fiber is a React renderer for Three.js, not a competing library.

JSX mesh tags become new THREE.Mesh() calls at runtime, so new Three.js features show up in JSX without waiting for a React Three Fiber release (React Three Fiber docs).

On versions, @react-three/fiber 8 pairs with React 18 and version 9 pairs with React 19. Version 10 is in alpha and adds WebGPU support, per the React Three Fiber release notes.

  • drei supplies helper components.
  • @react-three/rapier does 3D physics.
  • @react-three/xr handles VR and AR controllers.
  • gltfjsx turns glTF files into JSX components.

A-Frame comes at the same foundation from the HTML side. Its documentation describes an entity-component framework for VR built on three.js, started at Mozilla, where a scene is written as markup.

Three.js vs Babylon.js, PlayCanvas and Unity: Which One Fits?

Three.js suits custom visuals written by a team that’s comfortable in code. If physics or tooling has to come built in, or you want an editor, Babylon.js or PlayCanvas are the better bet.

OptionBuilt inWeb graphics APIBest fit
Three.jsRendering plus add-ons, including Rapier, Jolt and Ammo physics wrappersWebGL 2, WebGPUCustom visuals, viewers, creative sites
Babylon.jsPhysics, collisions and particles covered in its own courseWebGL, WebGPUFeature-heavy 3D apps and games
PlayCanvasCollaborative cloud editor, MIT-licensed engineWebGL 2, WebGPU with computeTeam-built games and configurators
UnityFull engine and editorWebGL 2 default, WebGPU experimentalProjects already in Unity

The gap is tooling, not rendering quality. Three.js ships a renderer and add-ons, while the other two ship a larger workflow around theirs.

Babylon.js puts its mission as building one of the world’s most powerful, beautiful, simple and open web rendering engines. Its getting-started course has chapters on collisions, particle systems and physics.

PlayCanvas pairs an MIT-licensed open-source engine with a collaborative cloud editor, and its site lists WebGPU with compute shaders plus WebGL2 compatibility.

Unity’s Web build defaults to WebGL2, and the Unity 6.3 LTS manual (built October 2026) labels its WebGPU path experimental. web.dev’s November 2025 list of libraries with WebGPU support names Three.js, Babylon.js and PlayCanvas, and Unity as well, so the two sources disagree on how settled Unity’s path is.

Three.js is the fit for a viewer, a visualization or a creative site when the team already writes JavaScript. Babylon.js or PlayCanvas make more sense when physics, collisions and an inspector or editor are needed on day one. Unity only wins when the project already lives there and the web build is one more target.

Three.js is the default pick for web 3D, but a small team building an online multiplayer game gets more from PlayCanvas’s editor than from Three.js’s ecosystem.

When Three.js Is the Wrong Choice

Three.js is a rendering library, so a team assembles physics, game logic and workflow itself. The manual’s own wording is that it includes the fundamentals of a 3D engine, and everything else is an add-on or third-party code.

Physics is the clearest gap. The add-ons directory carries RapierPhysics, JoltPhysics and AmmoPhysics wrappers, and React Three Fiber has Rapier and Cannon bindings, but each one is a choice the team makes and maintains.

Draw calls are the other place it bites. In the manual’s globe example, about 19,000 separate boxes ran below 20 fps on the author’s machine, and merging them into one geometry with BufferGeometryUtils.mergeGeometries brought it to 60 fps. Every Mesh costs one or more draw requests, so drawing two things carries more overhead than drawing one.

Merging has a cost of its own. A merged mesh has one material and its parts are no longer easy to move. Vertex colors restore per-box color, but independent movement gets harder (Three.js manual).

Bundlephobia lists the three package at version 0.186.1 as 736 kB minified and about 185 kB gzipped for its main entry point, with no dependencies. That suits a hero scene and weighs heavily on a page that only needs a spinning logo.

Skip Three.js for 2D work. A sprite game or flat interface fits PixiJS better, because a perspective camera and a 3D scene graph add weight the project never uses.

  • A flipping card or tilting panel is a CSS 3D transform job with zero dependencies.
  • A team where nobody writes JavaScript is better served by a visual editor such as PlayCanvas.

Three.js FAQ

Is Three.js hard to learn for beginners?

Moderately. The manual’s tutorials assume working JavaScript, mostly in ES6 style, so what’s new is the 3D vocabulary of cameras, materials and lights. Starting with a single spinning cube, as the manual does, keeps the first project small.

Does Three.js run on mobile browsers?

Yes, in any browser with WebGL 2 support, according to Wikipedia. WebGPURenderer adds Chrome for Android from version 121 on Android 12 devices with Qualcomm or ARM GPUs (web.dev, 2025), and the automatic WebGL 2 fallback covers the rest.

Why do Three.js releases use r numbers while npm shows 0.x versions?

The r number is the release label on GitHub and in the docs, and npm publishes the same release as a 0.x version, so r186 ships as 0.186.x. The Migration Guide advises updating old projects in steps of 10 releases, because deprecation warnings last for 10 releases.

Does Three.js include a visual editor?

Yes. The repository carries a web-based scene editor, documented in an Editor Manual on the project wiki, for assembling and exporting scenes. It’s a scene editor, not a collaborative project workflow like the PlayCanvas editor.

What to Learn After the First Three.js Scene

Once a first scene renders, the next thing to learn is the glTF asset pipeline, meaning GLTFLoader with the Draco and KTX2 decoders. The renderer choice, WebGLRenderer or WebGPURenderer, comes after that, and React Three Fiber after both for apps that already run on React.

The order follows dependency. A scene without loaded models stays a demo, the renderer choice decides whether materials are written in GLSL or TSL, and the React Three Fiber docs expect fluency in both React and Three.js first.

The cost of this order is a late start on shaders. Effects stay limited to built-in materials until the renderer decision is made.

Verified October 2026, React Three Fiber v10 is in alpha and adds WebGPU support. A stable release would let React teams settle the renderer and the React layer in one step.

Bogdan Sandu
Latest posts by Bogdan Sandu (see all)