Three.js基礎知識と基本構造

こんにちは、タクゾウです。

今回は、WebGLを扱いやすくしたThree.jsについて紹介致します。

自分の勉強を兼ねて、Three.jsの基礎を詳しく書いていくので、
Web上で3D表現をしたい人の参考になれば幸いです。

Three.jsとは?

three.jsとは、Ricardo Cabello(Mr.doob)氏によって開発されたWebGLの実装を簡易程にすることが可能なライブラリです。(3DWebのJQuery的な存在)
three.jsを利用することにより、ピュアなWebGLの実装の約30%ほどの記述で書くことができます。
また、ドキュメントや、記事も多く出ているので比較的簡単にWebGLを利用できます。実際になにができるかについては公式サイトを参考にしてください。
参考 three.js - Javascript 3D librarythree.js - Javascript 3D library

thee.jsを使うメリット

  • 手軽に、かつ効率的に WebGL を記述できる
  • 多彩で強力な機能を持ち拡張もできる
  • 情報が(比較的)豊富にある
  • 日本語で解説されていることも多いがバージョンの違いには注意
  • 現在も活発に開発が続いている

three.jsを使うデメリット

  • three.js の流儀に従う必要がある
  • パフォーマンスや柔軟性もピュア WebGL に 比べれば 低くなる
  • ややファイル容量が大きめ
  • バージョンアップに追従するのが大変
  • 成果物の見た目が似通う
  • 3Dプログラムの理解がなくてもできてしまう。

上記のようなメリット・デメリットがありますが、メリッドの方が大きいので使わない理由はあまりないです。

Thee.jsの基本構造

一番基本的な構造はこちらになります。
コメントを多めにしているので参考にして下さい。

参考 Three.js 基本構造 DEMOThree.js 基本構造 DEMO
HTML
<!DOCTYPE html>
<html>
    <head>
        <script src="../lib/three_90.js"></script>
        <script src="script.js"></script>
        <style>
            * {margin: 0; padding: 0;}
            html, body {
                overflow: hidden;
            }
        </style>
    </head>
    <body>
        <div id="webgl"></div>
    </body>
</html>

JavaScript
// = base ======================================================================
// three.js サンプルの雛形。
// ============================================================================

// グローバル空間を汚染しないように、無名関数で全体を囲んでおく
(() => {
    // ブラウザによる HTML のパースが終わってから初期化を開始するためにイベント
    // リスナーを使って初期化処理が開始されるようにする
    window.addEventListener('load', () => {

        // - 宣言・定義フェーズ -----------------------------------------------
        // まず最初に変数の宣言と、必要に応じた定義処理を行なっていきます。
        // 3D 系の実装を行うときに限りませんが、設定すべき項目が多岐に渡る場合は
        // できる限り「初期値を決める場所」は冒頭に集約させましょう。
        // これを好き勝手に、自由なタイミングで行うようにしてしまうと、後から自
        // 分がソースコードを見直した際に、どこでなにを定義しているのか把握する
        // のが難しくなります。
        // --------------------------------------------------------------------

        // 初期値を決める場所は冒頭にまとめた方がいい
        // 汎用変数の宣言
        let width = window.innerWidth;   // ブラウザのクライアント領域の幅
        let height = window.innerHeight; // ブラウザのクライアント領域の高さ
        let targetDOM = document.getElementById('webgl'); // スクリーンとして使う DOM

        // three.js 定義されているオブジェクトに関連した変数を宣言
        let scene;    // シーン
        let camera;   // カメラ
        let renderer; // レンダラ
        let geometry; // ジオメトリ
        let material; // マテリアル
        let box;      // ボックスメッシュ

        //大文字で宣言されている場所は定数でconstで宣言する
        // 各種パラメータを設定するために定数オブジェクトを定義
        // ※各パラメータの意味は別途説明しますので、まずは気にせずで OK
        const CAMERA_PARAM = { // カメラに関するパラメータ
            fovy: 60,
            aspect: width / height,
            near: 0.1,
            far: 10.0,
            x: 0.0,
            y: 2.0,
            z: 5.0,
            lookAt: new THREE.Vector3(0.0, 0.0, 0.0)
        };
        const RENDERER_PARAM = { // レンダラに関するパラメータ
            clearColor: 0xFFFFFF,
            width: width,
            height: height
        };
        const MATERIAL_PARAM = { // マテリアルに関するパラメータ
            color: 0x5CAC80
        };

        // - 初期化フェーズ ---------------------------------------------------
        // 変数の宣言や定義が済んだら、次に必要なオブジェクトのインスタンス化を
        // 行なっていきます。
        // three.js には多数の組み込みオブジェクトが用意されており、これらを通し
        // て様々な処理を行っていきます。この初期化フェーズではそれらを実際にイ
        // ンスタンス化しながら、必要な設定などを適宜行なっていきます。
        // --------------------------------------------------------------------

        // . シーンの初期化 ...................................................
        // Scene とは、その名のとおり 3D シーンを管理するためのものです。
        // たとえばこのシーンにはどんなオブジェクトを使うのか、であったり、ある
        // いはどんなカメラを使って撮影を行うのかなど、3D 空間全体の情報をまとめ
        // て持っているのが Scene オブジェクトです。
        //3D空間全体のことをscene 撮影する空間のこと。
        // ....................................................................
        scene = new THREE.Scene();

        // . カメラの初期化 ...................................................
        // three.js におけるカメラは、現実世界のカメラと同じように空間を撮影する
        // ために使います。
        // 現実のカメラがそうであるように、カメラの性能や、あるいは性質によって、
        // 最終的に描かれる世界はまったく違ったものになります。
        // カメラに限らず、設定しているパラメータの詳細については別途解説します。
        //望遠なのか、パノラマなのか、それと同じように3D空間に作成するカメラの性能をきめる
        // ....................................................................
        camera = new THREE.PerspectiveCamera(
            CAMERA_PARAM.fovy,
            CAMERA_PARAM.aspect,
            CAMERA_PARAM.near,
            CAMERA_PARAM.far
        );
        camera.position.x = CAMERA_PARAM.x;
        camera.position.y = CAMERA_PARAM.y;
        camera.position.z = CAMERA_PARAM.z;
        camera.lookAt(CAMERA_PARAM.lookAt);


        // . レンダラの初期化 .................................................
        // レンダラ、という言葉はフロントエンドではあまり見聞きしない言葉ですね。
        // わかりやすく言うなら、レンダラとは「現像する人」です。カメラが撮影し
        // たフィルムを、現像してスクリーンに映してくれるわけです。
        // レンダラという言葉自体は three.js に独特なものではありませんが、一般
        // 的なレンダラと three.js のレンダラは、ちょっとだけ意味合いが違うので
        // 間違った覚え方をしないように気をつけましょう。
        //theree.js用のレンダラを使用(一般の3Dで使うレンダラと違うので注意)
        // ....................................................................
        renderer = new THREE.WebGLRenderer();
        renderer.setClearColor(new THREE.Color(RENDERER_PARAM.clearColor));
        renderer.setSize(RENDERER_PARAM.width, RENDERER_PARAM.height);
        targetDOM.appendChild(renderer.domElement);

        // . ジオメトリとマテリアルの初期化 ...................................
        // ジオメトリとは、3D シーンを描くために使う「頂点」の集合体です。
        // もっと言うと、ジオメトリとは「単なる形状」であり、言うなれば設計図の
        // ようなものですね。
        // これにどのような色を塗るであるとか、どのような質感の材質を使うである
        // とか、そういったことは「マテリアル」が決めます。
        // ....................................................................
        geometry = new THREE.BoxGeometry(1.0, 1.0, 1.0);
        material = new THREE.MeshBasicMaterial(MATERIAL_PARAM);

        // . メッシュの初期化 .................................................
        // three.js では、ジオメトリとマテリアルを別々に生成し組み合わせることで
        // 3D 空間に置くことができるメッシュオブジェクトを定義できます。
        // ....................................................................
        box = new THREE.Mesh(geometry, material);

        // - 描画フェーズ -----------------------------------------------------
        // さていよいよ描画です。
        // 描画を行うためには、必要なオブジェクトをまず「シーンに追加」したあと、
        // そのシーンをレンダラで「スクリーンに描画」します。
        // --------------------------------------------------------------------

        // シーンにボックスメッシュを追加する
        scene.add(box);

        // レンダーメソッドを読んだ時に初めて、描画される。
        // レンダラにシーンとカメラを渡して描画させる
        renderer.render(scene, camera);
    }, false);
})();

まとめ

Three.jsいじってみましたが、やっぱり楽しい!!
WebGLはかなり敷居が高いですが、Three.jsを使うとすぐ表示ができちゃいます。
まずは、Three.jsで用語や3D表現する上でのイメージを掴みつつピュアなWebGLの勉強して行きたいと思います。

3Dプログラムの知識もそうですが、JavaScriptの根本的な知識も必要とされるので、
初心者の自分にとってはとても勉強になります。

次回はこの基礎構造をカスタマイズして、Key Visualに使われそうな表示をしてみようと思います。

コメントを残す

メールアドレスが公開されることはありません。 * が付いている欄は必須項目です

CAPTCHA