Leap Motionを使ってVR上にデスクトップ画面を作ろう
はじめに
Leap Motionとは
Leap Motionは、手の位置や指一本一本の動きをトラッキングすることのできる赤外線センサーです。
VR向けに対応したOrion SDKを導入することにより、Oculus RiftやHTC Viveと組み合わせてVR空間で手をトラッキングすることも可能になりました。
特徴
長所
- 手に握るタイプのコントローラー(Oculus touchなど)と違い、ものを持たずにVR上で操作が可能。
- ジェスチャーを使った直感的な操作ができる。
短所
- 手に握るタイプのコントローラーと比較して、トラッキング精度が劣る。
- ボタンのついたコントローラーと異なり、フォースフィードバックが感じられないので物を掴んだりする際に違和感を感じる。
- 視野角130度ぐらいしかカバーできないので、ジェスチャーでPinch outさせたときに手がトラッキングから外れることがしばしば。
- VRHMDを赤外線センサーでトラッキングするシステムを使っているHTC Viveだと、ViveとLeap Motionのセンサー同士が干渉することがある。
今回の目的
- HTC ViveとLeap Motionを用いて、VR空間にデスクトップ画面を生成する。
具体的には、親指と人差し指をくっつけた状態(Pinch point)で両手のPinch pointを近づけたときに、デスクトップ画面をVR空間内に生成させるというもの。 以下がそのイメージ図になります。
デモ
必要なもの
ハードウェア
- HTC Vive
- Leap Motion
使用したミドルウェア・アセットなど
- Unity5.5.0f3
- Leap Motion SDK v3.2.0 (ORION BETA)
- LeapMotion_CoreAsset_Orion_4.1.5.unitypackage
- Attachments-1.0.4.unitypackage
- UIInputModule-1.2.0.unitypackage
- uDesktopDuplication-v1.5.1.unitypackage
- SteamVR Plugin
- Purple Space Nebula Skybox
内容
Leap MotionのUnityアセットをあらかじめ、下記のサイトからダウンロードしておく。
Unity — Leap Motion Developer
デスクトップをミラーリングするのに、uDesktopDuplicationを使用した。 github.com
(1) SteamVR Pluginをインポートする。SteamVR_settingsが出てくるのでAccept All
をクリック(You made the right choice!
というコメントが出る)。
(2) [Assets] -> [Import Package] -> [Custom Package...]をクリックして、
- LeapMotion_CoreAsset_Orion_4.1.5.unitypackage
- uDesktopDuplication-v1.4.2.unitypackage
をそれぞれインポートする。
(3) Scenes
フォルダを作成し、新しいシーンPinchTest
を用意する。
(4) Hierarchy
のMain camera
を削除する(VRHMD専用のCameraをあとで追加するので、Unityの既存のカメラを削除する必要がある。)
(5) Assets/LeapMotion/Prefabs
からLMHeadMountedRig.prefab
をHierarchy
にドラッグ&ドロップする。
(6) Hierarchy
中のLMHeadMountedRig/HandModels
にあるCapsuleHand_L
とCapsuleHand_R
をそれぞれ右クリックし、Create empty
から空の子オブジェクトをつくる。それぞれ、PinchDetector_L、PinchDetector_Rと名前をつける。
(7) Assets/LeapMotion/Scripts/DetectionUtilities
からPinchDetector.cs
を先ほど作成したPinchDetector_L
とPinchDetector_R
にそれぞれアタッチする。これらのオブジェクトは人差し指と親指をくっつけた状態(Pinch)を手が取っているかどうか確認するのに必要です。
ここまででPinchの検出がする準備が整いました。
さらに、Pinch状態になっているかどうか視覚的に確認するために、ここではLeap Motionから提供されているAttachmentsのUnityアセットを導入します。
(8) [Assets] -> [Import Package] -> [Custom Package...]をクリックして、Attachments-1.0.4.unitypackage
とUIInputModule-1.2.0.unitypackage
をインポートする。
(9) Assets/LeapMotionModules/Attachments/Prefabs
からHandAttachment_L.prefab
とHandAttachment_R.prefab
をHandModels
にアタッチする。
(10) 先ほどアタッチしたHandAttachmentsを、使用するHandModelsとして設定するためにLeapHandController
の設定を変更する。
- Hand PoolのModel Poolで
Size
を1から2
に変更する。 - Model Poolが1つ追加されるので、
Group Name
をAttachment
と記載し、Left Model
とRight Model
にHandAttachments-L/R
をそれぞれアタッチする。
(11) Assets/LeapMotionModules/UIInput/Textures
をCircleCursor
をアタッチする。
(12) CircleCursor
のTransformを書き換える。Positionを(0, 0, 0)、Rotationを(120, 0, 0)、Scaleを(0.15, 0.15, 0.15)に設定する。CircleCursorの位置を設定しているだけなので、適当な値を入れて構わない。
(13) PinchPoint
のInspector
から、Add Componentをクリックして、Pinch Detector
を選択する。
(14) Scripts
フォルダを作り、PinchCursor.cs
という名前のスクリプトを用意する。
Pinchを検出したときに、子オブジェクトをActive状態にするスクリプトになります。
(15) 先ほど作成したPinchCursor.cs
をPinchPoint
にアタッチする。
(16) PinchPoint
のInspectorのPinch Detector内にあるOn Activate()
の+
をクリック。
Pinch状態にあるとき、On Activate
上で指定した関数が実行されます。一方で、Pinch状態が解除された場合、On Deactive
上で指定した関数が実行されます。つまり、手の状態の遷移に伴って、さまざまな命令を実行ができるというわけです。
(17) PinchPointオブジェクトを図に示した箇所にドラッグ&ドロップ。
(18) No Functionをクリックし、先ほど作成したPinchCursorのpinchOn()関数
を指定する。On Deactivate()
に関しても同様の操作を行い、No FunctionにpinchOff()関数
を指定する。
最終的に、以下のようになるはずです。
(19) CircleCursor
オブジェクトのチェックを外して、Deactivate
の状態にしておく。
こうしておくことで、シーンのはじめにCircleCursor
が見えない状態になります。
逆にチェックを外しておかないとはじめからCursorが見えてしまいます。
(20) シーンのプレビューを行う。
以下のように、Pinchが検出されると、設定したCircleCursor
が出現します。Pinch状態が解除されると、Cursorは見えなくなります。
最後に、Pinch状態にある両手を近づけたときに、デスクトップ画面がVR上で生成される仕組みを作っていきます。
(21) Hierarchy上で、何も選択していない状態で右クリックする。Create empty
を選択し、DisplayAnchor
という名前の空のゲームオブジェクトをつくる。
(22) Scriptsフォルダ内にCreateDisplay.cs
という名前のスクリプトを作る。
(23) CreateDisplay.cs
スクリプトを先ほど作成したDisplayAnchorオブジェクト
にアタッチする。
(24) Pinch Detector_L
、Pinch Detector_R
、Magic Display Prefab
に、HandModels内のPinchDetector_L
、PinchDetector_R
とAssets/uDesktopDuplication/Examples/Prefabs
のMonitor_Board.prefab
をそれぞれアタッチする。
(25) Skyboxがデフォルトのままで物悲しい感じなので、UnityアセットのPurple Space Nebula Skyboxを導入する。
(26) Assets/Skyboxes/PurpleNebula
にあるPurpleNebula.mat
をシーンにドラッグ&ドロップ。
周りが宇宙空間になりました。少しはマシな感じになったと思います。
(27) 最後に、CenterEyeAnchor
のInspectorのCameraでClear FlagsをSkybox
に変更する。
これを設定しないと、Skyboxが反映されないので周りが真っ暗なままになってしまいます。
(28) シーンのプレビューを行う。
以下のように両手のPinchを検出され、PinchPoint
を近づけたときにディスプレイが生成されます。
Pinch in
もしくはPinch out
することで自由自在に大きさを変えられます。
手(親指と人差し指)を離すと、その場にディスプレイが固定されます。
以上、C#のスクリプトの記述量は少なめで、Unityアセットを多用してイメージ通りのものが作れました。