おもちゃラボ

Unityで遊びを作ってます

【Unity】ARKitで水平面か垂直面かを調べる

 ARKitで検出した平面が水平面なのか垂直面なのかを調べて、床面と壁面でことなる平面オブジェクトを作りたいことがあります。

 検出された平面のRotationを確認しても良いのですが、ARKitでは水平面か垂直面かを調べる方法が提供されているので、それを使う方法を紹介します。

f:id:nn_hokuson:20190424194246j:plain

なぜか、写真に収まろうとするコジロー・・・

Unityで平面の方向を調べる

 検出した平面が床面か壁面かは、ARPlaneAnchorクラスのalignmentプロパティで調べることができます。このプロパティはARPlaneAnchorAlignment型で、次のふたつが定義されています

プロパティ 意味
ARPlaneAnchorAlignmentHorizontal 水平面
ARPlaneAnchorAlignmentVertical 垂直面

 

 Unity ARKit Pluginでは平面が検出されると、UnityARUtilityクラスの中のCreatePlaneInSceneメソッドが呼び出されます。このメソッドの引数に渡されるARPlaneAnchorの情報をもとにして平面を作成します。そこで、このCreatePlaneInSceneメソッドの中で、水平面か垂直面かを調べて、作成する平面の色を変えてみましょう。

f:id:nn_hokuson:20190424200152p:plain:w450

水平面か垂直面かを調べる

 UnityARUtilityクラスのCreatePlaneInSceneメソッドを次のように書き換えてください。

public static GameObject CreatePlaneInScene(ARPlaneAnchor arPlaneAnchor)
{    
    GameObject plane;
    if (planePrefab != null) {
        plane = GameObject.Instantiate(planePrefab);
    } else {
        plane = new GameObject (); 
    }

    plane.name = arPlaneAnchor.identifier;

    ARKitPlaneMeshRender apmr = plane.GetComponent<ARKitPlaneMeshRender> ();
    if (apmr != null) {
        apmr.InitiliazeMesh (arPlaneAnchor);
    }

    // 平面の向きによって平面オブジェクトの色を変える
    if(arPlaneAnchor.alignment == ARPlaneAnchorAlignment.ARPlaneAnchorAlignmentVertical)
    {
        plane.transform.Find("Plane").GetComponent<MeshRenderer>().material.color = new Color(1,1,0);
    }
    return UpdatePlaneWithAnchorTransform(plane, arPlaneAnchor);
}

 
 ここではreturnの直前の行で、引数で受け取ったarPlaneAnchorのalignmentプロパティを調べています。alignmentが水平面(ARPlaneAnchorAlignmentHorizontal)なら青色、垂直面(ARPlaneAnchorAlignmentVertical)なら緑色に塗り分けています。

 また、マテリアルの色を指定するため、UnityARKitPlugin/Examples/Common/Prefabs/にあるdebugPlanePrefabのシェーダは「Sprites/Default」に変更しています。

f:id:nn_hokuson:20190424194835p:plain:w450

壁と床で表示するオブジェクトを変えたい場合は・・・

 もし、壁面と床面で生成するオブジェクト自体を変えたい場合は、次のような手順で壁用のPrefabを作成&追加し、CreatePlaneInSceneの中でalignmentを見てPrefabを生成し分ければ、床と壁で違うオブジェクトが表示されます。

  1. UnityARGeneratePlaneに壁用のPrefabを追加
  2. UnityARUtilityにも壁用のPrefabを追加
  3. UnityARUtilityのInitializePlanePrefabで壁用のPrefabも渡せるようにする
  4. インスペクタから壁用のPrefabをセットする

実行してみた

 ちゃんと床と壁で違う色の平面になっていることが確認できました。何回とっても邪魔するよね・・・(笑)
f:id:nn_hokuson:20190424195026j:plain:w450

booth.pm