1. Three.js 基础入门


文档摘要

Three.js 基础入门 Three.js 基础入门 Three.js 是一个流行的 JavaScript 3D 库,它简化了在 Web 浏览器中创建和显示 3D 图形的过程。本文将引导你了解 Three.js 的基础知识,并通过实际代码示例进行演示。 Three.js 的核心概念 在深入代码之前,让我们先了解 Three.js 的几个核心概念: 场景 (Scene): 一个容器,用于存放你想要渲染的所有对象,比如模型、灯光和相机。 相机 (Camera): 定义了观察场景的角度和方式。Three.js 提供了多种相机,例如透视相机 (PerspectiveCamera) 和正交相机 (OrthographicCamera)。 渲染器 (Renderer): 负责将场景渲染到屏幕上。

1. Three.js 基础入门

Three.js 基础入门

Three.js 是一个流行的 JavaScript 3D 库,它简化了在 Web 浏览器中创建和显示 3D 图形的过程。本文将引导你了解 Three.js 的基础知识,并通过实际代码示例进行演示。

1. Three.js 的核心概念

在深入代码之前,让我们先了解 Three.js 的几个核心概念:

  • 场景 (Scene): 一个容器,用于存放你想要渲染的所有对象,比如模型、灯光和相机。

  • 相机 (Camera): 定义了观察场景的角度和方式。Three.js 提供了多种相机,例如透视相机 (PerspectiveCamera) 和正交相机 (OrthographicCamera)。

  • 渲染器 (Renderer): 负责将场景渲染到屏幕上。Three.js 提供了多种渲染器,例如 WebGLRenderer (用于利用 GPU 进行硬件加速渲染) 和 CSS3DRenderer (用于基于 CSS3D 渲染)。

  • 网格 (Mesh): 表示 3D 对象,由几何体 (Geometry) 和材质 (Material) 组成。

  • 几何体 (Geometry): 定义了 3D 对象的形状,例如立方体、球体或自定义形状。

  • 材质 (Material): 定义了 3D 对象的外观,例如颜色、纹理和光泽。

  • 光照 (Light): 照亮场景中的对象,使它们可见。Three.js 提供了多种光照类型,例如环境光 (AmbientLight)、点光源 (PointLight) 和方向光 (DirectionalLight)。

用 Mermaid 画一个简单的概念图:

2. 设置 Three.js 环境

首先,你需要引入 Three.js 库。你可以通过以下几种方式引入:

  • CDN: 在 HTML 文件中添加以下代码:

    <script src="https://cdn.jsdelivr.net/npm/three@0.155.0/build/three.min.js"></script>
  • npm: 如果你使用 Node.js 和 npm,可以安装 Three.js:

    npm install three

    然后在你的 JavaScript 文件中导入 Three.js:

    import * as THREE from 'three';

接下来,创建一个 HTML 文件,用于显示 Three.js 场景:

<!DOCTYPE html> <html> <head> <title>Three.js 基础</title> <style> body { margin: 0; } canvas { display: block; } </style> </head> <body> <script src="main.js"></script> </body> </html>

创建一个 main.js 文件,用于编写 Three.js 代码。

3. 创建一个简单的场景

现在,让我们创建一个简单的场景,包含一个立方体、一个相机和一个渲染器。

import * as THREE from 'three'; // 1. 创建场景 const scene = new THREE.Scene(); // 2. 创建相机 const camera = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000); camera.position.z = 5; // 将相机向后移动,以便看到立方体 // 3. 创建渲染器 const renderer = new THREE.WebGLRenderer(); renderer.setSize(window.innerWidth, window.innerHeight); document.body.appendChild(renderer.domElement); // 4. 创建立方体 const geometry = new THREE.BoxGeometry(); const material = new THREE.MeshBasicMaterial({ color: 0x00ff00 }); // 绿色 const cube = new THREE.Mesh(geometry, material); scene.add(cube); // 5. 渲染循环 function animate() { requestAnimationFrame(animate); // 旋转立方体 cube.rotation.x += 0.01; cube.rotation.y += 0.01; renderer.render(scene, camera); } animate();

代码解释:

  1. 创建场景: new THREE.Scene() 创建了一个新的场景对象。

  2. 创建相机: new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000) 创建了一个透视相机。

    • 75 是视野角度 (field of view)。

    • window.innerWidth / window.innerHeight 是宽高比 (aspect ratio)。

    • 0.11000 是近裁剪面 (near clipping plane) 和远裁剪面 (far clipping plane)。

    • camera.position.z = 5 将相机沿 Z 轴向后移动 5 个单位,以便我们能看到立方体。

  3. 创建渲染器: new THREE.WebGLRenderer() 创建了一个 WebGL 渲染器。

    • renderer.setSize(window.innerWidth, window.innerHeight) 设置渲染器的大小为窗口大小。

    • document.body.appendChild(renderer.domElement) 将渲染器的 DOM 元素添加到 HTML 文档中。

  4. 创建立方体:

    • new THREE.BoxGeometry() 创建了一个立方体几何体。

    • new THREE.MeshBasicMaterial({ color: 0x00ff00 }) 创建了一个基础材质,颜色为绿色。

    • new THREE.Mesh(geometry, material) 创建了一个网格对象,将几何体和材质组合在一起。

    • scene.add(cube) 将立方体添加到场景中。

  5. 渲染循环: animate() 函数是一个循环,它不断地更新场景并渲染它。

    • requestAnimationFrame(animate) 告诉浏览器在下次重绘之前调用 animate() 函数。

    • cube.rotation.x += 0.01; cube.rotation.y += 0.01; 旋转立方体。

    • renderer.render(scene, camera) 使用相机渲染场景。

打开 HTML 文件,你将会看到一个旋转的绿色立方体。

4. 使用不同的材质

MeshBasicMaterial 是一种简单的材质,它不受光照影响。Three.js 提供了许多其他材质,例如:

  • MeshLambertMaterial: 对光照有反应,但计算效率较高。

  • MeshPhongMaterial: 对光照有更逼真的反应,但计算量更大。

  • MeshStandardMaterial: 基于物理的渲染 (PBR) 材质,提供更真实的光照效果。

让我们将立方体的材质更改为 MeshPhongMaterial 并添加一个光源:

import * as THREE from 'three'; // ... (之前的代码) // 4. 创建立方体 const geometry = new THREE.BoxGeometry(); const material = new THREE.MeshPhongMaterial({ color: 0x00ff00, specular: 0xffffff, shininess: 30 }); // 绿色,具有高光 const cube = new THREE.Mesh(geometry, material); scene.add(cube); // 5. 添加光源 const light = new THREE.PointLight(0xffffff, 1, 100); // 白色点光源 light.position.set(0, 0, 5); // 将光源放在相机的位置 scene.add(light); // 6. 渲染循环 function animate() { requestAnimationFrame(animate); // 旋转立方体 cube.rotation.x += 0.01; cube.rotation.y += 0.01; renderer.render(scene, camera); } animate();

代码解释:

  • new THREE.MeshPhongMaterial({ color: 0x00ff00, specular: 0xffffff, shininess: 30 }) 创建了一个 MeshPhongMaterial,颜色为绿色,具有白色高光和 30 的光泽度。

  • new THREE.PointLight(0xffffff, 1, 100) 创建了一个白色点光源,强度为 1,距离为 100。

  • light.position.set(0, 0, 5) 将光源放在相机的位置。

现在,你将会看到一个具有高光的绿色立方体。

5. 控制相机

你可以使用鼠标或键盘来控制相机。以下是一个使用鼠标控制相机的简单示例,使用 OrbitControls

首先,安装 OrbitControls

npm install three @types/three

然后,在你的 JavaScript 文件中导入 OrbitControls

import * as THREE from 'three'; import { OrbitControls } from 'three/examples/jsm/controls/OrbitControls'; // ... (之前的代码) // 5. 创建 OrbitControls const controls = new OrbitControls(camera, renderer.domElement); controls.enableDamping = true; // 启用阻尼,使相机移动更平滑 controls.dampingFactor = 0.05; // 6. 添加光源 const light = new THREE.PointLight(0xffffff, 1, 100); // 白色点光源 light.position.set(0, 0, 5); // 将光源放在相机的位置 scene.add(light); // 7. 渲染循环 function animate() { requestAnimationFrame(animate); // 旋转立方体 cube.rotation.x += 0.01; cube.rotation.y += 0.01; controls.update(); // 更新 OrbitControls renderer.render(scene, camera); } animate();

代码解释:

  • import { OrbitControls } from 'three/examples/jsm/controls/OrbitControls'; 导入 OrbitControls

  • const controls = new OrbitControls(camera, renderer.domElement) 创建一个 OrbitControls 对象,将相机和渲染器的 DOM 元素传递给它。

  • controls.enableDamping = true; controls.dampingFactor = 0.05; 启用阻尼,使相机移动更平滑。

  • controls.update() 在渲染循环中更新 OrbitControls

现在,你可以使用鼠标拖动来旋转相机,使用鼠标滚轮来缩放相机。

6. 加载外部模型

Three.js 允许你加载外部模型,例如 glTF 模型。首先,你需要一个 glTF 模型文件。你可以从 Sketchfab 或其他资源网站下载一个。

然后,使用 GLTFLoader 加载模型:

import * as THREE from 'three'; import { GLTFLoader } from 'three/examples/jsm/loaders/GLTFLoader'; import { OrbitControls } from 'three/examples/jsm/controls/OrbitControls'; // ... (之前的代码) // 5. 创建 GLTFLoader const loader = new GLTFLoader(); // 6. 加载模型 loader.load('path/to/your/model.gltf', function (gltf) { scene.add(gltf.scene); // 将模型添加到场景中 // 可选:调整模型的位置和缩放 gltf.scene.scale.set(0.1, 0.1, 0.1); gltf.scene.position.set(0, -1, 0); }, undefined, function (error) { console.error(error); }); // 7. 创建 OrbitControls const controls = new OrbitControls(camera, renderer.domElement); controls.enableDamping = true; // 启用阻尼,使相机移动更平滑 controls.dampingFactor = 0.05; // 8. 添加光源 const light = new THREE.PointLight(0xffffff, 1, 100); // 白色点光源 light.position.set(0, 0, 5); // 将光源放在相机的位置 scene.add(light); // 9. 渲染循环 function animate() { requestAnimationFrame(animate); controls.update(); // 更新 OrbitControls renderer.render(scene, camera); } animate();

代码解释:

  • import { GLTFLoader } from 'three/examples/jsm/loaders/GLTFLoader'; 导入 GLTFLoader

  • const loader = new GLTFLoader(); 创建一个 GLTFLoader 对象.

  • loader.load('path/to/your/model.gltf', function (gltf) { ... }) 加载 glTF 模型。

    • 'path/to/your/model.gltf' 是你的 glTF 模型的路径。

    • function (gltf) { ... } 是加载完成后的回调函数。

      • gltf.scene 是模型的场景。

      • scene.add(gltf.scene) 将模型的场景添加到主场景中。

      • gltf.scene.scale.set(0.1, 0.1, 0.1) 将模型缩小到原来的 1/10。

      • gltf.scene.position.set(0, -1, 0) 将模型向下移动 1 个单位。

    • undefined 是加载过程中的回调函数 (可选)。

    • function (error) { console.error(error); } 是加载失败后的回调函数。

请记住将 'path/to/your/model.gltf' 替换为你实际的 glTF 模型文件的路径。

7. 总结

本文介绍了 Three.js 的基本概念和用法,包括场景、相机、渲染器、网格、几何体、材质、光照和相机控制。通过实际的代码示例,你学习了如何创建一个简单的 Three.js 场景,如何使用不同的材质,如何控制相机,以及如何加载外部模型。

这只是 Three.js 的冰山一角。你可以继续探索 Three.js 的文档和示例,学习更多高级功能,例如着色器、动画和物理引擎。祝你学习愉快!


作者与出处
原作者: 灏天文库
来源:灏天文库
整理: 灏天文库整理
由灏天文库平台收录,内容或由平台用户上传,仅供学习交流
发布者: 作者: 灏天文库 转发
评论区 (0)
U