Unity+Oculus Rift開発メモ(DK2対応)

2013年09月24日

(2014年9月13日更新)

Oculus Riftと、PCやビデオカードの選定、Unityで対応ソフトウェアを制作するためのTipsなどについてまとめてみました。

Oculus Riftについて

Oculus Riftって何?

Oculus Rift(オキュラス・リフト)は、Oculus VR社が開発中のバーチャルリアリティ用ヘッドマウントディスプレイです。比較的広視野な立体視が可能で、かつ、頭を動かして上下左右前後を見回すことができるため、CGの世界に本当に入り込んだような体験ができるのが特徴です。適切に調整すれば、空間内の物体が現実と同じサイズ・同じ場所に見えて、手を伸ばせば触れそうに感じられます。とても面白いデバイスです。

2014年9月現在、開発者向けの二世代目のキット(DK2)が販売されています。一般向けの製品は、対応ソフトが揃い、十分なクオリティのものをリリースする準備ができてからと考えているようです。

Unityを使うとOculus Rift対応アプリケーションが簡単に開発できます。UnityのProライセンスが必要です。

Oculusはラテン語由来で目の意味です。公式のロゴがまんま目ですね。

問題点はないの?

ヘッドマウントディスプレイを用いたバーチャルリアリティでは、VR酔いが発生します(乗り物酔いと似たようなものです)。酔いを引き起こす最大の原因は、頭や身体の動きと目で見ている光景のずれです。Oculus Riftでは、応答の速い有機ELディスプレイや、ずれを低減するさまざまな工夫を用いることでVR酔いをかなり解消できていますが、PCのセットアップや、アプリケーションの作り方が重要になります。

特にフレームレートの確保が最も重要で、左右両画面を常時最大フレームレート(DK2では75fps)で描画するために高性能なGPUが必要です。2014年現在では、だいたいGeForceやRadeonのミドルレンジ以上が必要になります。PC環境については下でもう少し詳しく触れていますので参照してください。

あと、視野はかなり広いのですが(映像鑑賞のための普通のヘッドマウントディスプレイが45度程度なのに対して、Oculus Riftは約90度あります)、十分に広いとは言えないかもしれません。現実世界でゴーグルを装着しているような感じです。

また、多少重かったり、暑いと汗でレンズが曇ったりします。

……と、一通り挙げてみましたが、Oculus Riftはまだ開発機の段階ですし、GPUの性能も今後さらに伸びていくでしょう。ハードウェアの問題については将来的に改善されていくのではないでしょうか。

他には、原理的に、ヘッドマウントディスプレイを装着すると手元のキーボードやマウス、ゲームコントローラーなどが見えません。周囲が見えないため安全面の問題も生じます。また、VR空間内では自分の手が見えなかったり、身体を動かすと物体をすり抜けてしまったりします。こうした制約をコンテンツや運用でどうカバーするかが鍵になりそうです。

視力が低くても大丈夫?

DK2にはA、Bの二種のレンズが付属していて、視力にあわせて交換できます。ただし、近視用のBレンズを使用すると視野がやや狭くなります。Riftの横についているダイヤルで目とレンズの距離を広げ、メガネをねじ込んで装着することもできますが、こちらもレンズが遠くなることで視野がだいぶ狭くなりますし、圧迫感があったり、レンズの接触で傷がつくリスクが生じます。100%楽しみたければコンタクトレンズがベストなのではないでしょうか。

とりあえず、かなり目の悪い自分がBレンズ・裸眼で楽しめていますが、度が弱いのと、開発時にメガネをかけたりはずしたりするのが面倒なため、コンタクトレンズを検討中という感じです。

どうすれば買えるの?

公式サイトから直接注文できます。送料と消費税・関税などがかかります。納期要確認です。自分のときは本体350ドル+送料75ドルで、FedExから別途2100円の請求が来ました。

なお、残念なことに特定の輸入代行業者を通しての購入でトラブルが発生していますので注意してください。Oculus VRから直接購入するのが一番です。

どうすればUnityで使えるの?

基本的には、公式サイトからUnity用のパッケージをダウンロードしてプロジェクトにインポートし、Oculus Rift用のカメラに置き換えてビルドするだけで対応ソフト完成です。実際簡単です。

注:DK2には現状かなり癖がありますので、適宜最新情報を追う必要があります。

UnityのPro版が必須なの?

公式のSDKはプラグインを使うため必要です。回避策として、Noraさんがフリー版でも使用できるOVRAgentを公開されています。

また、Unity Feedbackのこのあたりに投票するといいかもしれません。

ちなみに他のゲームエンジンでは、Unreal Engine 4がデフォルトでOculus Riftに対応していて、初期費用も少ないです(Oculus Rift with Unreal Engine 4 @ 第2回裏ocufes)。ただし、エンジン自体が重量級なので、かなりのGPU性能が必要です。

参考になる記事などはある?/新情報は?

はてなブックマークでOculus Riftタグでちょくちょくブクマしていますので参照してください。また、FacebookにVR Japanというグループがあります。

とりあえず実物を体験してみたい

OcuFesというOculus Riftの体験イベントが各地で開催されています。公式サイトで開催予定をチェックしてみてください。


PC環境について

Oculus Rift向きのビデオカードが欲しい

左右両画面をレンダリングしなければならないこと、75fpsの確保が必要なことから、高性能なGPUが必要です。もちろん描画内容次第ですが、普通に3Dゲームを遊ぶときと比べて数倍のGPU性能が必要だと考えてください。2014年現在では、GeForceやRadeonのミドルレンジ以上が望ましいです。

ちなみに、解像度、フレームレートともにまだまだ不足と考えられているため、要求水準は上がっていくものと思われます。DK2は解像度1920×1080・リフレッシュレート75Hzですが、製品版のOculus Riftでは2560×1440/90Hz以上を目指しているそうです。要求性能はフレームレートと画素数に概ね比例すると考えるなら、単純計算でDK2の2倍強のGPU性能が必要になります。また、Oculus VRからは、「完璧なVRには8Kでも足りない」「120Hzは何としても越えないといけない壁」といった発言が出てきています。これについて行くとすれば、ほどほどの性能のビデオカードを買い換えて行くのがいいのかもしれません。

大雑把な目算ですが、GPUのベンチマークの一つであるPassMark - G3D Markのスコアで、DK2で1500から2000、製品版で3000か4000程度のものが必要なのではという感覚です。

Oculus Rift DK2 動作状況報告シートに多数のPC環境での動作報告がまとめられていますので参考にしてください。

Oculus Rift向きのノートPCが欲しい

CPU内蔵GPUでは性能不足です。ゲーミングノートというカテゴリのものが必要です。

ゲーミングノートは薄い筐体にハイパワーなGPUを搭載している都合上、発熱の問題があるので注意です。不安になるくらい熱くなったり、真夏の屋外でのOculus Riftの展示で別途冷却が必要になったというような話があります。無理せずデスクトップPCを使うのも一つの方策かもしれません。

GPU PassMark G3D 参考機種
GeForce GTX 880M 4591  
GeForce GTX 780M 4116  
GeForce GTX 750 Ti 3627  
GeForce GTX 870M 3586 Razer Blade
GeForce GTX 860M 3415 NEXTGEAR-NOTE i420
GeForce GTX 770M 2611  
Radeon HD 7770 2157  
GeForce GTX 765M 1904 NEXTGEAR-NOTE i410
GeForce GT 750M 1667 15インチMacBook Pro Retina (Late 2013)
GeForce GT 650M 1290 15インチMacBook Pro Retina (Early 2013)
Intel Iris Pro 5200 853  
Intel HD Graphics 5000 562 MacBook Air (2014)
Intel HD Graphics 4400 504 Surface Pro 2
Intel HD Graphics 4000 466  
Intel HD Graphics 3000 307  

自分はGeForce GT 750M搭載のMacBook Pro Retinaの最上位機種を使用していますが、DK2で辛うじて合格ラインで、製品版のOculus Riftには明らかに足りなさそうです。Windowsゲーミングノートへの買い替えを検討しています。

こんな感じで一応外部電源なしでVRできます。HDMI端子とUSBポート2つ(Rift本体と付属の位置トラッキング用カメラ)を使っています。

Macでも大丈夫なの?

現状、OculusのSDKがWindows版から先にリリースされる傾向があるため、Windowsのほうが好ましいです。Boot CampにインストールしたWindowsでも使用できます。

Macの大きな問題として、GPUの制約があります。Windowsでは自作やBTOで高性能なビデオカードの載ったPCを組みやすいのですが、MacでOculus Riftを快適に動かすためには、iMacの(最)上位機種か、Mac Proが必要になってきます。また、Windowsにはゲーミングノートがあるのに対して、MacBook Proは最上位機種でもGeForce GT 750M止まりです。

また、UnityやUnreal Engineといったゲームエンジンも、OS XよりもBoot Camp上のWindowsで動かしたほうがフレームレートが出ているように思います。

Oculus Riftは、3Dゲームにより没入感をというPCゲームの文脈から登場したデバイスという一面がありますので、現時点ではWindowsがホームグラウンドだと言えるかもしれません。

さらに、Oculus Riftと他の特殊なデバイスを組み合わせて使う場合があるのですが、そうしたデバイスのSDKがMacに対応していないことがあります(例えばLogitechのステアリングコントローラなど)。


開発Tips

以下、開発Tipsです。DK2と、SDKのバージョン0.4.2に基づいています(一部内容が古い可能性あり)。

セットアップするには(Windows)

まず、Oculus Runtime for Windowsをダウンロードしてインストールします。インストールしたら、タスクトレイのOculusのアイコンからConfiguration Utilityを起動して、Riftが認識されているか確認してください。

(SDK 0.4.2で解消?)「The Oculus Service is not available」という通知が出て認識されない場合、Riftを抜き差ししたり、Windowsを再起動してみてください。また、C:\Program Files (x86)\Oculus\ServiceにあるOVRService_x64.exeまたはOVRService_x86.exeを手動で起動してみてください。サービスの起動まわりに不具合があるようです。

初めて使用する場合、Riftのファームウェアをアップデートする必要があります。Oculus Configuration UtilityのTools > Advanced > Firmware Update… を使って更新します。

Oculus Configuration UtilityからShow Demo Sceneを実行して、デモが動作すれば成功です。何も映らない場合、一度Rift Display ModeをExtend Desktopモードにして、Direct HMDモードに戻してみてください。Oculus SDK for Windowsに入っているOculus World Demoも試してみてください。

上手くいかない場合、楽しく使う Oculus Rift DK2も参照してみてください。

Unityで対応ソフトを作るには

Unity 4 Pro Integrationをダウンロードして、OculusUnityIntegration.unitypackageをインポートします。Main Cameraを削除または無効化して、OVR/Prefabs/OVRCameraControllerをシーンに配置してスタンドアローンでビルドします。通常のexeファイルとあわせて*_DirectToRift.exeが作られ、これを実行するとRiftの画面に出力されます(上手く行けば)。

動かない/スムーズに動かない

バージョン0.4.2現在だいぶ癖があるようで、試行錯誤することになると思います。正常に動作していればDemo SceneやOculus World Demoと同じようにスムーズに動いてヘッドトラッキングもぴったりついてくるはずですが、そうでない場合何かがおかしいです。

PC環境によって症状がかなりバラバラなようです。以下のようなことを試してみてください。

ビルドせずにOculus Riftで表示を確認したいんだけど……

一応、Extend DesktopモードでGameビューをOculus Riftの画面に持って行って最大化する方法があります。まだ試していませんが、これを楽にするスクリプトが作成されています。

UnityからOculus Riftでダイレクト表示できるようにする予定があるとのことですが、時期は未定とのことです。

OculusのパッケージをインポートするとUnityの起動ダイアログが出なくなる

OVR/Editor/OVRShimLoader.csによって、PlayerSettingsのDisplay Resolution DialogがHidden By Defaultに変更されています。また、UnityのPreferencesにOculus VRという項目が追加されますが、上手く動いていないようです。ちょっと気持ち悪いので、何をやっているか把握したら削除してしまうのも手かもしれません。

OVRShimLoader.csはビルド後の*_DirectToRift.exeの作成も行っており、これは、OVR/Editor/OculusUnityPatcher_32(64).exeをコピー・リネームすることで行われています。手作業で作成することも可能です。

自動車や飛行機など、移動するオブジェクトにカメラを載せるには?

OVRCameraControllerをそのオブジェクトの子にして、コンポーネントのFollow Orientationに親オブジェクトをセットします。

シーン間でOculus Riftの向きを維持するには?

デフォルトでは、Application.LoadLevelでシーンを移動するとRiftの向きがリセットされます。向きをキープしたい場合には、OVRCameraControllerのOVRDeviceコンポーネントのReset Tracker On Loadをオフにします。

メッセージなどを常に同じ位置に表示するには?

3D Textかテクスチャを貼ったポリゴンを、OVRCameraControllerの子のCameraLeftに接続します(描画順序の関係で、以前はCameraRightのほうが良かったのですが、0.4.0以降はCameraLeftのほうがいいようです)。

テクスチャポリゴンは3D空間内で他のオブジェクトと干渉しないよう、以下のような変更を加えたシェーダーを使います。

Tags { "Queue" = "Overlay" } // 最後に描画する
ZTest Always // Zテストをせず描画する

NGUIを使う場合にはこちらの記事が参考になると思います。同様の手法です。

位置トラッキングの基準位置はどうなってるの?

カメラと同じ高さで1メートル離れたポイントがデフォルトの基準位置です。また、実行中にOVRDevice.ResetOrientation()を呼ぶと、現在Riftがある位置・向き(ヨー方向)を基準にリセットされます。何かキーを押すと位置をリセットするようなスクリプトを置いておき、椅子に深く座った状態などでリセットするといいのではと思います。

using UnityEngine;

public class EnterKeyToReset : MonoBehaviour
{
    void Update()
    {
        // Enterキーで位置トラッキングをリセットする
        if (Input.GetKeyDown(KeyCode.Return)) {
            OVRDevice.ResetOrientation();
        }
    }
}

なお、カメラのトラッキング範囲は、カメラからの距離0.4メートルから2.5メートル、水平74度、垂直54度の錐台です。Oculus Developer Guideの7.1.1 Position Trackingに解説と図があります。

Sceneビューのカメラアイコンが大きくて目の位置がよく分からない

SceneビューのバーにあるGizmosをクリックして、3D Gizmosのスライダーを左に動かしてみてください。

「HEALTH & SAFETY WARNING」の警告メッセージはなくせないの?

なくせません。VRヘッドマウントディスプレイが事故や健康問題を引き起こすことは大いに考えられますから、必要でしょう。開発中だけでもなくせないかという議論はあるようです。

警告メッセージが消えたかどうか調べる方法は?

OVRCameraControllerだけのシーンを用意して以下のようなスクリプトを配置すれば、警告メッセージが閉じられるのを待ってメインのシーンに飛ぶことができます。

using UnityEngine;

public class OculusWarning : MonoBehaviour
{
    void LateUpdate()
    {
        if (!OVRDevice.HMD.GetHSWDisplayState().Displayed) {
            Application.LoadLevel("main");
        }
    }
}

画面が暗くなる(SDK 0.4.2)

SDK 0.4.2には、しばしば画面が暗くなる不具合があります。64bit(x86_64)でビルドすると大丈夫なようです。

Oculus Riftの接続チェックをするには?

SDK 0.4.2では64bitビルドではこれらの関数はNullReferenceExceptionで使えないようです。

OVRDevice.IsHMDPresent()でRiftが接続しているかどうか調べられます。

また、OVRDevice.IsCameraPresent()で位置トラッキングカメラの有無が分かります。ただし、Rift本体が繋がっていないとこちらもFalseになるようです。

なお、これらの関数はOVRDevice.Awake()が実行されたあと(Startなど)に呼び出す必要があります。

同じプロジェクトでOculus Rift版と通常版をビルドしたい

実行バイナリを分ける方法と、一緒にする方法が考えられます。

まず、バイナリを分ける方法としては、PlayerSettingsのOther SettingsタブにあるScripting Define Symbolsを使って、例えばOCULUSシンボルが定義されていればOVRCameraControllerを、されていなければ通常のカメラを有効にするといいのではと思います。

using UnityEngine;

public class VRCamera : MonoBehaviour
{
    public Transform riftCameraPrefab;

    void Awake()
    {
        #if OCULUS
        // OCULUSシンボルが定義されていればカメラを入れ替え
        Transform riftCamera = (Transform) Instantiate(riftCameraPrefab);
        riftCamera.SetParent(transform, false);

        transform.Find("Camera").gameObject.SetActive(false);
        #endif
    }
}

一緒にする方法としては、OVRDevice.IsHMDPresent()でRiftの有無を調べて、あればOVRCameraControllerを、なければ通常のカメラを使用するようにすることが考えられます。

ちなみにSDK 0.4.2現在、64bitビルドではIsHMDPresentが動かないためこの方法は採れない印象です。感覚としては前者のほうが安全かもしれません。

using UnityEngine;

public class VRCamera : MonoBehaviour
{
    public Transform riftCameraPrefab;

    void Awake()
    {
        // OVRCameraControllerをとりあえずインスタンス化する。IsHMDPresentに必要なため
        Transform riftCamera = (Transform) Instantiate(riftCameraPrefab);
        riftCamera.SetParent(transform, false);

        if (OVRDevice.IsHMDPresent()) {
            // Riftが接続されていれば通常カメラを無効化
            transform.Find("Main Camera").gameObject.SetActive(false);
        } else {
            // Riftが接続されていなければOVRCameraControllerをただちに削除
            DestroyImmediate(riftCamera.gameObject);
        }
    }
}

なお、先述のように、OVRShimLoader.csによって、起動ダイアログを隠したりといった処理が行われています。無効化するなどの措置が必要かもしれません。

OculusのSDKを配布物に含めてもいいの?

例えばUnity Asset Storeでアセットに含めて配布する場合などが考えられると思います。商業・クローズドソースのものに含めても問題なしとのことです。

酔いを低減するには?

VR酔いは、乗り物酔いと同じように、自分が予測・体感している動きと視覚情報との間にずれがあると発生します。ですので、とにかくまず描画負荷を低減したり、高性能なビデオカードを使うなどして、最大フレームレートを確保するのが重要です。スムーズに75fps再生できないとあっという間に酔います。それと、現状ゲーム等ではプレイ時間を短めにするのがいいのではないでしょうか。

また、公式からOculus VR Best Practices Guideというガイドラインが公開されています。非公式の日本語訳(本編付録)もあります。縮尺や移動速度を正確にする、頭の動きとは無関係なカメラ移動をしない、ユーザーが常に(ポーズ中やカットシーンでも)周囲を見回せるようにする、水平線や大きな表示要素を動かさない、加減速は短くあるいは即座に、残弾数は浮いているHUDではなく武器それ自体に表示する、等々、非常に多数の注意事項がありますので、じっくり読んでおいたほうがいいと思います。ここで挙げたものはほんの一部です。

スケール(縮尺)に関する注意

Riftのカメラは実際の左右の目と同じ間隔(デフォルトでは0.064=6.4cm、Oculus Configuration Utilityで変更可)でシーン上に配置され、これによってVR空間の物体が現実的な大きさに感じられるようになっています。Unityは1ユニット=1メートルが基本になっていますので、これを守りましょう。例えば、身長170cmのキャラクターを出すときは、Unity上で頭頂まできっかり縦1.7になるようにサイズを調整しましょう。これをはずすとちょっともったいない気がします。

Cubeオブジェクトを作って定規代わりにすると便利です。


番外編

ブラウザ(HTML5)では使えないの?

現在、FirefoxとChromeにおいて、WebVRというAPIの検討が始まっています。Oculus Riftなどの方向・位置センサーの状態をこのAPIで取得して、Three.jsなどを使って3D描画、変形表示をすることになります。はてなブックマークでWebVRタグで追っていますので参照してください。IEの開発チームも関心を持っているようです。

個人的には、VRというのは表示遅延や描画負荷など非常にシビアな処理ですし、また、ゲームエディタなしでVRソフトを作るのは困難なので、UnityやUnreal Engineなどのネイティブなゲームエンジンに頼ったほうがいいのではと思っています。Unity 5のWebGL出力などもいずれWebVRに対応するのではないでしょうか。Unityの開発者が「できない理由はない」とコメントしていました。

オープンなヘッドマウントディスプレイやゲームエンジンの発展にも期待したいところです。

Oculus Riftの取り扱いで気をつけることは?

DK2のレンズは非常に傷つきやすいので注意です。眼鏡の接触で傷が入ったり、使っていないほうのレンズをビニールパックに入れて持ち運んでいたらいつのまにか細かい傷がたくさん入っていたりというようなことが起きています。拭くときは、カメラ用のレンズクリーナーを使うといいようです。

なお、傷が入ってしまったレンズを研磨剤で磨いてみたところ、一応修復できました。自己責任でお願いします。

雑多なメモ

参考になる本はある?

Oculus Riftよりも前の情報になりますが、VR全般を包括的に扱っている「バーチャルリアリティ学」という本があります。

また、Oculus Riftそれ自体を扱う本も現在執筆されているようです。

これ書いてる人はどんなの作ってるの?

「3D駐車シミュレーター」「VRシューティング(仮)」などを作っています。Oculus Rift対応ソフトのコーナーにぜひお立ち寄りください。

comments powered by Disqus