2013年12月2日月曜日

3Dモデルの表示がしたい:WebGL編

少し前までAndroidでのOpenGLプログラムやら、Blenderからのモデル出力を調べていました。目的は3Dモデルを表示するのに楽な方法は現状だとなんだろうと試行錯誤していたわけです。
昔はc++なんかでガリガリViewerプログラムをInventorなんかつかったりして作っていたんです。Inventor自体は好きなんですが、肝心のSGIがどうもダメダメ(今ではGraphicsは完全に撤退して、スーパーコンピューティングの会社になってしまってます。唯一Graphicsの部門をNECに売却して日本SGIとして細々とやっているくらいですか。。。)で、Inventorを使い続けるのに不安をずっと感じていたんです。仕事でやるならもう自分でViewerは作りません、できあいの製品かってきます。その方が安心です。

ただそれでもどうしても特注のカスタマイズしたViewerが欲しい場合どうしたらいいか?と考えて、様子を見てたんですが、どうも結局OpenGLでガリガリ書くのが時流のような気がします。それでまあ、特注で必要になるとすると今時のタブレット用アプリくらいかとAndroidを見てたんですが、やはりOpenGLをガリガリするのは疲れます。何より、モデルデータの読み込みを自分で用意しないといけないのがしんどいです。そこでモデルデータ作成にBlenderを調べて、今度はモデルデータのエクスポートから表示方法を考えていました。
実は前から気になっていた技術に「WebGL」があります。JavaにもOpenGLの実装がありますが、それをブラウザのJavaScriptでやってしまおうというものです。可能性を非常に感じていたんですがいかんせん「重い!」に当時はつきました。ブラウザを使うPC性能(正確にはGraphicsボードの性能になります)に依存しますし、それでも素でアプリから動かすより数倍重く感じました。(昔々、SGIが同じような考えでVRMLというのを考えてましたが、結局今じゃ聞かなくなってしまいましたね)その後、セキュリティ上の問題がJavaScriptおよびWebGLの両方に見つかり、一時停滞したようですが、また最近記事がでるようになり、JavaScript用のライブラリもScene.jsとかThree.jsとかさかんにでてくるようになりました。ところで現状WebGLが使えるのは、以下のブラウザだけとのことです。

  • Chrome
  • FireFox
  • Safari
  • Opera(機能限定らしい)
  • IE11(やっとMSも実装したらしいけど、どの程度の実力かは不明)


そんなところで、ChromeとFireFoxを使いながらThree.jsで様子を見てみることにしました。(理由は、BlenderからモデルデータをThree.jsが読み込める形式にする方法があるから)ところがこれが非常に難航しました。まずWebの記事のようにThree.jsが動かない。(表示がおかしい)これの原因究明にかなり時間がかかりましたが、大体わかってきたのでメモしておきます。(利用したブラウザはChromeとFireFoxです)

1.簡単なサンプルしか表示されない
簡単な立方体を表示するJavaScriptのプログラムは問題なく動きました。

ところが、これにjpegのテクスチャを張ろうとすると、、、
何コレ?っていう感じですが、本当は以下の様に表示される(予定)ものです。
(これはその後、試行錯誤の結果表示できるようになったものです)
球体に、地球表面のjpegを用意してそれをテクスチャとして貼り付けているはず、なんですがうまくいきません。

2.ChromeとFireFoxで挙動が違う
上記の地球のサンプルですが、実はFireFoxだとうまく表示できるんです。Chromeはだめ。ブラウザの開発コンソールを見ても特にエラーは返してこないし、なんでだ!?と悩みましたが、確かJavaScriptのセキュリティ問題で、ローカルなファイルはJavaScriptでは読めないようにしたのを思い出しました。(IEは、今更そんな制限つけれるかという感じのようですが)FireFoxも緩いようですが、テクスチャとしての読み込みだけは許可してくれたようです。(注:WebGLはさらにメモリリークの問題も発生していたため、Chromeではテクスチャデータだろうがローカルからの読み込みを禁止しているんでしょうね)

Three.jsのサンプルにテクスチャを貼ったものがありますが、Chromeだと全滅ですね。FireFoxじゃないとローカルな環境ではまともに表示してくれません。

3.Blenderのモデルデータを読み込んでくれない
さあここまでくれば問題はあきらかです。肝心のBlenderのモデルデータファイルを読みこもうとするとChromeやらの開発コンソールに明確に、ローカルファイルは読み込めませんといってきます。(正確にはローカルなファイルを指定するfile://というURLでは不正と判断され、http経由じゃなきゃだめ、みたいな感じ)
これにはまいりました。Webで見つかった記事には一言もそんなこと書いていてくれません。あきらめてLinuxマシンにapache2をインストールしましたよ。(設定はデフォルトのまま。特に外部のPCから見たいわけではないんで。URLはhttp:://localhostで参照できれば十分です。)そうしたら無事表示されました。(基本、ローカルでしか使いません。ローカルなファイル見るのにapache経由というのも変な感じがしますが、そうしないとセキュリティをクリアできない!)
何表示してるの?って感じですが、まずBlenderでモデル作成したとき、XYZ軸の+方向がどう表示されるのか確認しないといけなかったので、Blenderで四角すいを3つ、XYZ軸(RGB)方向に作成した(ついでに各四角すいはそれぞれの軸の色にしてあります)モデルデータを表示してみたものです。(下図のモデルを出力したものです)

WebGLには軸表示としてHelperを使っています。なんかX軸(R)で90度回転してますね・・・
ところで、Three.jsのGitHubにあるエクスポートスクリプト(python)はBlender2.66用です。自分は現状最新の2.69を使っており、これが表示されない原因かとも一時思いました。しかし、結果的にはBlender2.66だろうが、2.69だろうがエクスポートされるファイル(JSON形式です)は同じものでした。Blenderを両方インストールして確認してみました。モデルがもっと複雑になると違ってくるかもしれませんが。

3.5 Blenderモデルのエクスポートオプション
上述の結果は、Blenderにてthree.js用にモデルデータをエクスポートするさい、デフォルト設定で行ったものです。改めてオプションを見てみたら、座標軸を変換するオプションがありました。
下部の「Flip YZ」がデフォルトではオンになっていますが、これをオフにして出力してみると、以下のようになりました。
XYZ(RGB)軸がきちんと同じ方向に表示されるようになりました。しかし、なんでこんなオプションがあるんだか…


色々試行錯誤して、「Blnederで作成したモデルデータをWebGLで表示する」という目的は達成できました。ついでにかなりまだクセが強いのも理解できましたが。(最後のモデルが回転してしまう、というのはよくある話なんで、理解できてればそんなに苦にはなりません。)

結局、Three.jsに多数格納されているexampleですが、テクスチャ関係使っているものはFireFoxでないとローカル環境だけでは見れません。apache動かして、http経由で見ればChromeでも見ることができます。(逆にいうと、これ気づかないと大多数の人が「Three.jsってこんな表現しかできないのか」と勘違いしてしまいそうです。

0 件のコメント:

コメントを投稿