対話可能

対話可能

コンポーネントは、 Interactable すべてのオブジェクトを簡単に Interactable し、入力に応答できるようにするためのオールインワンのコンテナーです。 対話型は、タッチ、手の形、音声などを含むすべての種類の入力に対して、キャッチしたものとして機能し、 イベント視覚テーマ の応答に対するこれらの対話をじょうごします。 このコンポーネントを使用すると、ボタンの作成、フォーカスのあるオブジェクトの色の変更などを簡単に行うことができます。

対話型を構成する方法

コンポーネントでは、次の3つの主要な構成セクションが許可されます。

  1. 一般的な入力構成
  2. 複数のオブジェクトを対象としたビジュアルテーマ
  3. イベント ハンドラー

一般的な入力設定

General 対話型設定

状態

Statesは、対話型プロファイルビジュアルテーマに対して、press またはScriptableObjectのような相互作用フェーズを定義するパラメーターです。

Defaultinteractablestates (ASSETS/MRTK/SDK/FEATURES/UX/対話型/States/defaultinteractablestates) には、既定で対話型コンポーネントのパラメーターとして mrtk が付属しています。

Inspector の状態 ScriptableObject の例

Defaultinteractablestates資産には、4つの状態が含まれ、状態モデルの実装を利用し ます。

  • 既定: 何も発生していません。これは最も分離された基本状態です。

  • フォーカス: オブジェクトがポイントされています。 これは1つの状態であり、他の状態は現在設定されていませんが、順位付けの既定値があります。

  • 押されている: オブジェクトがポイントされていて、ボタンまたは手が押されています。 押された状態では、既定とフォーカスが順位付けされます。 この状態は、物理プレスへのフォールバックとしても設定されます。

  • [無効]: ボタンを対話形式にすることはできません。また、何らかの理由でこのボタンを使用できない場合に、視覚的なフィードバックによってユーザーに通知されます。 理論的には、無効状態には他のすべての状態が含まれる可能性がありますが、有効にすると、Disabled 状態は他のすべての状態を勝るます。

リスト内の順序に応じて、状態にビット値 (#) が割り当てられます。

Note

一般に、対話型コンポーネントの作成時には、 defaultinteractablestates (Assets/MRTK/SDK/Features/UX/対話型/States/defaultinteractablestates) を使用することをお勧めします。

ただし、他のコンポーネントによって駆動されることを意図している場合でも、テーマを設定するために使用できる対話型の状態は17個あります。 組み込み機能を持つものの一覧を次に示します。

  • [閲覧済み: 対話型がクリックされました。
  • 切り替え: ボタンが切り替えられた状態またはディメンションのインデックスが奇数です。
  • ジェスチャ: ハンドまたはコントローラーが押され、元の位置から移動しました。
  • VoiceCommand: speech コマンドを使用して対話型をトリガーしました。
  • PhysicalTouch: タッチ入力が現在検出されて NearInteractionTouchable います。を使用してを有効にします。
  • グラブ: 現在、オブジェクトの境界を取得しています。を使用して NearInteractionGrabbable を有効にします。

有効

対話型を有効にするかどうかを切り替えます。 これは、コード内のに対応し Interactable.IsEnabled ます。

対話型のenabled プロパティは、設定オブジェクト/コンポーネント (つまり、setactive など) で構成されている enabled プロパティとは異なります。 設定オブジェクトまたは 対話型 モノの動作を無効にすると、入力、ビジュアルテーマ、イベントなどを含む、クラス内のすべての実行が無効になります。Via を無効にする と、ほとんどの入力処理が無効になり、関連する入力状態がリセットされます。 ただし、クラスは、すべてのフレームを実行し、入力イベントを受信します。これは無視されます。 これは、対話型を無効な状態で表示する場合に便利です。これは、ビジュアルテーマを使用して実行できます。 一般的な例としては、必要なすべての入力フィールドの完了を待機している [送信] ボタンがあります。

入力アクション

対話型コンポーネントが応答する入力構成またはコントローラーマッピングプロファイルから入力アクションを選択します。

このプロパティは、を使用してコードで実行時に構成でき Interactable.InputAction ます。

IsGlobal

True の場合、選択した 入力アクションのグローバル入力リスナーとしてコンポーネントがマークされます。 既定の動作は false です。この場合、入力はこの対話型 collider/ オブジェクトのみに制限されます。

このプロパティは、を使用してコードで実行時に構成でき Interactable.IsGlobal ます。

Speech コマンド

音声を操作するために OnClick イベントをトリガーする、MRTK Speech コマンドプロファイルのspeech コマンド

このプロパティは、を使用してコードで実行時に構成でき Interactable.VoiceCommand ます。

フォーカスが必要

True の場合、音声コマンドは、ポインターから既にフォーカスがある場合にのみ、 対話型 をアクティブにします。 False の場合、 対話型 は選択された音声コマンドのグローバルリスナーとして機能します。 複数のグローバル音声リスナーをシーンで整理するのが難しいため、既定の動作は true です。

このプロパティは、を使用してコードで実行時に構成でき Interactable.VoiceRequiresFocus ます。

選択モード

このプロパティは、選択ロジックを定義します。 対話型をクリックすると、次のディメンションレベルに反復処理されます。 ディメンション はランクに似ており、入力外の状態を定義します (つまり、フォーカスやプレスなど)。 これは、ボタンに関連付けられているトグル状態やその他の複数ランクの状態を定義する場合に便利です。 現在のディメンションレベルは、によって追跡され Interactable.DimensionIndex ます。

選択できるモードは次のとおりです。

  • ボタンディメンション= 1、単純なクリック可能な対話型
  • 切り替えディメンション= 2、対話型がオフの状態を切り替えます
  • 複数次元ディメンション= 3 の場合、クリックするたびに現在のディメンションレベル + 1 が増加します。 リストにボタンの状態を定義する場合に便利です。

対話型 では、 ディメンションごとに複数のテーマを定義することもできます。 たとえば、 SelectionMode = トグルの場合、 対話型 を選択 解除 し、コンポーネントを 選択したときに別のテーマを適用すると、1つのテーマが適用されることがあります。

現在の選択モードは、を使用して実行時に照会でき Interactable.ButtonMode ます。 実行時にモードを更新するには、 Interactable.Dimensions 目的の機能に合わせてプロパティを設定します。 さらに、現在のディメンションは、 トグル モードと 多次元 モードに便利です。また、を使用してアクセスでき ます。

対話型プロファイル

プロファイル は、作成オブジェクトと ビジュアルテーマの間にリレーションシップを作成するアイテムです。 プロファイルでは、 状態の変更が発生したときにテーマによって操作されるコンテンツを定義します。

テーマは、素材によく似ています。 これらは、現在の状態に基づいてオブジェクトに割り当てられるプロパティの一覧を含む、スクリプト可能なオブジェクトです。 また、テーマは再利用可能であり、複数の 対話型 UX オブジェクトに割り当てることができます。

破棄時にリセット

ビジュアルテーマは、選択したテーマエンジンのクラスと種類に応じて、対象となるオブジェクトのさまざまなプロパティを変更します。 対話型コンポーネントが破棄されたとき に Reset On Destroy が true の場合、コンポーネントは、変更されたすべてのプロパティをアクティブテーマから元の値にリセットします。 それ以外の場合、対話型コンポーネントを破棄すると、変更されたプロパティはそのまま残ります。 後者の場合、値の最後の状態は、別の外部コンポーネントによって変更されない限り保持されます。 既定値は false です。

Theams のプロファイル

イベント

すべての 対話型 コンポーネントには、コンポーネントが単純に選択されたときに発生する OnClick イベントがあります。 ただし、 対話型 を使用して、単に OnClick以外の入力イベントを検出することができます。

[ イベントの追加 ] ボタンをクリックして、新しい種類のイベントレシーバー定義を追加します。 追加したら、目的のイベントの種類を選択します。

イベントの例)

さまざまな種類の入力に応答するためのさまざまな種類のイベントレシーバーがあります。 MRTK には、次の一連のレシーバーが付属しています。

カスタムレシーバーは、を拡張する新しいクラスを作成することによって作成でき ReceiverBase ます。

イベント切り替えレシーバーの例

トグル イベント レシーバーの例

対話可能な受信者

コンポーネント InteractableReceiver を使用すると、ソースの InteractableReceiver コンポーネントの外部でイベントを定義できます。 InteractableReceiver は、別の Interactable によって発生したフィルター処理されたイベントの種類をリッスンしますInteractableプロパティが直接割り当てられていない場合、検索スコープ プロパティは、それ自体、親、または子 GameObject にあるイベントをInteractableReceiverがリッスンする方向を定義します。

InteractableReceiverList は同様の方法で動作しますが、一致するイベントの一覧に対して機能します。

対話可能な再設定

カスタム イベントを作成する

Visual Themes と同様に、イベントを拡張して、任意の状態パターンを検出したり、機能を公開したりすることができます。

カスタム イベントは、主に次の 2 つの方法で作成できます。

  1. クラスを ReceiverBase 拡張して、イベントの種類のドロップダウン リストに表示されるカスタム イベントを作成します。 Unity イベントは既定で提供されますが、追加の Unity イベントを追加するか、 イベントを設定して Unity イベントを非表示にできます。 この機能により、デザイナーはプロジェクトのエンジニアと一緒に作業し、エディターでデザイナーが設定できるカスタム イベントを作成できます。

  2. クラスを拡張して、Interactable または別のオブジェクトに存在できる完全にカスタム の ReceiverBaseMonoBehavior イベント コンポーネントを作成します。 ReceiverBaseMonoBehaviorReceiverBaseMonoBehavior 、状態の変化 ReceiverBaseMonoBehavior を参照します。

拡張の例 ReceiverBase

クラス CustomInteractablesReceiver は、Interactable に関する状態 CustomInteractablesReceiver し、カスタム イベント レシーバーを作成する方法の例です。

public CustomInteractablesReceiver(UnityEvent ev) : base(ev, "CustomEvent")
{
    HideUnityEvents = true; // hides Unity events in the receiver - meant to be code only
}

次のメソッドは、カスタム イベント レシーバーを作成するときにオーバーライドまたは実装する場合に便利です。 ReceiverBase.OnUpdate() は、状態パターン/遷移を検出するために使用できる抽象メソッドです。 さらに、 メソッドと メソッドは、Interactable が選択されている場合にカスタム イベント ロジック ReceiverBase.OnVoiceCommand()ReceiverBase.OnClick()ReceiverBase.OnVoiceCommand() に便利です。

public override void OnUpdate(InteractableStates state, Interactable source)
{
    if (state.CurrentState() != lastState)
    {
        // the state has changed, do something new
        lastState = state.CurrentState();
        ...
    }
}

public virtual void OnVoiceCommand(InteractableStates state, Interactable source,
                                    string command, int index = 0, int length = 1)
{
    base.OnVoiceCommand(state, source, command, index, length);
    // voice command called, perform some action
}  

public virtual void OnClick(InteractableStates state,
                            Interactable source,
                            IMixedRealityPointer pointer = null)
{
    base.OnClick(state, source);
    // click called, perform some action
}
インスペクターでのカスタム イベントレシーバー フィールドの表示

ReceiverBase スクリプト では、 属性を使用してインスペクターでカスタム プロパティを公開します。 ツールヒントとラベル情報を含むカスタム プロパティである Vector3 の例を次に示します。 このプロパティは 、Interactable GameObject が選択され、関連するイベント レシーバーの種類が追加されている場合、インスペクターに構成 可能 として表示されます。

[InspectorField(Label = "<Property label>",Tooltip = "<Insert tooltip info>",Type = InspectorField.FieldTypes.Vector3)]
public Vector3 EffectOffset = Vector3.zero;

Interactable を使用する方法

単純なボタンの作成

入力イベントを受信するように構成された GameObject に Interactable コンポーネントを追加することで、単純なボタンを作成できます。 入力を受け取るコライダーまたは子にコライダーを設定できます。 Unity UI ベースの GameObjects で Interactable を使用する場合は、Canvas GameObject の下に存在する必要があります。

ボタンをさらに一歩進め、新しいプロファイルを作成し、GameObject 自体を割り当て、新しいテーマを作成します。 さらに 、OnClick イベントを使用 して何かを行います。

Note

ボタンを押 し可能にするには、 コンポーネントが必要 です。 さらに PhysicalPressEventRouter 、Interactable コンポーネントにイベントをファネルで押し込むには、 PhysicalPressEventRouter です。

切り替えボタンと複数次元ボタンの作成

トグル ボタン

ボタンを切り替え可能にするには、フィールドを Selection Mode 「」と入力します Toggle 。 [プロファイル] セクションでは、Interactable がオンに切り替え時に使用されるプロファイルごとに、新しい切り替えテーマが追加されます。

SelectionMode Toggle に設定されている間 SelectionMode チェック ボックスを使用して、実行時の初期化時にコントロールの既定値を設定できます。

CanSelect、Interactable がオフからオンに切り替え、CanDeselectは逆を意味します。

プロファイルの切り替えビジュアル テーマの例

開発者は、 インターフェイスと SetToggled インターフェイスを IsToggled 利用して、コードを介して Interactable のトグル状態 SetToggled 設定できます。

// If using SelectionMode = Toggle (i.e Dimensions == 2)

// Make the Interactable selected and toggled on
myInteractable.IsToggled = true;

// Get whether the Interactable is selected or not
bool isSelected = myInteractable.IsToggled;
切り替えボタンのコレクション

一般的に、任意の時点でアクティブにできるトグル ボタン (放射状セットやラジオ ボタンなど) の一覧が表示されます。

この機能 InteractableToggleCollection を有効にするには、 コンポーネントを使用します。 このコントロールを使用すると、 任意の時点で 1 つの Interactable のみをオンに切り替える必要があります。 RadialSet (Assets/MRTK/SDK/Features/UX/Interactable/Prefabs/RadialSet.prefab) も、最初から始めるのに最適です。

カスタム放射状ボタン グループを作成するには:

  1. 複数の 対話可能 な GameObject/ボタンを作成する
  2. SelectionMode = Toggle、CanSelect = true、およびCanDeselect = false で各対話可能を設定します
  3. すべての Interactable に対して空の親 GameObject を作成し、InteractableToggleCollection コンポーネントを追加します
  4. InteractableToggleCollectionToggleListにすべての Interactable を追加する
  5. InteractableToggleCollection.CurrentIndexプロパティを設定して、開始時に既定で選択されているボタンを決定します
コレクションの切り替え

多次元ボタン

複数次元選択モードは、シーケンシャル ボタン、または 3 つの値 (高速 (1x)、高速 (2x)、または最速 (3 倍) で速度を制御するボタンなど、2 つ以上のステップを持つボタンを作成するために使用されます。

ディメンションが数値の場合、ステップごとに異なるテーマを使用して、速度設定ごとにボタンのテキスト ラベルまたはテクスチャを制御するために、最大 9 つのテーマを追加できます。

すべてのクリック イベントは、値 DimensionIndex に達するまで実行時に を 1 Dimensions 進します。 その後、サイクルは 0 にリセットされます。

多次元プロファイルの例

開発者は を評価して DimensionIndex 、現在アクティブなディメンションを判断できます。

// If using SelectionMode = Multi-dimension (i.e Dimensions >= 3)

//Access the current DimensionIndex
int currentDimension = myInteractable.CurrentDimension;

//Set the current DimensionIndex to 2
myInteractable.CurrentDimension = 2;

// Promote Dimension to next level
myInteractable.IncreaseDimension();

実行時に Interactable を作成する

Interactable は、実行時に任意の GameObject に簡単に追加できます。 次の例では、ビジュアル テーマ を使用してプロファイルを割り当てる方法 を示します

var interactableObject = GameObject.CreatePrimitive(PrimitiveType.Cylinder);
var interactable = interactableObject.AddComponent<Interactable>();

// Get the default configuration for the Theme engine InteractableColorTheme
var newThemeType = ThemeDefinition.GetDefaultThemeDefinition<InteractableColorTheme>().Value;

// Define a color for every state in our Default Interactable States
newThemeType.StateProperties[0].Values = new List<ThemePropertyValue>()
{
    new ThemePropertyValue() { Color = Color.black},  // Default
    new ThemePropertyValue() { Color = Color.black}, // Focus
    new ThemePropertyValue() { Color = Random.ColorHSV()},   // Pressed
    new ThemePropertyValue() { Color = Color.black},   // Disabled
};

interactable.Profiles = new List<InteractableProfileItem>()
{
    new InteractableProfileItem()
    {
        Themes = new List<Theme>()
        {
            Interactable.GetDefaultThemeAsset(new List<ThemeDefinition>() { newThemeType })
        },
        Target = interactableObject,
    },
};

// Force the Interactable to be clicked
interactable.TriggerOnClick()

コードを使用した対話可能なイベント

次の例を使用して、コードを使用 Interactable.OnClick して基本イベントにアクションを追加できます。

public static void AddOnClick(Interactable interactable)
{
    interactable.OnClick.AddListener(() => Debug.Log("Interactable clicked"));
}

関数を Interactable.AddReceiver<T>() 使用して、実行時にイベント レシーバーを動的に追加します。

次のコード例では、フォーカスの入力/終了をリッスンし、さらにイベント インスタンスが発生するときに実行するアクション コードを定義する InteractableOnFocusReceiverを追加する方法を示します。

public static void AddFocusEvents(Interactable interactable)
{
    var onFocusReceiver = interactable.AddReceiver<InteractableOnFocusReceiver>();

    onFocusReceiver.OnFocusOn.AddListener(() => Debug.Log("Focus on"));
    onFocusReceiver.OnFocusOff.AddListener(() => Debug.Log("Focus off"));
}

次のコード例では、切り替え可能なInteractableで選択または選択解除された状態遷移をリッスンし、さらにイベント インスタンスが発生するときに実行するアクション コードを定義するInteractableOnToggleReceiverを追加する方法を示します。

public static void AddToggleEvents(Interactable interactable)
{
    var toggleReceiver = interactable.AddReceiver<InteractableOnToggleReceiver>();

    // Make the interactable have toggle capability, from code.
    // In the gui editor it's much easier
    interactable.Dimensions = 2;
    interactable.CanSelect = true;
    interactable.CanDeselect  = true;

    toggleReceiver.OnSelect.AddListener(() => Debug.Log("Toggle selected"));
    toggleReceiver.OnDeselect.AddListener(() => Debug.Log("Toggle un-selected"));
}

関連項目