(この記事の使用環境: Unity5.5.0f3 Personal、Windows10、SteamVR Plugin 1.2.0、VRTK3.0.1)


VR用アセット「VRTK」の Example 027_CameraRig_TeleportByModelVillage の解説です。
ポインターを使わずに、ミニマップ状に配置されたオブジェクトを使ってテレポートするデモです。
SnapCrab_NoName_2017-2-6_13-19-26_No-00

■公式サイトの解説

VRTK公式サイトでこのExampleの解説文及び解説動画を見ることができます。ただし、動画に関してはVRTK旧バージョンのときに作られたものであり、VRTK3.0(以降)では設定等が異なっている場合があることに留意してください。動きを中心に見てもらえれば良いかと思います。

このExampleの解説動画



■VRTKのセットアップ方法および使用されているスクリプトの解説

適宜、以下の記事を参照願います。

■Exampleの解説

VRTK/Examples 内にある当該番号のシーンを呼び出すことで、デモを動かしてみることができます。

このデモシーンは、ポインターを使わずに、抽象クラス VRTK_DestinationMarker を使って異なる場所へテレポートする方法を示します。それはゲーム世界でミニマップ状に配置されたオブジェクトに付けられています。マップ上のオブジェクトにタッチし使用すると、ユーザーは特定の地点にテレポートします。
SnapCrab_NoName_2017-2-6_13-19-26_No-00

以下、シーンに配置されているオブジェクトについての概要説明です。
  • ExampleAreas: シーン上に配置されている、それぞれ赤、緑、青のオブジェクトで構成された3つのエリア。それぞれのエリアには「AreaXTeleportLocation」と名付けられた、テレポート先の位置を指定するためのゲームオブジェクトがある。
    SnapCrab_NoName_2017-2-6_13-41-4_No-00

  • Left Controller、RightController: [VRTK] ゲームオブジェクトの下に配置されている、左右のコントローラー用のVRTKスクリプトをアタッチするゲームオブジェクト。
    VRTK_ControllerEvents 、VRTK_ControllerActions 、VRTK_InteractTouch スクリプトがアタッチされており、オブジェクトにタッチできるようになっている。

  • PlayArea: [VRTK] ゲームオブジェクトの配置されているゲームオブジェクト。
    VRTK_HeightAdjustTeleport スクリプトがアタッチされており、テレポートが可能になっている。

  • TeleportTable: [VRTK] ゲームオブジェクトの配置されているゲームオブジェクト。テーブル上に赤・緑・青のCube(Area1, 2, 3)が配置されている。このテーブルは Follow スクリプトがアタッチされており、[CameraRig] の位置・回転に追従し、常にユーザーの目の前に置かれる。
    SnapCrab_NoName_2017-2-6_14-17-35_No-00

  • Area1、Area2、Area3: TeleportTable上に置かれた赤・緑・青のCube。
    VRTK_DestinationMarker を継承した ModelVillage_TeleportLocation スクリプトがアタッチされており、それらのCubeをコントローラーでタッチし使うことにより、触れたオブジェクトの色に対応したエリアにテレポートする。
    SnapCrab_NoName_2017-2-6_14-3-10_No-00

    ModelVillage_TeleportLocation スクリプトの中身。
    namespace VRTK.Examples
    {
        using UnityEngine;
    
        // --- テレポート先を定める ModelVillage_TeleportLocation スクリプト(VRTK_DestinationMarker を継承)--------
        public class ModelVillage_TeleportLocation : VRTK_DestinationMarker
        {
            public Transform destination;               // 目的地(テレポート先)
            private bool lastUsePressedState = false;   // 直前のUseボタン(デフォルトではトリガー)の状態(押されていたか否か)
    
            private void OnTriggerStay(Collider collider)   // Cubeに触れている状態
            {
                var controller = (collider.GetComponent<VRTK_ControllerEvents>() ? collider.GetComponent<VRTK_ControllerEvents>() : collider.GetComponentInParent<VRTK_ControllerEvents>());
                if (controller)
                {
                    if (lastUsePressedState == true && !controller.usePressed)  // Useボタンが離されたタイミングで処理する
                    {
                        var distance = Vector3.Distance(transform.position, destination.position);  // 目的地までの距離
                        var controllerIndex = VRTK_DeviceFinder.GetControllerIndex(controller.gameObject);
    
                        // 目的地のセット(VRTK_DestinationMarker)
                        OnDestinationMarkerSet (SetDestinationMarkerEvent(distance, destination, new RaycastHit(), destination.position, controllerIndex));
                    }
                    lastUsePressedState = controller.usePressed;
                }
            }
        }
    }
    

今回は以上です。