圧縮されたglTF(.glb)ファイルをLoadして表示(Threejs)

この記事は約8分で読めます。

スポンサーリンク

やりたいこと

圧縮されたglTF(.glb)ファイルをThreejsを読み込む。

圧縮方法は↓

保存するglTF(.glb)ファイルのファイルサイズを小さくする(Blender)
やりたいこと下の記事で紹介した通り、BlenderでglTF(.glb)ファイルを保存することができますが、形状が複雑になればファイルサイズは大きくなりWEBで読み込む際などにロード時間が遅くなります。ここでは保存されるg...
スポンサーリンク

環境

Threejs: r150

Chrome: 111.0.5563.65

スポンサーリンク

準備

圧縮なしのソースおよび環境の準備は↓の記事を参考にしてください。

スポンサーリンク

DRACOLoaderを用いた読み込み

フォルダ構成

フォルダ構成は以下の通りです。

dice‐c.glbが読み込み対象の圧縮されたglTFファイルです。

DRACOLoader.jsファイル、dracoフォルダを追加しています。ともにThreejsに含まれるファイルです。

ROOT
|   dice-c.glb
|   index.html
|
\---js
    +---libs
    |   |   3d.js
    |   |   DRACOLoader.js    ///追加 元ファイル (three.js\examples\jsm\loaders¥DRACOLoader.js)
    |   |   GLTFLoader.js //元ファイル (three.js\examples\jsm\loaders¥GLTFLoader.js)
    |   |   three.module.js //元ファイル (three.js\build\three.module.js)
    |   |
    |   \---draco         ///追加 元ファイル (threejs\three.js\examples\jsm\libs\draco)
    |       |   draco_decoder.js
    |       |   draco_decoder.wasm
    |       |   draco_encoder.js
    |       |   draco_wasm_wrapper.js
    |       |   README.md
    |       |
    |       \---gltf
    |               draco_decoder.js
    |               draco_decoder.wasm
    |               draco_encoder.js
    |               draco_wasm_wrapper.js
    |
    \---utils
            BufferGeometryUtils.js //元ファイル (three.js\examples\jsm\utils¥BufferGeometryUtils.js)

HTML

フォルダ構成のindex.htmlは以下のように記述します。

前回から変更はありません。

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">

</head>
<body>
    <canvas id="canvas1" width=600 height=600></canvas>
    <script type="importmap">{"imports": {"three": "./js/libs/three.module.js"}}</script>
    <script type="module" src="./js/libs/3d.js"></script>
</body>
</html>

JavaScript

3d.jsの中身は以下の通りです。

import * as THREE from 'three';
import { GLTFLoader } from './GLTFLoader.js';
import { DRACOLoader } from './DRACOLoader.js'; ///追加

let renderer;
let scene;
let camera;

scene = new THREE.Scene();
const canvas = document.querySelector("#canvas1");
renderer = new THREE.WebGLRenderer({ canvas: canvas });

const width = canvas.width;
const height = canvas.height;
renderer.setSize(width, height);

setupCamera();
loadObjects(scene, "./dice-c.glb");
setupLights(scene);

function setupCamera() {
	const canvas = document.querySelector("#canvas1");
	const width = canvas.width;
	const height = canvas.height;

	camera = new THREE.PerspectiveCamera(45, width / height, 0.1, 3000);
	camera.position.set(4, 4, 4);
	camera.lookAt(new THREE.Vector3(0, 0, 0));
}

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

function setupLights(scene) {
	let ambientLight = new THREE.AmbientLight(0xffffff);
	ambientLight.intensity = 1;
	scene.add(ambientLight);
}

function loadObjects(scene, path) {
	const loader = new GLTFLoader();
///ここから追加
	const dracoLoader = new DRACOLoader();
	dracoLoader.setDecoderPath('./js/libs/draco/');
	loader.setDRACOLoader(dracoLoader);

///ここまで追加

	loader.load(path, function (gltf) {
		let box = gltf.scene;
		scene.add(box);
		requestAnimationFrame(render);
	}, undefined, function (e) {
		console.error(e);
	});
}

圧縮された.glbファイルを読み込むための処理は以下の通りです。ほかの個所は前回と同様です。

import { DRACOLoader } from './DRACOLoader.js';

圧縮された.glbファイルを読み込むためのLoaderをインポートします。

	const dracoLoader = new DRACOLoader();
	dracoLoader.setDecoderPath('./js/libs/draco/');
	loader.setDRACOLoader(dracoLoader);

DRACOLoaderを作成してGLTFLoaderにセットします。

setDecoderPathで指定するパスはdracoフォルダへのhtmlからのパスです。

結果

圧縮されたdice-c.glbを読み込んで表示することができました。

エラーメッセージ

対応せずに圧縮されたglTFファイルをロードすると以下のエラーがログされます。

3d.js:47 Error: THREE.GLTFLoader: No DRACOLoader instance provided.
    at new GLTFDracoMeshCompressionExtension (GLTFLoader.js:1730:10)
    at GLTFLoader.parse (GLTFLoader.js:380:37)
    at Object.onLoad (GLTFLoader.js:218:11)
    at three.module.js:40715:38

dracoLoader.setDecoderPath(‘./js/libs/draco/’);の引数が間違えていると以下のエラーがログされます。

xxxxxxxxxxxxxxは環境により異なります。

three.module.js:40577          GET file:///xxxxxxxxxxxxxx/js/libs/draco/draco_wasm_wrapper.js net::ERR_FILE_NOT_FOUND
three.module.js:40577          GET file:///xxxxxxxxxxxxxx/js/libs/draco/draco_decoder.wasm net::ERR_FILE_NOT_FOUND
3three.module.js:40577          Uncaught (in promise) TypeError: Failed to fetch
    at FileLoader.load (three.module.js:40577:3)
    at DRACOLoader.js:251:11
    at new Promise (<anonymous>)
    at DRACOLoader._loadLibrary (DRACOLoader.js:249:10)
    at DRACOLoader._initDecoder (DRACOLoader.js:278:32)
    at DRACOLoader.preload (DRACOLoader.js:259:8)
    at new GLTFDracoMeshCompressionExtension (GLTFLoader.js:1737:20)
    at GLTFLoader.parse (GLTFLoader.js:380:37)
    at Object.onLoad (GLTFLoader.js:218:11)
    at three.module.js:40715:38
スポンサーリンク

参考にさせていただいたサイト

Three.js – JavaScript 3D Library
スポンサーリンク

関係するページ

Blenderで作成した3DオブジェクトをThreejsで読込、表示するまとめ

コメント

タイトルとURLをコピーしました