使用 Three.js 载入 3D 模型(Loading 3D Models)

person 少陵野老    watch_later 2024-10-11 22:53:49
visibility 42    class Loading 3D Models    bookmark 专栏

在 Three.js 中,载入和展示 3D 模型是创建交互式三维场景的关键步骤。无论是游戏、虚拟现实应用还是数据可视化,能够灵活地载入和操作 3D 模型都是至关重要的。本文将详细介绍如何使用 Three.js 载入 3D 模型,包括不同的格式、常用的加载器,以及一些高级用法和示例代码。

1. 3D 模型格式

Three.js 支持多种 3D 模型格式,包括但不限于:

  • OBJ:一种常见的模型格式,适合静态模型。
  • FBX:通常用于动画和复杂模型。
  • GLTF/GLB:一种现代的高效格式,支持动画、纹理和材质,推荐使用。
  • Collada (DAE):较为复杂的格式,支持多种功能。

在本文中,我们将主要使用 GLTF 格式,因为它是 Three.js 推荐的格式。

2. 准备工作

2.1 安装 Three.js

确保你在项目中引入了 Three.js 和所需的加载器。以下是基本的 HTML 结构:

<!DOCTYPE html>
<html lang="zh">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Three.js 载入 3D 模型示例</title>
    <script src="https://cdnjs.cloudflare.com/ajax/libs/three.js/r128/three.min.js"></script>
    <script src="https://cdnjs.cloudflare.com/ajax/libs/three.js/r128/examples/js/loaders/GLTFLoader.js"></script>
    <style>
        body { margin: 0; }
        canvas { display: block; }
    </style>
</head>
<body>

2.2 创建基本场景

<script> 标签中,设置基本的 Three.js 场景、摄像机和渲染器:

const scene = new THREE.Scene();
const camera = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000);
const renderer = new THREE.WebGLRenderer();
renderer.setSize(window.innerWidth, window.innerHeight);
document.body.appendChild(renderer.domElement);

camera.position.z = 5;

3. 载入 GLTF 模型

3.1 使用 GLTFLoader

要载入 GLTF 模型,我们需要使用 GLTFLoader。以下是载入模型的步骤:

const loader = new THREE.GLTFLoader();
loader.load('path/to/model.glb', (gltf) => {
    scene.add(gltf.scene);
}, undefined, (error) => {
    console.error(error);
});

3.2 处理模型

加载完成后,我们可以对模型进行各种操作,比如调整位置、缩放、旋转等。例如:

loader.load('path/to/model.glb', (gltf) => {
    const model = gltf.scene;
    model.position.set(0, 0, 0); // 设置位置
    model.scale.set(1, 1, 1); // 设置缩放
    model.rotation.set(0, Math.PI / 2, 0); // 设置旋转
    scene.add(model);
}, undefined, (error) => {
    console.error(error);
});

4. 渲染场景

在动画循环中渲染场景:

function animate() {
    requestAnimationFrame(animate);
    renderer.render(scene, camera);
}

animate();

4.1 处理窗口大小变化

确保在窗口大小变化时调整摄像机和渲染器的大小:

window.addEventListener('resize', () => {
    camera.aspect = window.innerWidth / window.innerHeight;
    camera.updateProjectionMatrix();
    renderer.setSize(window.innerWidth, window.innerHeight);
});

5. 完整示例代码

以下是一个完整的示例代码,展示了如何在 Three.js 中载入和渲染 GLTF 模型:

<!DOCTYPE html>
<html lang="zh">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Three.js 载入 3D 模型示例</title>
    <script src="https://cdnjs.cloudflare.com/ajax/libs/three.js/r128/three.min.js"></script>
    <script src="https://cdnjs.cloudflare.com/ajax/libs/three.js/r128/examples/js/loaders/GLTFLoader.js"></script>
    <style>
        body { margin: 0; }
        canvas { display: block; }
    </style>
</head>
<body>
    <script>
        const scene = new THREE.Scene();
        const camera = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000);
        const renderer = new THREE.WebGLRenderer();
        renderer.setSize(window.innerWidth, window.innerHeight);
        document.body.appendChild(renderer.domElement);

        camera.position.z = 5;

        const loader = new THREE.GLTFLoader();
        loader.load('path/to/model.glb', (gltf) => {
            const model = gltf.scene;
            model.position.set(0, 0, 0);
            model.scale.set(1, 1, 1);
            model.rotation.set(0, Math.PI / 2, 0);
            scene.add(model);
        }, undefined, (error) => {
            console.error(error);
        });

        function animate() {
            requestAnimationFrame(animate);
            renderer.render(scene, camera);
        }

        animate();

        window.addEventListener('resize', () => {
            camera.aspect = window.innerWidth / window.innerHeight;
            camera.updateProjectionMatrix();
            renderer.setSize(window.innerWidth, window.innerHeight);
        });
    </script>
</body>
</html>

6. 添加灯光和阴影

6.1 添加光源

为了使模型看起来更真实,建议添加光源:

const ambientLight = new THREE.AmbientLight(0xffffff, 0.5); // 环境光
scene.add(ambientLight);

const directionalLight = new THREE.DirectionalLight(0xffffff, 1); // 平行光
directionalLight.position.set(5, 5, 5).normalize();
scene.add(directionalLight);

6.2 启用阴影

如果你的模型支持阴影,可以启用阴影效果:

renderer.shadowMap.enabled = true;
directionalLight.castShadow = true;

7. 处理动画

如果模型包含动画,GLTFLoader 也会加载这些动画。我们可以通过 AnimationMixer 来播放动画:

const mixer = new THREE.AnimationMixer(gltf.scene);
gltf.animations.forEach((clip) => {
    mixer.clipAction(clip).play();
});

// 在动画循环中更新混合器
function animate() {
    requestAnimationFrame(animate);
    if (mixer) mixer.update(0.01); // 更新动画
    renderer.render(scene, camera);
}

8. 结论

在本博客中,我们详细探讨了如何在 Three.js 中载入和渲染 3D 模型,包括使用 GLTFLoader 加载 GLTF 模型、添加灯光和阴影、处理动画等。通过这些示例,你可以在自己的项目中灵活地使用 3D 模型,提升用户体验。希望本博客能够帮助你更好地理解和使用 Three.js。如果有任何问题或建议,欢迎在评论区留言讨论!

评论区
评论列表
menu