夜風のMixedReality

xRと出会って変わった人生と出会った技術を書き残すためのGeekなHoloRangerの居場所

MRDL Surfacesを学ぶ FingerSurface 

本日はMRDLの[Surfaces]の調査枠です。

前回から[FingerSurface]クラスを見ています。

コード全文は次の様になっています。

github.com

〇Awake関数

Surfacesアプリの各体験でシーンがロードされると[FingerSurface]クラスをスーパークラスとする各シーンごとのコンポーネントが実行されます。

[FingerSurface]クラスが実行されると最初にAwake関数の処理が実行されます。

 protected ContextualHandMenu menu;
     protected virtual void Awake()
     {
         menu = FindObjectOfType<ContextualHandMenu>();
         activeSurface = this;
         Initialized = false;

         SurfacePosition = surfaceTransform.position;
     }

ここではシーンロードごとの初期化を行っています。

[menu]にシーンから[ContextualHandMenu]…つまりシーンロード時に使用する[HandMenu]が代入されます。

また[activeSurface]に自分自身を、[Initialized]にはFalseが代入されます。

[SurfacePosition]は各体験の親オブジェクトの座標になります。

例えば[Cube(Unityシーン名はVolume)]では[Smoke]がアタッチされます。

f:id:Holomoto-Sumire:20210406101512j:plain

〇LateUpdate

LateUpdate関数はUpdate関数と同じで毎フレーム読み込まれる関数です。Updateとの違いはLateUpdate関数の場合Update関数の後に呼ばれます。

void LateUpdate()
    {
        if(!MixedRealityToolkit.IsInitialized)
            return;
        if(!Initialized)
            return;
        
        #region hand tracking

        IMixedRealityInputSystem inputSystem = MixedRealityToolkit.Instance.GetService<IMixedRealityInputSystem>();
        IMixedRealityHandJointService handHointService = (inputSystem as MixedRealityInputSystem).GetDataProvider<IMixedRealityHandJointService>();

        int fingerIndex = 0;
        //Righthand
        foreach (TrackedHandJoint joint in fingerJointTypes)
        {
            ...
        }
}

ここではMRTKのインスタンスが初期化されているかを判断します。

   if(!MixedRealityToolkit.IsInitialized)
            return;

初期化されていない場合処理を終えます。

microsoft.github.io

また[Instalized]がfalseの場合も(初期化がされていない場合)処理を終えます。

 if(!Initialized)
            return;
     IMixedRealityInputSystem inputSystem = MixedRealityToolkit.Instance.GetService<IMixedRealityInputSystem>();
        IMixedRealityHandJointService handJointService = (inputSystem as MixedRealityInputSystem).GetDataProvider<IMixedRealityHandJointService>();

[HandTracking]を取得するために、[IMixedRealityInputSystem]の[GetService]を取得します。

 int fingerIndex = 0;
        // Right hand
        foreach (TrackedHandJoint joint in fingerJointTypes)
        {
            if (handJointService.IsHandTracked(Handedness.Right))
            {
                Transform jointTransform = handJointService.RequestJointTransform(joint, Handedness.Right);
                fingers[fingerIndex].position = jointTransform.position;
                fingers[fingerIndex].rotation = jointTransform.rotation;
                fingers[fingerIndex].gameObject.SetActive(true);
            }
            else if (!Application.isEditor || disableInactiveFingersInEditor)
            {
                fingers[fingerIndex].gameObject.SetActive(false);
            }
            fingerIndex++;
        }
     //左手

その後左右の手の[Tip]を取得してPosition、Rotationを取得し[protected Transform[] fingers]に格納します。

この際使用される[fingerJointTypes]は以下のように各指の先が指定されています。

    protected TrackedHandJoint[] fingerJointTypes = new TrackedHandJoint[]
    {
      TrackedHandJoint.ThumbTip,
      TrackedHandJoint.IndexTip,
      TrackedHandJoint.MiddleTip,
      TrackedHandJoint.RingTip,
      TrackedHandJoint.PinkyTip,
    };