シーンとカメラとレンダラーの準備
「three.js」の読み込み
まず、「three.js」を「script」タグでHTMLファイルに読み込みます。本記事では「jQuery」も使うので、こちらも同様に読み込みを行ってください。
「three.js」をHTMLファイルに読み込むと、「three.js」は「THREE.WebGLRenderer 58」といったメッセージをコンソールに出力します。しかし、一部のブラウザではコンソールが存在しないために、この時点でエラーが出ます。エラーを回避したい場合は、以下の「console.js」のようなコードを、「three.js」の前に読み込むと、エラーが表示されません。
<script src="http://ajax.googleapis.com/ajax/libs/jquery/2.0.2/jquery.min.js"></script> <script charset="UTF-8" src="js/console.js"></script> <script charset="UTF-8" src="js/three.js"></script>
// Init Console.log
if (typeof window.console === "undefined") {
window.console = new function() {
this.log = function() {};
this.error = function() {};
};
}
カメラの設定と位置
「three.js」で3D空間を描画するには「カメラ」と「シーン」と「レンダラー」の3つのオブジェクトを作成する必要があります。まずは、このカメラについて説明します。
カメラを初期化する際は、4つの値「視野角」「アスペクト比」「近距離限界」「遠距離限界」を設定します。
「視野角」の値を大きくすると、広い範囲を一度に見ることができますが、画面の端の方では物体が歪みます。対して値を小さくすると、狭い範囲しか見ることができませんが、画面の端の方でも歪みが少ないです。今回はマンガのコマを作るので、歪みが少なくなるように、値を小さくします。
「アスペクト比」は、「横/縦」の値です。これは作成する描画領域を元に計算します。
「近距離限界」「遠距離限界」は、3Dプログラミングが初めての場合には戸惑う値だと思います。3Dプログラミングでは、カメラが向いている方向の、すべての物体を描画するわけではありません。カメラに近すぎる物体や、遠すぎる物体は、計算を行わず描画をしません。
これは無駄な計算をしてマシンに負荷を掛けないための仕組みです。「近距離限界」よりもカメラに近い物体は描画されません。また「遠距離限界」よりもカメラから遠い物体も描画されません。
この仕様は、3Dプログラミングを始めて行う際には、見落としがちな所です。物体を作成しても、カメラに近すぎたり、逆に遠すぎたりして、何も表示されないということがよくあります。
最後に、カメラの位置を変更します。なぜカメラの位置を変更するかというと、初期化の時点では原点(0, 0, 0)の位置にカメラがあるからです。これから物体を作成する際に、カメラが原点にあると、物体が近すぎて表示されません。そのため、カメラを少し下げて、作成する物体がうまく表示されるようにします。
カメラを含め、「three.js」の3Dオブジェクトには「位置(position)」「回転(rotation)」「拡縮倍率(scale)」の値があります。この中でカメラで使うのは、位置と回転でしょう。本記事ではカメラは固定して使うので、位置のみを利用します。
obj3d = {
position: {x: 0, y:0, z: 0}
,rotation: {x: 0, y:0, z: 0}
,scale: {x: 0, y:0, z: 0}
,…
};
// カメラの初期化
camera = new THREE.PerspectiveCamera(
10, // fov(視野角) 10ぐらいが歪みが少ない
w / .h, // アスペクト比
1, // near 近距離限界
10000 // far 遠距離限界
);
camera.position.z = 4000; // カメラ位置を移動
また、シーンも作成します。シーンには、カメラを追加します。
// シーンの初期化 scene = new THREE.Scene(); scene.add(camera);
「Canvasレンダラー」と「WebGLレンダラー」
「three.js」には、「Canvasレンダラー」と「WebGLレンダラー」が存在します。「Canvasレンダラー」は、WebGLに対応していないブラウザでも、「Canvas」を利用して3D表示を行うためのレンダラーです。ただし、かなり重いです。実用レベルで使いたいのならば、「WebGLレンダラー」を選択して、対応するブラウザを利用するのがよいでしょう。
「レンダラー」を初期化する際は、アンチエイリアスの有無など、各種パラメータを付けることができます。設定可能な引数は「WebGLRendererのドキュメント」で確認可能です。
また、レンダラーは「setSize」で描画サイズ(Canvasのサイズ)を設定します。その後、「domElement」を、DOMツリーに追加することで、Webページ上に「WebGL」の表示を行うことができます。
// レンダラーの初期化
renderer = new THREE.WebGLRenderer({
preserveDrawingBuffer: true,
format: THREE.RGBAFormat,
antialias: true
});
renderer.setSize(w, h);
// コンテナーにキャンバスを格納
cntnr.empty(); // 空にする
cntnr.append(renderer.domElement); // DOM要素を追加
初期化までの「まとめコード」
ここまでの初期化処理をまとめた「crocro.bc.js」を掲載します。本記事の処理については「crocro.bc」(bcはBoxComicの略)オブジェクトにすべて格納するようにしています。また、Three.jsに関わるようなオブジェクトは「crocro.bc.d3」以下に格納するようにしています。
//= 3D表示の基本部分の関数群
//== パッケージの初期化
if (typeof crocro === "undefined") {var crocro = function() {};}
if (typeof crocro.bc === "undefined") {crocro.bc = function() {};}
crocro.bc.cntnr = null; // 格納要素
crocro.bc.ui = null; // UI要素
crocro.bc.d3 = {}; // 3D格納用
//========================================
//== コンテナーの初期化
crocro.bc.initContainer = function() {
// 変数の初期化
var d3 = crocro.bc.d3; // 3D格納用
d3.w = 640;
d3.h = 480;
// コンテナーの初期化
crocro.bc.cntnr = $("#container");
var cntnr = crocro.bc.cntnr;
cntnr.width(d3.w).height(d3.h); // 縦横をセット
cntnr.empty(); // 空にする
}
//== 構築
crocro.bc.build = function() {
// 変数の初期化
var d3 = crocro.bc.d3; // 3D格納用
var cntnr = crocro.bc.cntnr; // コンテナー
//=== カメラの初期化
d3.camera = new THREE.PerspectiveCamera(
10, // fov(視野角)10ぐらいが歪みが少ない
d3.w / d3.h, // アスペクト比
1, // near 近距離限界
10000 // far 遠距離限界
);
d3.camera.position.z = 4000; // カメラ位置を移動
//=== シーンの初期化
d3.scene = new THREE.Scene();
d3.scene.add(d3.camera);
//=== レンダラーの初期化
d3.renderer = new THREE.WebGLRenderer({
preserveDrawingBuffer: true,
format: THREE.RGBAFormat,
antialias: true
});
d3.renderer.setSize(d3.w, d3.h);
// コンテナーにキャンバスを格納
cntnr.empty(); // 空にする
cntnr.append(d3.renderer.domElement); // DOM要素を追加
};
//== レンダリング実行
crocro.bc.render = function() {
var d3 = crocro.bc.d3; // 3D格納用
d3.renderer.render(d3.scene, d3.camera);
}
//== UIのリセット
crocro.bc.resetUI = function() {
$("window").unbind("blur"); // イベント削除
crocro.bc.cntnr.unbind(); // イベント削除
crocro.bc.ui = $("#ui");
crocro.bc.ui.empty(); // 空にする
crocro.bc.ui.unbind(); // イベント削除
}
//== 切り替え時の終了処理
crocro.bc.finalizeFnc = null;
crocro.bc.setFinalize = function(arg) {
crocro.bc.finalizeFnc = arg;
}
crocro.bc.execFinalize = function() {
if (typeof crocro.bc.finalizeFnc === "function") {
crocro.bc.finalizeFnc();
}
crocro.bc.finalizeFnc = null;
}
また、実行を開始する「main.js」も掲載します。
//= 読み込み後実行
$(document).ready(function() {
//== ブラウザ判定
if (/*@cc_on!@*/false) {
return; // IEなので終了
}
//== コンテナーの初期化
crocro.bc.initContainer();
//== リストの値を設定
$("#lstSmplTyp > option").each(function() {
var ths = $(this);
ths.val(ths.text());
});
//== 実行ボタンの処理
$("#btnSmplTypExec").click(function() {
// 3Dの初期化
crocro.bc.execFinalize(); // 終了処理
crocro.bc.build(); // 構築
// UIの初期化
crocro.bc.resetUI();
//========================================
// サンプルによる分岐
var smplType = $("#lstSmplTyp").val();
if (smplType == "基本オブジェクトの表示") {
crocro.bc.viewBasicObject();
}
// 以降、サンプル作成ごとに追加。
});
});
これで準備はできました。この先は、「crocro.bc.js」「main.js」が読み込まれているという前提で話を進めます。また、作成したファイルは、以後の記事においても、すべて読み込み済みということでご案内していきますので、ご承知おきください。
では次ページでは、立方体を作成して表示してみます。
