株式会社デジタル・フロンティア-Digital Frontier

Header

Main

  • TOP
  • DF TALK
  • [WebGL入門] javascriptを使って3Dプログラミングをやってみる

[WebGL入門] javascriptを使って3Dプログラミングをやってみる

2014/7/16

Tag: ,

久しぶりの投稿になります。TDの田辺です。

前回に引き続き、web関連について書きたいと思います。

今回挑戦するのは、題名の通り 「WebGL」 です。

WebGL とは

Webブラウザで3次元グラフィックス(3DCG)を高速に表示するための仕様の一つ。
Webページ上に記述されたスクリプトからOpenGLを利用して高速な3D描画を実現する技術で、
OSやコンピュータのビデオ機能(ビデオカードやCPU内蔵ビデオ)がOpenGLに対応している必要がある。

WebGLはJavaScriptの拡張として提供され、HTMLのCanvasタグで定義されたページ上の領域に動的に
3次元グラフィックスを描画することができる。
ブラウザが本来持つJavaScriptの機能と組み合わせて、3DCGを利用したコンテンツを作成することができる。

業界団体のKhronos Groupが標準を策定しており、Google ChromeやFirefox、
Internet Explorer 11以降などで利用できる。

e-wordsより引用)

■WebGLのデモが載っているサイト
 Web ブラウザで動くとは思えない、凄い WebGL デモ・アプリ 65 個
 WebGLのデモ

要約すると、WebGLを使用することでブラウザ上で3D表現が出来るというわけです。すごいですね!

しかし、WebGLを使用するためには openGLshading の言語を理解していなければならず、
そのため、手軽には使えません。。

そこで、WebGLを簡単に使用するために three.js というものを使います。

three.js とは

HTML5でリッチなゲームなどを作る際に活用が期待される、WebGLをサポートした3D描画ライブラリです。
OpenGL独特の使いにくさがあるWebGLをラッピングしており、
JavaScript開発者にとって直感的に使いやすくなっています。
またWebGL非サポート環境用としてCanvasやSVGでのレンダリングも可能で、
WebGLまたはWebでの3D表現の入門用にはうってつけのライブラリといえます。

Naverまとめより引用)

three.js公式サイト

WebGLのjavascriptライブラリには、他にも Away3D.jsBabylon.js などがあるのですが、
今回は、その中でも特に人気のある three.js を使って、WebGLに挑戦してみます。

準備

■対応しているブラウザ
 Google Chrome 8 (8は要設定、9から標準で有効)
 Internet Explorer 11
 Mozilla Firefox 4
 Opera 12 (12は要設定、15から標準で有効)
 Safari 5.1 (要設定)

 ※OpenGL 2.x 世代はウェブブラウザ側で強制的に利用する設定をしないと WebGL は利用できないそうです。

■「dftalk」フォルダ(作業フォルダ)
 どこでも良いので、dftalk という名前でフォルダを作成しましょう。
 この後の作業は、このフォルダの中で行います。

■three.js
 公式サイト からダウンロードできます。
 メニューの download から、 zipファイル をダウンロードしましょう。

 ファイルを解凍したら、必要なライブラリ本体は buildフォルダ 内に 「three.min.js」 として配置されているので、
 先ほど作成した 「dftalk」フォルダ の中に 「three.min.js」 を入れましょう。

■OrbitControls.js
 マウスでカメラの視点移動を行うために必要なスクリプトです。
 three.jsを取得する際にダウンロードしたzipファイル内の

 examples\js\controls\OrbitControls.js

 に配置されているので、先程と同じく 「dftalk」フォルダ に入れましょう。
 

実際にthree.jsを使ってみる

では、早速作業に入ります。

まず、HTMLファイル の作成と three.js のインポートをします。
下記のコードをテキストディタで書いて、「index.html」 という名前で
「dftalk」 フォルダの中に作成しましょう。

<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>DF_Talk three.js サンプル</title>
</head>

<body>

    <!-- three.jsを読み込む -->
    <script type="text/javascript" src="three.min.js"></script>

    <script>
        // ここにコードを書いていきます。
    </script>

</body>
</html>

■ シーンを作成する

続いて、シーンを作成します。
先ほど作成したHTMLファイル内の 「ここにコードを書いていきます」 と書いた行の下に
下記のコードを書きます。

// ここにコードを書いていきます。
// シーンの作成 ------------------------------------------
var scene = new THREE.Scene();

■ カメラを作成する

次にシーンの状態を撮影するためのカメラを作成します。
シーン作成のコードの下に書きます。

// ここにコードを書いていきます。
// シーンの作成 ------------------------------------------
var scene = new THREE.Scene();

// カメラの作成 ------------------------------------------
// fov: 画角(視野角)
var fov = 75;

var height = 600; // 縦幅
var width = 400; // 横幅
// aspect: アスペクト比、カメラで撮影したものの縦横比
var aspect = height/width;

// near: ニアークリップ、 カメラからの撮影開始位置、これより近いものは撮影しない
var near = 1;
// far: ファークリップ カメラからの撮影終了位置、これより遠いものは撮影しない
var far = 1000;

// カメラ作成
var camera = new THREE.PerspectiveCamera(fov, aspect, near, far);
// カメラ配置
camera.position.set(0, 0, 70); // (x, y, z)

■ レンダラーの追加

次にレンダラーの追加をします。
ここでようやく、HTMLとの紐付けがされます。
カメラの作成部分のコードの下に書きます。

// カメラ作成
var camera = new THREE.PerspectiveCamera(fov, aspect, near, far);
// カメラ配置
camera.position.set(0, 0, 70); // (x, y, z)

// レンダラーの追加 ----------------------------------------
var renderer = new THREE.WebGLRenderer();
renderer.setSize(height, width); // Canvasのサイズ設定
document.body.appendChild(renderer.domElement);

■ ライティングを設定する

次にライティングを設定します。
レンダラーの追加部分のコードの下に書きます。

// レンダラーの追加 ----------------------------------------
var renderer = new THREE.WebGLRenderer();
renderer.setSize(height, width); // Canvasのサイズ設定
document.body.appendChild(renderer.domElement);

// ライティングを設定する ------------------------------------------
var color = 'white'; // 光の色
// ライトオブジェクトの作成
var directionalLight = new THREE.DirectionalLight(color);
directionalLight.position.set(0, 7, 10); // 光源の角度を設定
scene.add(directionalLight); // シーンに追加

■ 物体を追加する

次に物体を追加します。
今回は、立方体を追加しようと思います。
ライティングの設定の下に書きます。

// ライティングを設定する ------------------------------------------
var color = 'white'; // 光の色
// ライトオブジェクトの作成
var directionalLight = new THREE.DirectionalLight(color);
directionalLight.position.set(0, 7, 10); // 光源の角度を設定
scene.add(directionalLight); // シーンに追加

// 物体を追加する ----------------------------------------
// ジオメトリーの作成
var geometry = new THREE.CubeGeometry(20, 20, 20); // サイズ設定(x, y, z)
// マテリアルの作成
var material = new THREE.MeshPhongMaterial({color: 'orange'});
// メッシュの作成
cube = new THREE.Mesh(geometry, material);
cube.position.set(0, 0, 0);  // 位置を設定(x, y, z)
scene.add(cube); // シーンに追加

■ レンダリングする

ここまで出来たらレンダリングしてみたいと思います。
物体の追加部分のコードの下に下記のように render関数の定義と、
関数呼び出し部分を書きます。

// 物体を追加する ----------------------------------------
// ジオメトリーの作成
var geometry = new THREE.CubeGeometry(20, 20, 20); // サイズ設定(x, y, z)
// マテリアルの作成
var material = new THREE.MeshPhongMaterial({color: 'orange'});
// メッシュの作成
cube = new THREE.Mesh(geometry, material);
cube.position.set(0, 0, 0);  // 位置を設定(x, y, z)
scene.add(cube); // シーンに追加

// レンダリング ----------------------------------------
function render() {
  // シーンとカメラを渡してレンダリング
  renderer.render(scene, camera);
}
render();

コードが書けたら、HTMLファイルをブラウザで開いてみましょう。

画像のようにオレンジ色の正方形が表示されたでしょうか。

サンプル

■ ここまでのコード

<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>DFTALK three.js サンプル</title>
</head>

<body>

    <!-- three.jsを読み込む -->
    <script type="text/javascript" src="three.min.js"></script>

    <script>
        // ここにコードを書いていきます。
        // シーンの作成 ------------------------------------------
        var scene = new THREE.Scene();

        // カメラの作成 ------------------------------------------
        // fov: 画角(視野角)
        var fov = 75;

        var height = 600; // 縦幅
        var width = 400; // 横幅
        // aspect: アスペクト比、カメラで撮影したものの縦横比
        var aspect = height/width;

        // near: ニアークリップ、 カメラからの撮影開始位置、これより近いものは撮影しない
        var near = 1;
        // far: ファークリップ カメラからの撮影終了位置、これより遠いものは撮影しない
        var far = 1000;

        // カメラ作成
        var camera = new THREE.PerspectiveCamera(fov, aspect, near, far);
        // カメラ配置
        camera.position.set(0, 0, 70); // (x, y, z)

        // レンダラーの追加 ----------------------------------------
        var renderer = new THREE.WebGLRenderer();
        renderer.setSize(height, width); // Canvasのサイズ設定
        document.body.appendChild(renderer.domElement);

        // ライティングを設定する ------------------------------------
        var color = 'white'; // 光の色
        // ライトオブジェクトの作成
        var directionalLight = new THREE.DirectionalLight(color);
        directionalLight.position.set(0, 7, 10); // 光源の角度を設定
        scene.add(directionalLight); // シーンに追加

        // 物体を追加する ----------------------------------------
        // ジオメトリーの作成
        var geometry = new THREE.CubeGeometry(20, 20, 20); // x, y, z
        // マテリアルの作成
        var material = new THREE.MeshPhongMaterial({color: 'orange'});
        // メッシュの作成
        cube = new THREE.Mesh(geometry, material);
        cube.position.set(0, 0, 0); // 位置を設定(x, y, z)
        scene.add(cube); // シーンに追加

        // レンダリング ----------------------------------------
        function render() {
          // シーンとカメラを渡してレンダリング
          renderer.render(scene, camera);
        }
        render();

    </script>

</body>
</html>

■ 立方体を回転させる

今の状態では平面にしか見えないので、立体的に見えるように立方体を回転させたいと思います。
先ほどのrender関数の中に3行書き足します。

// レンダリング ----------------------------------------
function render() {

  // 回転アニメーションを追加
  requestAnimationFrame(render);
  cube.rotation.x += 0.01; // x軸に0.01加算
  cube.rotation.y += 0.01; // y軸に0.01加算

  // シーンとカメラを渡してレンダリング
  renderer.render(scene, camera);
}
render();

ブラウザを更新して再度確認してみましょう。
立方体が回転しながら、ライティングの効果で立体的に見えるようになったでしょうか。

回転アニメーションサンプル

■ カメラを自分で操作出来るようにする

カメラを自分で操作できるようにしたいと思います。
まず、カメラ操作用ライブラリを読み込む必要があるため、three.jsの読み込みの下に書き足します。

<!-- three.jsを読み込む -->
<script type="text/javascript" src="three.min.js"></script>
<!-- カメラ操作用ライブラリを読み込む -->
<script type="text/javascript" src="OrbitControls.js"></script>

続いて、レンダリング処理部分の下に書き足します。

// レンダリング ----------------------------------------
function render() {

  // 回転アニメーションを追加
  requestAnimationFrame(render);
  cube.rotation.x += 0.01; // x軸に0.01加算
  cube.rotation.y += 0.01; // y軸に0.01加算

  // シーンとカメラを渡してレンダリング
  renderer.render(scene, camera);
}
render();

// カメラコントロール ----------------------------------------
var controls = new THREE.OrbitControls(camera);

では、ブラウザを更新して確認してみましょう。
マウスの操作に合わせてカメラを動かせるようになったかと思います。

カメラ操作サンプル

あとがき

長々とお付き合いいただきありがとうございました。
今回、WebGLに初挑戦したわけですが、ライブラリを使うことで、これだけのコード量で3D表現が出来ることに驚きました。
3Dソフトで作られたモデルデータの読み込みも出来るようなので、調査して挑戦してみたいと思います。


 ※免責事項※
 本記事内で公開している全ての手法・コードの有用性、安全性について、当方は一切の保証を与えるものではありません。
 これらのコードを使用したことによって引き起こる直接的、間接的な損害に対し、当方は一切責任を負うものではありません。
 自己責任でご使用ください

Pocket

コメント

コメントはありません

コメントフォーム

コメントは承認制ですので、即時に反映されません。ご了承ください。

*