Three.js 学习系列(一)序章:它是什么,为什么学,怎么学

一份从 0 到 1 的 Three.js 学习地图。这是 10 篇系列的第一篇——讲清楚 WebGL 与 Three.js 的关系、整个生态长什么样、官方三大入口怎么用,以及一段最小可运行的 "Hello Cube"。看完你能立刻动手,并清楚后面 9 篇会带你去哪里。
threejswebgl3djavascriptlearning-series

这是 Three.js 学习系列 的第一篇(共 10 篇规划)。 系列定位:使用入门 + 源码剖析 双线推进—— 既能让你写出代码,也能让你看懂 mrdoob/three.js 仓库到底是怎么组织的。 本篇是序章,建立全局观,把整张地图先放在你面前。

一、Three.js 是什么

一句话定义:Three.js 是一个用 JavaScript 写的 3D 渲染库,让你在浏览器里画 3D 而不用直接写 WebGL

它的作者是西班牙开发者 Ricardo Cabello(mrdoob),2010 年 4 月发布第一版。 到 2026 年它已经是 GitHub Star 数最高的 3D 引擎之一,全网用户基础大概只有 Unity / Unreal 这类游戏引擎能比。

为什么"在浏览器里画 3D"是大事? 因为 浏览器零安装、跨平台、内置在每台设备里—— 3D 内容一旦能跑在 Web 上,分发成本立刻塌方。

Three.js 的典型应用:

  • 产品展示(鞋、车、家具的可旋转 3D 预览)
  • 数据可视化(地球仪、网络拓扑、3D 图表)
  • 在线游戏与互动叙事
  • VR/AR(WebXR)
  • 创意作品集网站(很多艺术家的 portfolio)
  • 工业级 BIM / CAD 在线预览
  • AI 时代的 3D 场景编辑器(Blender 之外的 Web 替代)

二、WebGL 与 Three.js:底层和"封装"的关系

为了真正理解 Three.js,先把它和 WebGL 的关系说清楚:

┌─────────────────────────────────────┐
│        Three.js(高层抽象)         │ ← 你写: scene.add(cube)
├─────────────────────────────────────┤
│        WebGL / WebGPU API           │ ← 浏览器: gl.drawArrays(...)
├─────────────────────────────────────┤
│         GPU 驱动 + 硬件             │ ← OS / Driver
└─────────────────────────────────────┘
  • WebGL:W3C 标准,浏览器原生提供,API 极度底层—— 你要手动管理顶点缓冲区、写 GLSL shader、配置投影矩阵
  • Three.js:在 WebGL 上做了一层友好封装,把 3D 世界的概念(场景、相机、光、材质)抽象成对象

直观对比:画一个旋转的立方体,原生 WebGL 大约要 200 行,Three.js 大约要 20 行。

Three.js 的核心价值是**"把 GPU 编程的入门成本降一个数量级"**。 这一点和 React 之于 DOM、PyTorch 之于 CUDA 是同一种现象—— 行业普及一种新技术,几乎总是靠一层好抽象,而不是教所有人写底层

WebGPU 的关系:Three.js 从 r150+ 开始引入 WebGPU 渲染器(next-gen,性能更好、可计算着色器)。 现在仓库里 WebGL 与 WebGPU 并存——本系列会以 WebGL 渲染器为主,单独一篇讲 WebGPU 切换。

三、官方三大入口(先收藏,反复用)

学习 Three.js 最容易踩的坑是信息源太杂——网上教程版本不同步、API 改动频繁。 官方三件套就够了

入口链接用法
官网threejs.org看 examples,几百个交互式 demo 是最快建立"它能做什么"的方式
文档threejs.org/docsAPI 参考,所有类 / 方法 / 参数;遇到不懂的类直接到这里查,别看二手教程
手册threejs.org/manual官方教程,从基础到进阶,比所有第三方教程都新(社区维护,跟着版本走)
源码github.com/mrdoob/three.js真正想搞清楚原理时唯一可信源;本系列的"源码剖析"以这里为准

别在 2026 年还看 2019 年的 Three.js 教程—— API 变化大,构造函数签名、模块拆分、动画系统都改过几轮。 以官方 manual + examples 为主、第三方教程为辅,能避开 80% 的"我代码为啥不跑"的坑。

四、第一段可运行代码:Hello Cube

直接动手——这段代码在浏览器里能跑出一个旋转的彩色立方体

<!doctype html>
<html lang="zh">
  <head>
    <meta charset="utf-8" />
    <title>Hello Three.js</title>
    <style>body { margin: 0; overflow: hidden; }</style>
  </head>
  <body>
    <script type="importmap">
      {
        "imports": {
          "three": "https://unpkg.com/three@0.170.0/build/three.module.js"
        }
      }
    </script>
    <script type="module">
      import * as THREE from 'three'

      // 1. 三大件:场景 / 相机 / 渲染器
      const scene = new THREE.Scene()
      const camera = new THREE.PerspectiveCamera(
        75,                                // 视场角 fov
        window.innerWidth / window.innerHeight,  // 宽高比
        0.1,                               // 近裁剪面
        1000                               // 远裁剪面
      )
      camera.position.z = 3

      const renderer = new THREE.WebGLRenderer({ antialias: true })
      renderer.setSize(window.innerWidth, window.innerHeight)
      renderer.setPixelRatio(window.devicePixelRatio)
      document.body.appendChild(renderer.domElement)

      // 2. 加一个立方体进场景
      const geometry = new THREE.BoxGeometry(1, 1, 1)
      const material = new THREE.MeshNormalMaterial()   // 用法线着色,免光源
      const cube = new THREE.Mesh(geometry, material)
      scene.add(cube)

      // 3. 每帧渲染 + 旋转
      renderer.setAnimationLoop(() => {
        cube.rotation.x += 0.01
        cube.rotation.y += 0.01
        renderer.render(scene, camera)
      })

      // 4. 适配窗口尺寸
      window.addEventListener('resize', () => {
        camera.aspect = window.innerWidth / window.innerHeight
        camera.updateProjectionMatrix()
        renderer.setSize(window.innerWidth, window.innerHeight)
      })
    </script>
  </body>
</html>

把这段保存成 index.html双击打开就能看到一个旋转的彩色立方体。 (如果你浏览器对 CORS 严格,可以用 python -m http.server 本地起服务)

这段代码已经体现了 Three.js 的三大件 + 一个网格 + 一个渲染循环这套基础结构—— 后面所有更复杂的应用,本质上都是在这个骨架上扩展。

五、Three.js 的"三大件 + 一个生态"

让上面这段代码跑起来的几个基本概念,先把名字记住:

┌──────────────────┐
│      Scene       │  ← "舞台",所有可见对象都放进它
└────────┬─────────┘
         │
   ┌─────┴─────┐
   ↓           ↓
┌──────┐   ┌──────┐
│ Mesh │   │ Light│  ← 可被渲染的对象、光源、辅助物
└──────┘   └──────┘
   ↑
   │
┌──────────┐  ┌──────────┐
│ Geometry │  │ Material │
└──────────┘  └──────────┘

┌──────────────────┐    ┌──────────────────┐
│     Camera       │    │     Renderer     │
│ (观察者视角)     │    │ (把场景画成像素) │
└──────────────────┘    └──────────────────┘
概念角色关键类
Scene场景,对象的容器THREE.Scene
Camera相机,决定我们怎么看PerspectiveCamera / OrthographicCamera
Renderer渲染器,把场景画到 canvasWebGLRenderer / WebGPURenderer
Geometry几何体(形状)BoxGeometrySphereGeometryBufferGeometry
Material材质(外观、反射方式)MeshBasicMaterialMeshStandardMaterialShaderMaterial
Mesh网格 = Geometry + MaterialTHREE.Mesh
Light光源DirectionalLightPointLightAmbientLight

外围生态(不在核心仓库但常用):

  • OrbitControls —— 鼠标拖拽旋转相机
  • GLTFLoader —— 加载 .glb/.gltf 3D 模型
  • dat.GUI / lil-gui —— 实时调参
  • stats.js —— FPS 监测
  • EffectComposer —— 后处理(辉光、景深、抗锯齿)
  • drei(React Three Fiber 生态)—— React 写 Three.js 的工程辅助

六、Three.js 的源码全景(先看目录,再啃模块)

github.com/mrdoob/three.js 仓库根目录最值得了解的几个文件夹:

路径作用
src/所有源码,按模块组织
src/core/场景图基础:Object3D、BufferAttribute、Layers ……
src/cameras/各种相机实现
src/geometries/内置几何体(Box / Sphere / Plane / Torus / ……)
src/materials/内置材质(Basic / Standard / Phong / Shader / ……)
src/lights/光源实现
src/renderers/渲染管线核心——WebGLRenderer / WebGPURenderer
src/renderers/shaders/内置 GLSL 着色器源码(chunk 系统)
src/loaders/各种 Loader
src/animation/动画系统(AnimationMixer、KeyframeTrack)
examples/几百个交互式 demo
editor/官方在线场景编辑器源码

整个仓库有上千个 .js 文件,但 80% 的关键逻辑集中在 src/core + src/renderers/webgl 这两块—— 本系列后续会按"先看用法,再看源码"的方式,一层层往下挖。

对学习者来说一个非常好的习惯:遇到不懂的类,先打开 docs 看 API, 再 cmd+click 到源码看实现。 Three.js 源码风格非常一致,类的层级清晰、命名直白—— 是少数能"读源码学到东西不会被劝退"的开源项目

七、本系列的 10 篇规划

按 "0 → 1 → 精通 + 源码剖析" 的节奏排:

#主题重点
01序章(本篇)全景 + 第一段代码 + 系列地图
02三大件深入:Scene / Camera / Renderer各自参数、坐标系、投影
03Geometry 与 Material 全面拆解BufferGeometry 原理、各种 Material 适用场景
04光照与阴影三种光、阴影贴图、PBR 基础
05动画系统 + 控制器requestAnimationFrame、补间、AnimationMixer、OrbitControls
06加载外部资产GLTF / OBJ / FBX、Draco 压缩、纹理流水线
07着色器入门ShaderMaterial + GLSL、uniforms、内置 chunk 系统
08后处理与特效EffectComposer、辉光、景深、SSAO
09性能优化InstancedMesh、LOD、frustum culling、Drawcall 合批
10源码架构总览仓库目录、渲染管线主流程、和上 9 篇连点成线

每篇都会保持 使用层(怎么写)+ 源码层(为什么这样实现) 两条线并行—— 学完整个系列,你既能做项目,也能在出 bug 时看 Three.js 源码自助调试

八、给你的第一个"作业"

把上面那段 Hello Cube 代码跑起来,然后改三件事:

  1. BoxGeometry 换成 SphereGeometry(1, 32, 32)
  2. MeshNormalMaterial 换成 MeshBasicMaterial({ color: 0x44aa88, wireframe: true })
  3. 在 Animation Loop 里只让它绕 Y 轴慢慢转

跑出效果后,回头看代码—— 你会发现自己已经无意识地理解了"网格 = 几何体 + 材质" 这套抽象。 这就是 Three.js 教学最神奇的地方:你不知不觉就上路了

下一篇 《Three.js(二)三大件深入:Scene / Camera / Renderer 的真正面貌》 会把 Hello Cube 里那 3 个类逐一拆开—— 参数到底有哪些、各种相机怎么选、Renderer 在底层做了什么

一句话总结

Three.js 是把 WebGL 从"博士级 API"压缩成"前端开发可用"的那一层抽象。 学它不是学一个库,是学3D 世界在浏览器里是怎么组装出来的—— 等你看完这 10 篇,你看到任何一个 3D Web 站点都能 F12 拆开它, 知道它用了什么几何体、什么材质、什么光、什么后处理。 这是 Web 时代少数能让你"看穿别人作品"的硬技能之一。

延伸阅读

官方资源(永远以这里为准)

经典书与教程

  • Three.js Essentials, Jos Dirksen —— 老但扎实
  • Discover three.js, Lewy Blue —— 免费在线教程,覆盖到中级
  • Bruno Simon: Three.js Journey —— 付费课程,圈内公认最完整
  • Real-Time Rendering, Akenine-Möller et al. —— 想真正理解 GPU 渲染原理的"圣经"

邻居生态

  • React Three Fiber —— React 写 Three.js,工程上更顺手
  • drei —— R3F 的工程辅助库
  • Theatre.js —— 在浏览器里做动画的可视化工具
  • Blender —— 免费 3D 建模工具,配合 GLTF 导出

站内相关