{"id":936,"date":"2026-07-02T06:22:30","date_gmt":"2026-07-01T23:22:30","guid":{"rendered":"https:\/\/sumberlaba.com\/index.php\/2026\/07\/02\/mastering-three-js-build-immersive-3d-web-experiences-from-scratch\/"},"modified":"2026-07-02T06:22:30","modified_gmt":"2026-07-01T23:22:30","slug":"mastering-three-js-build-immersive-3d-web-experiences-from-scratch","status":"publish","type":"post","link":"https:\/\/sumberlaba.com\/index.php\/2026\/07\/02\/mastering-three-js-build-immersive-3d-web-experiences-from-scratch\/","title":{"rendered":"Mastering Three.js: Build Immersive 3D Web Experiences from Scratch"},"content":{"rendered":"<p>Here is a comprehensive, HTML-formatted tutorial covering how to use Three.js for 3D on the web. It includes a detailed step-by-step guide, best practices, an FAQ section, and reference tables, all structured for clarity and depth.<br \/>\n&#8220;`html<br \/>\n<!DOCTYPE html><br \/>\n<html lang=\"en\"><br \/>\n<head><br \/>\n    <meta charset=\"UTF-8\"><br \/>\n    <meta name=\"viewport\" content=\"width=device-width, initial-scale=1.0\"><br \/>\n    <title>Three.js 3D Web Development: The Ultimate Step-by-Step Guide<\/title><\/p>\n<style>\n        body {\n            font-family: 'Georgia', serif;\n            line-height: 1.8;\n            max-width: 960px;\n            margin: 2rem auto;\n            padding: 0 1.5rem;\n            color: #1a1a2e;\n            background: #fafafa;\n        }\n        h1 {\n            font-size: 2.4rem;\n            border-bottom: 4px solid #e94560;\n            padding-bottom: 0.5rem;\n            color: #0f3460;\n        }\n        h2 {\n            font-size: 1.8rem;\n            margin-top: 2.5rem;\n            color: #16213e;\n            border-left: 6px solid #e94560;\n            padding-left: 1rem;\n        }\n        h3 {\n            font-size: 1.4rem;\n            margin-top: 1.8rem;\n            color: #0f3460;\n        }\n        p {\n            margin: 1.2rem 0;\n            text-align: justify;\n        }\n        ul, ol {\n            margin: 1rem 0 1rem 2rem;\n        }\n        li {\n            margin: 0.5rem 0;\n        }\n        table {\n            width: 100%;\n            border-collapse: collapse;\n            margin: 2rem 0;\n            font-size: 0.95rem;\n        }\n        th {\n            background: #16213e;\n            color: #fff;\n            padding: 12px 10px;\n            text-align: left;\n        }\n        td {\n            padding: 10px;\n            border-bottom: 1px solid #ddd;\n            vertical-align: top;\n        }\n        tr:nth-child(even) {\n            background: #f0f0f5;\n        }\n        pre {\n            background: #1e1e2f;\n            color: #f8f8f2;\n            padding: 1.2rem;\n            border-radius: 8px;\n            overflow-x: auto;\n            font-size: 0.9rem;\n            line-height: 1.5;\n            margin: 1.5rem 0;\n        }\n        code {\n            font-family: 'Courier New', monospace;\n            background: #eaeef2;\n            padding: 0.2rem 0.4rem;\n            border-radius: 4px;\n            font-size: 0.9rem;\n        }\n        pre code {\n            background: transparent;\n            padding: 0;\n            color: inherit;\n        }\n        .faq-question {\n            font-weight: 700;\n            color: #0f3460;\n            margin-top: 1.5rem;\n        }\n        .faq-answer {\n            margin-left: 1rem;\n        }\n        .tip-box {\n            background: #e8f4f8;\n            border-left: 5px solid #0f3460;\n            padding: 1rem 1.5rem;\n            border-radius: 0 8px 8px 0;\n            margin: 1.5rem 0;\n        }\n        .article-placeholder {\n            display: block;\n            width: 100%;\n            height: 60px;\n            background: linear-gradient(135deg, #eee 0%, #ddd 100%);\n            border-radius: 8px;\n            text-align: center;\n            line-height: 60px;\n            color: #888;\n            font-style: italic;\n            margin: 2rem 0;\n        }\n        @media (max-width: 600px) {\n            body { font-size: 1rem; padding: 0 1rem; }\n            h1 { font-size: 1.8rem; }\n            h2 { font-size: 1.4rem; }\n            table { font-size: 0.8rem; }\n        }\n    <\/style>\n<p><\/head><br \/>\n<body><\/p>\n<h1>Mastering Three.js: Build Immersive 3D Web Experiences from Scratch<\/h1>\n<p>Three.js has revolutionized the way developers approach three-dimensional graphics on the web. Gone are the days when building interactive 3D scenes required deep expertise in low-level WebGL, complex shader programming, and painful cross-browser compatibility workarounds. Three.js abstracts all that complexity into a clean, well-documented JavaScript library that lets you create stunning 3D visualizations, product configurators, data dashboards, games, and even virtual reality experiences using nothing more than a modern browser. Whether you are a front-end developer looking to add a wow factor to your portfolio, a data scientist who wants to visualize complex datasets in three dimensions, or a creative coder eager to push the boundaries of what the web can do, Three.js provides the tools you need without forcing you to become a graphics programming expert.<\/p>\n<p>In this comprehensive guide, we will walk through everything you need to know to start building 3D applications with Three.js. You will learn how to set up a scene, create and manipulate objects, apply materials and lighting, add interactivity with raycasting, and optimize performance for real-time rendering. We will also cover best practices that professional developers use in production and answer frequently asked questions that trip up beginners. By the time you finish reading, you will have the confidence to build your own 3D web projects from scratch. Let&#8217;s begin our journey into the third dimension.<\/p>\n<p><img decoding=\"async\" src=\"https:\/\/via.placeholder.com\/800x600\/4a90d9\/ffffff?text=how%20to%20use%20Three.js%20for%203D%20on%20web\" alt=\"Article illustration\" style=\"display:block;margin:20px auto;max-width:100%;height:auto;border-radius:8px;\" \/><\/p>\n<h2>What is Three.js and Why Should You Use It?<\/h2>\n<p>Three.js is a cross-browser JavaScript library and application programming interface (API) used to create and display animated 3D computer graphics in a web browser. It uses WebGL under the hood, but it wraps the raw WebGL calls into intuitive high-level objects like scenes, cameras, meshes, lights, and materials. The library was first released by Ricardo Cabello (known as Mr.doob) in 2010 and has since grown into the most popular 3D library on the web, with a massive community, extensive documentation, and thousands of examples. One of the greatest strengths of Three.js is its balance between power and accessibility. You can create a rotating cube with fewer than twenty lines of code, yet you can also build advanced effects like post-processing, shadows, particle systems, and physically-based rendering (PBR) that rival desktop applications.<\/p>\n<p>Why should you choose Three.js over raw WebGL or other libraries like Babylon.js? First, Three.js has the largest ecosystem, which means more tutorials, more community extensions, and more pre-built components. Second, it is framework-agnostic, so you can integrate it with React (via react-three-fiber), Vue, Angular, or vanilla JavaScript. Third, it has excellent documentation and a huge collection of official examples that demonstrate virtually every feature. Fourth, it supports a wide range of 3D model formats including glTF, OBJ, FBX, Collada, and STL, making it easy to import assets from Blender, Maya, or SketchUp. Finally, Three.js has a gentle learning curve compared to writing raw WebGL, and its API is consistent and well-thought-out. Whether you are building a simple product viewer or a complex multiplayer game, Three.js gives you a solid foundation.<\/p>\n<h2>Step-by-Step Guide: Building a 3D Scene with Three.js<\/h2>\n<h3>Step 1: Setting Up Your Development Environment<\/h3>\n<p>Before you can start coding, you need to set up a project environment. Three.js can be used in several ways: you can include it via a CDN link in a simple HTML file, install it as an npm package for a more advanced build pipeline, or use it with module bundlers like Webpack or Vite. For beginners, the fastest way to get started is to use a CDN. Create a new HTML file and include the Three.js core library using a script tag. As of 2025, the recommended CDN is unpkg or cdnjs, and you should always specify a version to avoid breaking changes. For example, you can use <code>https:\/\/unpkg.com\/three@0.160.0\/build\/three.module.js<\/code> if you are using ES modules, or the classic build with <code>https:\/\/cdnjs.cloudflare.com\/ajax\/libs\/three.js\/r128\/three.min.js<\/code> for older-style scripts. In this tutorial, we will use the ES module approach because it is cleaner and more modern. Create a minimal HTML file with a container div, import Three.js, and set up a basic renderer.<\/p>\n<p>For those who prefer a more professional setup, you can initialize a project with npm. Run <code>npm init -y<\/code> in your project folder, then <code>npm install three<\/code>. This will install the latest version into your node_modules. You can then import Three.js in your JavaScript file using <code>import * as THREE from 'three';<\/code>. If you are using Vite as your build tool (which we highly recommend for its speed and simplicity), your setup is even easier: just create a new Vite project with <code>npm create vite@latest<\/code> and select the vanilla JavaScript template. Then install Three.js and start coding. Regardless of which method you choose, the core concepts remain identical. Once your environment is ready, it is time to create the four essential components of any Three.js application: the scene, the camera, the renderer, and an object.<\/p>\n<h3>Step 2: Creating the Scene, Camera, and Renderer<\/h3>\n<p>Every Three.js application revolves around three fundamental objects: a <strong>Scene<\/strong>, a <strong>Camera<\/strong>, and a <strong>Renderer<\/strong>. The Scene is a container that holds all the objects, lights, and backgrounds. Think of it as your 3D world. The Camera defines the viewpoint from which the scene is rendered. Three.js offers several camera types, but the most common are PerspectiveCamera (which mimics human vision with perspective distortion) and OrthographicCamera (which renders without perspective, useful for 2D-like views or technical diagrams). The Renderer takes the scene and camera and draws the image onto an HTML canvas element. WebGLRenderer is the standard choice. Let&#8217;s create these three objects step by step.<\/p>\n<p>First, define a Scene: <code>const scene = new THREE.Scene();<\/code>. You can optionally set a background color using <code>scene.background = new THREE.Color(0x1a1a2e);<\/code>. Next, create a PerspectiveCamera. The constructor takes four parameters: field of view (FOV) in degrees, aspect ratio (width \/ height), near clipping plane, and far clipping plane. A typical setup looks like this: <code>const camera = new THREE.PerspectiveCamera(75, window.innerWidth \/ window.innerHeight, 0.1, 1000);<\/code>. The camera starts at the origin (0,0,0), so you need to move it back so you can see the scene: <code>camera.position.set(0, 2, 5);<\/code>. Finally, create a WebGLRenderer: <code>const renderer = new THREE.WebGLRenderer({ antialias: true });<\/code>. Set its size to match the window, and append the canvas to your HTML document: <code>renderer.setSize(window.innerWidth, window.innerHeight); document.body.appendChild(renderer.domElement);<\/code>. Now you have a blank 3D canvas. To make it responsive, add a window resize listener that updates the camera aspect ratio and renderer size.<\/p>\n<h3>Step 3: Adding Geometry, Material, and Mesh<\/h3>\n<p>With the scene, camera, and renderer ready, you can start adding 3D objects. In Three.js, any visible object is a <strong>Mesh<\/strong>, which is a combination of a <strong>Geometry<\/strong> (the shape) and a <strong>Material<\/strong> (the surface appearance). Three.js provides a wide variety of geometries: BoxGeometry, SphereGeometry, CylinderGeometry, PlaneGeometry, TorusGeometry, and many more. For materials, you have options like MeshBasicMaterial (no lighting), MeshStandardMaterial (PBR-based, works with lights), MeshPhongMaterial (classic Phong shading), and MeshPhysicalMaterial (advanced PBR with clearcoat, roughness, metalness). Let&#8217;s create a simple rotating cube as your first object.<\/p>\n<p>Create a box geometry with dimensions 1x1x1: <code>const geometry = new THREE.BoxGeometry(1, 1, 1);<\/code>. Then create a material. We will use MeshStandardMaterial so that lighting affects the cube: <code>const material = new THREE.MeshStandardMaterial({ color: 0xe94560, roughness: 0.4, metalness: 0.1 });<\/code>. Now combine them into a mesh: <code>const cube = new THREE.Mesh(geometry, material);<\/code>. By default, the cube is placed at the origin (0,0,0). Add it to the scene: <code>scene.add(cube);<\/code>. If you render right now, you would see nothing because there is no light \u2014 MeshStandardMaterial requires lights to be visible. So let&#8217;s add some lights. A basic ambient light provides overall illumination: <code>const ambientLight = new THREE.AmbientLight(0xffffff, 0.4); scene.add(ambientLight);<\/code>. Then add a directional light to create shadows and highlights: <code>const dirLight = new THREE.DirectionalLight(0xffffff, 1.0); dirLight.position.set(5, 10, 7); scene.add(dirLight);<\/code>. Now you have a visible cube. To see it in motion, you need an animation loop.<\/p>\n<h3>Step 4: Creating an Animation Loop and Rendering<\/h3>\n<p>Three.js uses a rendering loop to update the scene 60 times per second (or whatever the monitor&#8217;s refresh rate allows). The most common approach is to use <code>requestAnimationFrame<\/code>, which tells the browser to call your render function before the next repaint. Inside this loop, you can update object positions, rotations, scales, or any other property, and then call <code>renderer.render(scene, camera);<\/code>. This creates real-time interactive graphics. Let&#8217;s make our cube rotate by incrementing its rotation properties each frame.<\/p>\n<p>Write a function called <code>animate<\/code> that does three things: calls <code>requestAnimationFrame(animate)<\/code> for the next frame, updates the cube&#8217;s rotation by adding a small delta, and renders the scene. Here is the code skeleton: <code>function animate() { requestAnimationFrame(animate); cube.rotation.x += 0.01; cube.rotation.y += 0.01; renderer.render(scene, camera); } animate();<\/code>. This will make the cube spin smoothly along both the X and Y axes. If you run the page, you should see a nicely lit red cube rotating in the center of the viewport. Congratulations \u2014 you have created your first real-time 3D scene with Three.js! From here, you can experiment with different geometries, materials, and transformation properties.<\/p>\n<h3>Step 5: Adding Interactivity with Raycaster and Mouse Events<\/h3>\n<p>A static 3D scene is cool, but true web experiences need interactivity. Three.js provides the <strong>Raycaster<\/strong> class to detect mouse clicks, hovers, and touches on 3D objects. The raycaster works by casting an invisible ray from the camera through the mouse position into the scene, and then checking which objects intersect that ray. This is the foundation for clickable buttons, drag-and-drop, tooltips, and game interactions. Let&#8217;s add a simple hover effect that changes the cube&#8217;s color when the mouse is over it.<\/p>\n<p>First, create a Raycaster and a Vector2 for the mouse position: <code>const raycaster = new THREE.Raycaster(); const mouse = new THREE.Vector2();<\/code>. Then add an event listener for &#8216;mousemove&#8217; on the canvas or the window. In the listener, convert the mouse coordinates to normalized device coordinates (NDC) where x and y range from -1 to 1: <code>mouse.x = (event.clientX \/ window.innerWidth) * 2 - 1; mouse.y = -(event.clientY \/ window.innerHeight) * 2 + 1;<\/code>. In your animation loop (or in a separate update function), update the raycaster with the camera and mouse: <code>raycaster.setFromCamera(mouse, camera);<\/code>. Then compute intersections with the objects you want to interact with: <code>const intersects = raycaster.intersectObjects([cube]);<\/code>. If the array is not empty, the mouse is over the cube. Change the material color for feedback, and reset it when the mouse leaves. You can use <code>cube.material.color.setHex(0xffaa00);<\/code> for hover and <code>cube.material.color.setHex(0xe94560);<\/code> for normal. This simple interaction opens the door to sophisticated UI and game mechanics.<\/p>\n<h3>Step 6: Loading and Displaying 3D Models<\/h3>\n<p>While primitive geometries are great for learning, real-world projects often use complex 3D models created in external tools like Blender, Maya, or Cinema 4D. Three.js supports many model formats, but the preferred format is <strong>glTF<\/strong> (GL Transmission Format) because it is efficient, supports PBR materials, and can include animations. To load a glTF model, you need to use the GLTFLoader, which is part of the examples add-on. First, import the loader: <code>import { GLTFLoader } from 'three\/examples\/jsm\/loaders\/GLTFLoader.js';<\/code>. Then create an instance and call <code>loader.load('path\/to\/model.glb', callback)<\/code>. The callback receives the loaded scene, which you can add directly to your main scene.<\/p>\n<p>Here is an example: <code>const loader = new GLTFLoader(); loader.load('models\/robot.glb', (gltf) => { scene.add(gltf.scene); }, undefined, (error) => { console.error(error); });<\/code>. You may need to adjust the model&#8217;s scale, position, or rotation after loading. Many models come with animations, which you can play using three.js&#8217;s AnimationMixer. Loading models asynchronously requires careful handling, but it allows you to incorporate high-quality assets into your web experience. Always ensure your model files are optimized for the web \u2014 heavy polygon counts can ruin performance. Tools like Blender&#8217;s decimate modifier or online compressors can help reduce file size while preserving visual quality.<\/p>\n<h3>Step 7: Implementing Shadows for Realism<\/h3>\n<p>Shadows add a tremendous amount of depth and realism to 3D scenes. Three.js supports both directional and spot light shadows, as well as point light shadows. To enable shadows, you need to set several properties. First, enable shadow mapping on the renderer: <code>renderer.shadowMap.enabled = true;<\/code>. Then, tell the light to cast shadows: <code>dirLight.castShadow = true;<\/code>. Set the shadow map size for quality: <code>dirLight.shadow.mapSize.width = 1024; dirLight.shadow.mapSize.height = 1024;<\/code>. Also define the shadow camera frustum \u2014 the area where shadows are calculated: <code>dirLight.shadow.camera.near = 0.1; dirLight.shadow.camera.far = 25; dirLight.shadow.camera.left = -10; dirLight.shadow.camera.right = 10; dirLight.shadow.camera.top = 10; dirLight.shadow.camera.bottom = -10;<\/code>. For the objects, set <code>mesh.castShadow = true<\/code> on the cube and <code>mesh.receiveShadow = true<\/code> on the ground plane. Create a ground plane using <code>new THREE.PlaneGeometry(10, 10)<\/code> with a MeshStandardMaterial. Rotate it to be horizontal: <code>ground.rotation.x = -Math.PI \/ 2;<\/code>. Add it to the scene. Now your cube will cast a crisp shadow onto the ground, creating a professional-looking scene.<\/p>\n<h2>Tips and Best Practices for Three.js Development<\/h2>\n<div class=\"tip-box\">\n<h3>1. Optimize Performance with Geometry Merging and Instancing<\/h3>\n<p>When you have hundreds or thousands of objects in a scene, draw calls can quickly become a bottleneck. Three.js provides several techniques to reduce draw calls. <strong>Geometry merging<\/strong> (or BufferGeometry merging) combines multiple geometries into a single geometry, which can be rendered in one draw call. For repeated objects that share the same geometry but have different transformations (like a forest of trees or a field of particles), use <strong>InstancedMesh<\/strong>. InstancedMesh renders the same geometry multiple times with different transform matrices in a single draw call, drastically improving performance. Always profile your scene using the browser&#8217;s developer tools or the Three.js Stats panel to identify bottlenecks.<\/p>\n<\/div>\n<div class=\"tip-box\">\n<h3>2. Use LOD (Level of Detail) for Complex Models<\/h3>\n<p>If your scene contains models that are far from the camera, you can switch to lower-detail versions to save GPU cycles. Three.js provides the <strong>LOD<\/strong> class (Level of Detail) that automatically swaps between different geometry representations based on the distance from the camera. Create multiple versions of your model with decreasing polygon counts, and add them as levels to the LOD object. This is especially useful for large open-world scenes or when displaying many detailed characters. The transition between levels should be smooth to avoid popping artifacts.<\/p>\n<\/div>\n<div class=\"tip-box\">\n<h3>3. Always Dispose of Resources When Removing Objects<\/h3>\n<p>One of the most common memory leak sources in Three.js applications is failing to properly dispose of geometries, materials, and textures when they are no longer needed. When you remove an object from the scene, call <code>geometry.dispose()<\/code> and <code>material.dispose()<\/code> to free GPU memory. Textures also need to be disposed: <code>texture.dispose()<\/code>. If you are using a render target or a depth texture, dispose those as well. Neglecting this can cause your application to consume ever-increasing memory, leading to crashes or slowdowns. Make disposal a habit, especially in dynamic scenes where objects are created and destroyed frequently.<\/p>\n<\/div>\n<h2>Common Three.js Objects and Properties Reference<\/h2>\n<table>\n<thead>\n<tr>\n<th>Component<\/th>\n<th>Class \/ Constructor<\/th>\n<th>Key Properties<\/th>\n<th>Common Use Case<\/th>\n<\/tr>\n<\/thead>\n<tbody>\n<tr>\n<td>Scene<\/td>\n<td>THREE.Scene()<\/td>\n<td>background, fog, children<\/td>\n<td>Container for all objects<\/td>\n<\/tr>\n<tr>\n<td>Perspective Camera<\/td>\n<td>THREE.PerspectiveCamera(fov, aspect, near, far)<\/td>\n<td>position, rotation, zoom<\/td>\n<td>First-person view, games<\/td>\n<\/tr>\n<tr>\n<td>WebGLRenderer<\/td>\n<td>THREE.WebGLRenderer({antialias: true})<\/td>\n<td>setSize, shadowMap, toneMapping<\/td>\n<td>Rendering to canvas<\/td>\n<\/tr>\n<tr>\n<td>Box Geometry<\/td>\n<td>THREE.BoxGeometry(width, height, depth)<\/td>\n<td>parameters: widthSegments, etc.<\/td>\n<td>Cubes, crates, buildings<\/td>\n<\/tr>\n<tr>\n<td>MeshStandardMaterial<\/td>\n<td>THREE.MeshStandardMaterial({color, roughness, metalness})<\/td>\n<td>color, roughness, metalness, map<\/td>\n<td>PBR-based realistic surfaces<\/td>\n<\/tr>\n<tr>\n<td>DirectionalLight<\/td>\n<td>THREE.DirectionalLight(color, intensity)<\/td>\n<td>position, target, castShadow<\/td>\n<td>Simulating sunlight<\/td>\n<\/tr>\n<tr>\n<td>Raycaster<\/td>\n<td>THREE.Raycaster()<\/td>\n<td>setFromCamera, intersectObjects<\/td>\n<td>Mouse picking, interaction<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<h2>Performance Comparison: Rendering Strategies<\/h2>\n<table>\n<thead>\n<tr>\n<th>Strategy<\/th>\n<th>Draw Calls<\/th>\n<th>Memory Usage<\/th>\n<th>Best For<\/th>\n<th>Complexity<\/th>\n<\/tr>\n<\/thead>\n<tbody>\n<tr>\n<td>Individual Meshes<\/td>\n<td>High (bad)<\/td>\n<td>Low per mesh<\/td>\n<td>&lt; 100 objects<\/td>\n<td>Very simple<\/td>\n<\/tr>\n<tr>\n<td>Geometry Merging<\/td>\n<td>Low (1 per merged group)<\/td>\n<td>High (combined)<\/td>\n<td>Static scenes with many objects<\/td>\n<td>Medium<\/td>\n<\/tr>\n<tr>\n<td>InstancedMesh<\/td>\n<td>Low (1 per instance group)<\/td>\n<td>Medium (shared geo + per-instance data)<\/td>\n<td>Repeated objects (trees, particles)<\/td>\n<td>Medium-High<\/td>\n<\/tr>\n<tr>\n<td>LOD<\/td>\n<td>Variable<\/td>\n<td>Medium (multiple geo copies)<\/td>\n<td>Large worlds with distant objects<\/td>\n<td>High<\/td>\n<\/tr>\n<\/tbody>\n<\/table>\n<h2>Frequently Asked Questions (FAQ)<\/h2>\n<div class=\"faq-question\">1. Do I need to know WebGL to use Three.js?<\/div>\n<div class=\"faq-answer\">\n<p>No, you do not need to know WebGL to use Three.js effectively. The entire purpose of Three.js is to abstract away the complexities of WebGL. However, having a basic understanding of how 3D graphics work (vertices, normals, textures, shaders) will help you debug issues and optimize your scenes. For most common tasks like creating objects, adding lights, and loading models, you can work entirely with Three.js&#8217;s high-level API without ever writing a WebGL call.<\/p>\n<\/div>\n<div class=\"faq-question\">2. How do I make my Three.js scene responsive to window resizing?<\/div>\n<div class=\"faq-answer\">\n<p>To handle window resizing, listen for the &#8216;resize&#8217; event on the window object. Inside the event handler, update the camera&#8217;s aspect ratio to match the new window dimensions and call <code>camera.updateProjectionMatrix()<\/code>. Then update the renderer size: <code>renderer.setSize(window.innerWidth, window.innerHeight)<\/code>. If you are using a Canvas that is not fullscreen, you will need to calculate the correct width and height based on your container element. This ensures your 3D scene scales correctly without distortion.<\/p>\n<\/div>\n<div class=\"faq-question\">3. Can I integrate Three.js with React, Vue, or Angular?<\/div>\n<div class=\"faq-answer\">\n<p>Yes, absolutely. Three.js can be integrated with any JavaScript framework. For React, the most popular approach is to use <strong>react-three-fiber<\/strong> (R3F), which is a React renderer for Three.js. R3F lets you declare Three.js objects as JSX components and manages the render loop and lifecycle for you. For Vue, there is <strong>TroisJS<\/strong> and the more recent <strong>VueThree<\/strong>. For Angular, you can use <strong>ngx-three<\/strong> or simply wrap Three.js code in Angular services and components. In all cases, you need to be mindful of the framework&#8217;s lifecycle and avoid memory leaks by properly disposing of Three.js resources.<\/p>\n<\/div>\n<div class=\"faq-question\">4. How do I add text or UI labels to my 3D scene?<\/div>\n<div class=\"faq-answer\">\n<p>There are several ways to display text in Three.js. You can use <strong>TextGeometry<\/strong> to create 3D text that behaves like any other mesh, but you need to load a font. Alternatively, you can use <strong>CSS2DRenderer<\/strong> or <strong>CSS3DRenderer<\/strong> to overlay HTML\/CSS elements on top of your 3D scene, which is great for labels and tooltips. Another approach is to use sprite-based text with <strong>CanvasTexture<\/strong>, where you draw text onto a 2D canvas and then use that canvas as a texture on a plane or sprite. Each method has trade-offs in terms of performance, readability, and interactivity.<\/p>\n<\/div>\n<div class=\"faq-question\">5. What is the best way to optimize my Three.js application for mobile devices?<\/div>\n<div class=\"faq-answer\">\n<p>Mobile optimization requires careful attention to performance. Start by reducing polygon counts and texture sizes. Use <strong>compressed textures<\/strong> (KTX2 or Basis) to reduce GPU memory bandwidth. Limit the number of lights and use efficient shadow map resolutions (512 or 1024). Enable <strong>pixel ratio capping<\/strong>: <code>renderer.setPixelRatio(Math.min(window.devicePixelRatio, 2))<\/code> to avoid rendering at ultra-high resolutions on devices with Retina displays. Use <strong>geometry instancing<\/strong> for repeated objects and prefer <strong>MeshStandardMaterial<\/strong> over <strong>MeshPhysicalMaterial<\/strong> when possible. Finally, use the browser&#8217;s performance profiler and Three.js Stats to identify bottlenecks specific to mobile hardware.<\/p>\n<\/div>\n<div class=\"faq-question\">6. How can I create animations more complex than simple rotation?<\/div>\n<div class=\"faq-answer\">\n<p>For complex animations, Three.js provides the <strong>AnimationMixer<\/strong>, <strong>AnimationClip<\/strong>, and <strong>AnimationAction<\/strong> system. You can load animated models (glTF with animations) and play, blend, and cross-fade between animation clips. You can also use the <strong>TWEEN<\/strong> library (or the modern <strong>gsap<\/strong>) to tween property values over time. For skeleton-based animations, the AnimationMixer handles skinning and bone transforms. Additionally, you can create custom animation loops by updating object properties manually using sine\/cosine functions or easing equations for organic motion. For complex character animation, consider using Blender to create the animations and export them as glTF.<\/p>\n<\/div>\n<div class=\"faq-question\">7. What are the common pitfalls when loading external 3D models?<\/div>\n<div class=\"faq-answer\">\n<p>One common pitfall is incorrect scaling. Many modeling tools use different units (centimeters vs. meters), so a model may appear too large or too small. Always check the model&#8217;s scale and adjust it with <code>gltf.scene.scale.set(0.01, 0.01, 0.01)<\/code> if necessary. Another issue is missing textures, which happens when the model references external texture files with absolute paths or unsupported formats. Use relative paths and convert textures to JPEG or PNG. Also, be aware that some models contain multiple nested groups, so you may need to traverse the scene to find specific meshes. Finally, ensure that your model is optimized \u2014 heavy polygon counts and large texture files can kill frame rates. Use tools like <strong>glTF-Transform<\/strong> or <strong>Draco compression<\/strong> to reduce file size.<\/p>\n<\/div>\n<h2>Conclusion<\/h2>\n<p>Three.js has democratized 3D graphics on the web, making it possible for any developer with basic JavaScript skills to build immersive, interactive experiences that run directly in the browser. In this tutorial, we covered the entire pipeline: from setting up a development environment and creating a basic scene with a camera and renderer, to adding geometries, materials, and lights, animating objects, implementing mouse interaction with raycaster, loading external 3D models, and enabling realistic shadows. We also discussed performance optimization strategies like instancing, LOD, and proper resource disposal, and answered common questions that beginners often struggle with. The journey from a simple rotating cube to a fully interactive 3D web application is surprisingly short, and the creative possibilities are virtually endless.<\/p>\n<p>As you continue to explore Three.js, you will discover advanced topics like post-processing (bloom, depth of field, ambient occlusion), particle systems for smoke and fire, shader programming with custom GLSL, and integration with WebXR for virtual reality and augmented reality. The official Three.js documentation and the massive collection of examples on the Three.js website are invaluable resources. Join the community on Discord, GitHub, and forums to share your work and learn from others. The most important step is to start building \u2014 pick a small project, iterate on it, and gradually push your boundaries. The web is ready for 3D, and Three.js is the key that unlocks it.<\/p>\n<p><em>Happy coding, and welcome to the third dimension.<\/em><\/p>\n<p><\/body><br \/>\n<\/html><br \/>\n&#8220;`<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Here is a comprehensive, HTML-formatted tutorial covering how to use Three.js for 3D on the web. It includes a detailed step-by-step guide, best practices, an FAQ section, and reference tables, all structured for clarity and depth. &#8220;`html Three.js 3D Web Development: The Ultimate Step-by-Step Guide Mastering Three.js: Build Immersive 3D Web Experiences from Scratch Three.js &hellip; <\/p>\n","protected":false},"author":2716,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"om_disable_all_campaigns":false,"_monsterinsights_skip_tracking":false,"_monsterinsights_sitenote_active":false,"_monsterinsights_sitenote_note":"","_monsterinsights_sitenote_category":0,"footnotes":""},"categories":[],"tags":[],"class_list":["post-936","post","type-post","status-publish","format-standard","hentry"],"aioseo_notices":[],"_links":{"self":[{"href":"https:\/\/sumberlaba.com\/index.php\/wp-json\/wp\/v2\/posts\/936","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/sumberlaba.com\/index.php\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/sumberlaba.com\/index.php\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/sumberlaba.com\/index.php\/wp-json\/wp\/v2\/users\/2716"}],"replies":[{"embeddable":true,"href":"https:\/\/sumberlaba.com\/index.php\/wp-json\/wp\/v2\/comments?post=936"}],"version-history":[{"count":0,"href":"https:\/\/sumberlaba.com\/index.php\/wp-json\/wp\/v2\/posts\/936\/revisions"}],"wp:attachment":[{"href":"https:\/\/sumberlaba.com\/index.php\/wp-json\/wp\/v2\/media?parent=936"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/sumberlaba.com\/index.php\/wp-json\/wp\/v2\/categories?post=936"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/sumberlaba.com\/index.php\/wp-json\/wp\/v2\/tags?post=936"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}