Unity の QR コード
HoloLens 2 ヘッドセットは、ホログラムやその他の AR 機能を提供するために使用できる QR コードを追跡および検出できます。 この記事では、Unity アプリで QR コードの使用を開始するために知っておくべきすべての手順について説明します。これには、次のものが含まれます。
- Unity アプリに QR コード検出を追加する。
- 使用する必要がある重要な概念と Unity コンポーネントについて説明します。
- 一般的な QR コードの使用方法に関するチュートリアルを提供します。
- QR コード対応のシーンとサンプル スクリプトを示す AR マーカーのサンプル シナリオ について説明します。
この記事に進む前に、 QR コードの概要を確認することをお勧めします。
Unity プロジェクトとアプリの構成
QR コード機能を有効にするには、Unity プロジェクトとアプリを適切に設定して構成する必要があります。これには、次のものが必要です。
- OpenXR for Windows Mixed Reality バージョン 113.2403.5001 以降。
Note
これは OS に付属しており、Windows ストアを通じて更新できます。 ユーザーは以前のバージョンがインストールされている可能性があり、デバイスはバージョン 113.2403.5001 以降に更新されるまで QR コードなどの AR マーカーを使用できません。
- サポートされているバージョンの Unity と互換性のあるプロジェクト:
- Unity 2022.3 LTS (推奨)
- Unity 2021.3 LTS
- Mixed Reality OpenXR プラグイン。
- Unity プロジェクトで Web カメラ機能が有効になっています。
- アプリに付与されたカメラのアクセス許可。
以下のセクションでは、QR コード検出を有効にするように Unity プロジェクトとアプリを構成する方法について説明します。
Mixed Reality OpenXR プラグインの取得
Mixed Reality OpenXR Plugin パッケージには、QR コード機能にアクセスするために使用できる C# API が含まれています。
パッケージをインポートするには、次のようにします。
Mixed Reality 機能ツールを使用すると、パッケージ管理も簡素化され、アプリで必要な Mixed Reality 機能を検索、更新、追加するために使用できます。 ツールの使用方法の詳細については、「 Mixed Reality Feature Tool に関する記事を参照してください。
WebCam 機能の有効化
QR コードを検出して追跡するには、Unity プロジェクトで WebCam 機能が有効になっている必要があります。
WebCam機能を有効にするには:
- Unity プロジェクトを開きます。
- Unity エディターのアプリ メニューで Edit をクリックします。
- Project Settings > Player に移動し次のように UWP タブを選択します。
- Capabilities リストで WebCam を有効にします。
- プロジェクト設定を終了します。
Unity アプリで WebCam 機能が有効になりました。 ただし、デバイス カメラにアクセスするためのアクセス許可がアプリに付与されている必要があります。
アプリ カメラへのアクセス許可の付与
アプリで WebCam 機能が有効になっている場合、アクセス許可ダイアログでは、デバイス カメラへのアクセス権をアプリに付与するようにユーザーに求められます。
このダイアログボックスは、通常、QR コード マーカーがサポートされている ARMarkerManager
を含むシーンを入力する場合 有効に 1 回だけ表示されます。 カメラ アクセスが拒否された場合、ユーザーは Settings > Apps に移動し アプリの Advanced Options を使用して有効にすることができます。
QR コード検出をシーンに組み込む
QR コード検出は、QR コードを使用するすべてのシーンに組み込む必要があります。これには次のものが必要です。
ARMarkerManager
がアタッチされたGameObject
。ARMarkerManager
は、検出された QR コードのすべてのGameObject
を作成、更新、および削除する責任を負います。ARMarker
がアタッチされたプレハブ。ARMarkerManager
QR コードが検出されたときにGameObject
を作成するときにプレハブを使用するように構成されています。
QR コード用のプレハブの作成
シーンで QR コードを使用するには、QR コード用のプレハブを作成する必要があります。 ARMarkerManager
は、このプレハブを使用して、QR コードが検出されるたびに GameObject
を作成します。
QR コードのプレハブを作成するには:
- プロジェクトの新しいプレハブ を作成します。
ARMarker
コンポーネントをプレハブに追加します。このコンポーネントは、microsoft.MixedReality.OpenXR > ARMarker > Script の下にあります。
これで、使用する基本的なプレハブが作成されました。 多くの場合、環境内で検出された QR コードをアプリで視覚的に表す必要があります。 次のセクションでは、QR コードの視覚的表現を追加する方法について説明します。
ビジュアルの追加
前のセクションでは、プレハブに ARMarker
を追加すると、 ARMarkerScale
コンポーネントも自動的に追加されました。 このコンポーネントは、QR コードの視覚的表現のスケールを、対応する物理的な表現と一致させるために使用されます。
そのためには次のようにします。
- 前のセクションで作成したプレハブに空の
GameObject
を追加します。 すべてのビジュアル マーカー コンテンツを表します。 - マーカー コンテンツ
GameObject
に、Quad
などの子 3DGameObject
を追加します。 - プレハブの
ARMarkerScale
コンポーネントで、マーカー コンテンツGameObject
Marker Scale Transform を設定します。 このフィールドを設定すると、選択した 3DGameObject
が実際の QR コードと一致するように正しくスケーリングされます。
シーンに ARMarkerManager
を追加する
ARMarkerManager
は、検出された QR コードのすべての GameObject
を作成、更新、および削除する責任を負います。
シーンに ARMarkerManager
を追加するには:
- シーンに
GameObject
を配置します。 ARMarkerManager
コンポーネントを、Script > Microsoft.MixedReality.OpenXR > ARMarkerManager の下にあるGameObject
に追加します。
ARMarkerManager
Marker Prefab フィールドを前のセクションで作成したプレハブに設定します。- [ Enabled Marker Types を展開し、要素を選択し、 QR コードに設定します。
QR コードの変更を追跡する
ARMarkerManager
には、サブスクライバーにARMarkersChangedEventArgs
を提供するmarkersChanged
イベントが含まれています。 これらのイベント引数を使用して、検出または更新されたポーズ データに対して追加または削除される QR コードを追跡します。
次のコードは、ARMarkerManager.markersChanged
イベントをサブスクライブし、そのイベント引数を使用して、追加、削除、または更新のどちらであるかに関係なく、処理および Debug への書き込みARMarkerManager
ARMarker
オブジェクトを反復処理する方法を示しています。
using System;
using Microsoft.MixedReality.OpenXR;
// ...
private void Awake()
{
m_arMarkerManager = GetComponent<ARMarkerManager>();
m_arMarkerManager.markersChanged += OnQRCodesChanged;
}
void OnQRCodesChanged(ARMarkersChangedEventArgs args)
{
foreach (ARMarker qrCode in args.added)
Debug.Log($"QR code with the ID {qrCode.trackableId} added.");
foreach (ARMarker qrCode in args.removed)
Debug.Log($"QR code with the ID {qrCode.trackableId} removed.");
foreach (ARMarker qrCode in args.updated)
{
Debug.Log($"QR code with the ID {qrCode.trackableId} updated.");
Debug.Log($"Pos:{qrCode.transform.position} Rot:{qrCode.transform.rotation} Size:{qrCode.size}");
}
}
QR コードが最後に検出された時刻を取得する
ARMarker.lastSeenTime
プロパティを使用して、デバイスが最後に検出された QR コードを追跡した時刻と、追跡が失われた時間 (ある場合) を判断します。 Unity がアプリケーションを起動してからの時間は秒数で測定され、 UnityEngine.Time.realtimeSinceStartup
に似ています。
QR コードの追跡可能な ID の使用
QR コードは 追跡可能ですこれは、AR デバイスが物理環境で検出して追跡できるあらゆるものです。 追跡可能オブジェクトは、ID、追跡状態、ポーズ、およびその他のデータを提供する型 ARTrackable<TSessionRelativeData, TTrackable>
から派生します。
QR コードの追跡可能な ID を ARMarkerManager
メソッドに渡して、QR コードのプロパティ、生バイト データ、および文字列表現を取得し、QR コードの変換モードを設定できます。 これらのメソッドを使用すると、 ARMarker
オブジェクト参照を保持することなく、QR コードのデータを取得できます。
QR コードの ID は、次の ARMarkerManager
メソッドに渡すことができます。
GetDecodedString(UnityEngine.XR.ARSubsystems.TrackableId trackableId)
GetMarker(UnityEngine.XR.ARSubsystems.TrackableId trackableId)
GetQRCodeProperties(UnityEngine.XR.ARSubsystems.TrackableId)
GetRawData(UnityEngine.XR.ARSubsystems.TrackableId, Unity.Collections.Allocator)
SetTransformMode(UnityEngine.XR.ARSubsystems.TrackableId, Microsoft.MixedReality.OpenXR.TransformMode)
Note
GetRawData
メソッド パラメーターのallocator
では、ほとんどのシナリオでUnity.Collections.Allocator.Temp
を渡すことで十分です。
QR コードの追跡状態に従う
ARMarker
は追跡可能であるため、trackingState
プロパティを継承し、次の 3 つのUnityEngine.XR.ARSubsystems.TrackingState
のいずれかに設定されます。
Limited
: QR コードが追跡されているが、限られた情報が利用可能であるか、品質が低いかどうかを示します。Tracking
: QR コードが完全に追跡されていることを指定します。None
: QR コードが追跡されていないことを示します。
QR コードの追跡状態を監視するには、 ARMarkerManager.markersChanged
をサブスクライブし、イベント ハンドラーに渡されたイベント引数で提供される ARMarker
マーカー コレクションを反復処理します。
次のコードは、 ARMarkerManager.markersChanged
イベントを使用して、新しく検出された QR コードの ARMarker
オブジェクトを反復処理し、追跡可能な ID をデバッグ ウィンドウに書き込む方法を示しています。
using System;
using Microsoft.MixedReality.OpenXR;
// ...
private void Awake()
{
m_arMarkerManager = GetComponent<ARMarkerManager>();
m_arMarkerManager.markersChanged += OnQRCodesChanged;
}
void OnQRCodesChanged(ARMarkersChangedEventArgs args)
{
foreach (ARMarker qrCode in args.added)
{
if (qrCode.trackingState == UnityEngine.XR.ARSubsystems.TrackingState.Tracking)
Debug.Log($"Fully tracked QR code with the ID {qrCode.trackableId} was added.");
}
}
QR コードのバージョンと QR コードの種類を取得する
検出された QR コードのバージョンと種類を取得するには:
QRCodeProperties
インスタンスを返すARMarker.GetQRCodeProperties()
を呼び出します。- 戻り値のフィールド
QRCodeProperties
にアクセスして、QR コードの型を取得します。 値はQRCodeType.QRCode
またはQRCodeType.MicroQRCode
です。 - 戻り値の
QRCodeProperties.version
フィールドにアクセスして、QR コードのバージョンを取得します。 型がQRCodeType.QRCode
の場合は 1 から 40、型がQRCodeType.MicroQRCode
の場合は 1 から 4 の範囲です。
別の方法として、 ARMarker
オブジェクトの追跡可能な ID を ARMarkerManager.GetQRCodeProperties(TrackableId)
に渡して、QR コードの種類とバージョンを取得します。
警告
QR コードは現在サポートされている唯一のマーカーの種類ですが、他のマーカーの種類のサポートは今後のリリースで追加される可能性があります。 markerType
がARMarkerType.QRCode
されていない場合、GetQRCodeProperties(TrackableId)
を呼び出すとSystem.InvalidOperationException
がスローされます。 後でアプリで問題が発生する可能性がある場合は、try-catch ブロックで GetQRCodeProperties(TrackableId)
の呼び出しをラップすることを検討してください。
QR データの読み取り
ARMarker
コンポーネントは、ARMarkerManager
作成されるすべてのGameObject
にアタッチされます。 ARMarker
には、QR コード データを返す 2 つのメソッドが用意されています。
GetDecodedString()
:このメソッドは、URL などの QR コードの文字列表現を取得します。GetRawData(Unity.Collections.Allocator allocator)
: このメソッドは QR コードの内容をバイト配列として返し、配列の割り当て方法を細かく調整できます。 このメソッドは、ホット パスや、パフォーマンスが重要なその他の状況で使用します。
次のコードは、 GetDecodedString()
と GetRawData(Unity.Collections.Allocator allocator)
の基本的な使用方法を示しています。
using System;
using Microsoft.MixedReality.OpenXR;
// ...
void OnQRCodesChanged(ARMarkersChangedEventArgs args)
{
foreach (ARMarker qrCode in args.added)
{
var text = qrCode.GetDecodedString();
Debug.Log($"QR code text: {text}");
var bytes = qrCode.GetRawData(Unity.Collections.Allocator.Temp);
Debug.Log($"QR code bytes: {bytes.Length}");
bytes.Dispose();
}
}
QR コードのサイズ、位置、回転、および中央を取得する
ARMarker
オブジェクトは、それが表す QR コードのサイズ、位置、回転、および中心を提供します。
QR コードのサイズをメートル単位で取得するには、プロパティ ARMarker.size
を使用します。
ARMarker.transform
プロパティを使用して、QR コードの変換の回転位置とワールド空間位置を取得し、QR コードの変換に対する QR コードの 2D 座標にARMarker.center
します。 変換自体は、 ARMarker.transformMode
( transform モード) が TransformMode.MostStable
( 最も安定、QR コードの左上) または TransformMode.Center
(center QR コードの幾何学的中心) に設定されているかどうかに応じて中央に配置されます。
ARMarkerManager.defaultTransformMode
フィールドを使用して、新しいARMarker
オブジェクトを作成ARMarkerManager
変換モードを設定します。 このフィールドは、次のように Unity インスペクターで Default Transform Mode
フィールドが設定されて初期化されます。
ARMarker.transformMode
を使用する代わりに、ARMarker
オブジェクトの追跡可能な ID を渡して、変換モードを設定ARMarkerManager.SetTransformMode(TrackableId, TransformMode)
。
次のコードは、新しい QR コードのサイズと中心、変換の位置と回転、および変換モードを変更した後の更新された変換位置を取得する方法を示しています。
using System;
using Microsoft.MixedReality.OpenXR;
// ...
void OnMarkersChanged(ARMarkersChangedEventArgs args)
{
Debug.Log($"Default transform mode is {ARMarkerManager.Instance.defaultTransformMode}./n");
if (e.added.Count > 0)
{
ARMarker qrCode = args.added[0];
Debug.Log($"Position: {qrCode.transform.position}");
Debug.Log($"Rotation: {qrCode.transform.rotation}");
Debug.Log($"Center: {qrCode.center}");
if (qrCode.transformMode == TransformMode.Center)
qrCode.transformMode = TransformMode.MostStable;
else
qrCode.transformMode = TransformMode.Center;
Debug.Log($"QR code's transform mode is now set to {qrCode.transformMode}. /n");
Debug.Log($"New position: {qrCode.transform.position}");
}
}
AR マーカーのサンプル シナリオ
OpenXR プラグイン パッケージで提供されるサンプルには、 ARMarkerManager
と ARMarker
を使用する方法の例を示す QR コード対応のシーンが含まれています。
次に示すように、シーンは Assets > ARMarker にあります。
シーンで使用されている C# スクリプトは、GitHub の OpenXR Unity Mixed Reality Samples リポジトリにあります : /OpenXR-Unity-MixedReality-Samples/tree/main/SampleScenarios/Scenarios/MarkerSample/Scripts