diff --git a/Packages/com.unity.inputsystem/Documentation~/TableOfContents.md b/Packages/com.unity.inputsystem/Documentation~/TableOfContents.md index 4af1bb1d6f..e9b7846bd7 100644 --- a/Packages/com.unity.inputsystem/Documentation~/TableOfContents.md +++ b/Packages/com.unity.inputsystem/Documentation~/TableOfContents.md @@ -9,10 +9,10 @@ * [Workflow - Direct](using-direct-workflow.md) * [Setting up input](setting-up-input.md) * [Actions](actions.md) - * [Action Assets](action-assets.md) + * [Action assets](action-assets.md) * [About action assets](about-action-assets.md) * [About project-wide actions](about-project-wide-actions.md) - * [Create and assign project-wide actions](create-project-wide-actions.md) + * [Create and assign a project-wide action asset](create-project-wide-actions.md) * [Create an empty action asset](create-empty-action-asset.md) * [Assign a project-wide action asset](assign-project-wide-actions.md) * [Default actions](default-actions.md) @@ -20,11 +20,28 @@ * [Create action maps](create-edit-delete-action-maps.md) * [Create, edit and delete actions](create-edit-delete-actions.md) * [Configure actions](configure-actions.md) + * [Action and control types](action-and-control-types.md) + * [About action and control types](about-action-control-types.md) + * [Configure action type](configure-action-type.md) + * [Action types reference](action-type-reference.md) + * [Configure control type](configure-control-type.md) + * [Bindings](bindings.md) + * [Introduction to bindings](introduction-to-bindings.md) + * [Binding types](binding-types.md) + * [Composite bindings](composite-bindings-reference.md) + * [Add, duplicate or delete a binding](add-duplicate-delete-binding.md) + * [Select a control for binding](select-control-binding.md) + * [Edit composite bindings](edit-composite-bindings.md) + * [Group bindings to control schemes](group-binding-to-control-scheme.md) + * [Binding resolution](binding-resolution.md) + * [Restrict binding to a specific device](restrict-binding-specific-device.md) + * [Binding conflicts](binding-conflicts.md) + * [Initial state checks](binding-initial-state-checks.md) * [Stand-alone actions](stand-alone-actions.md) * [Load actions from JSON](load-actions-from-json.md) * [Create actions in code](create-actions-in-code.md) * [Action properties](action-and-control-types.md) - * [Bindings](action-bindings.md) + * [Bindings](ActionBindings-Old-Content.md) * [Controls](controls.md) * [Controls schemes](control-schemes.md) * [Interactions](interactions.md) diff --git a/Packages/com.unity.inputsystem/Documentation~/about-action-control-types.md b/Packages/com.unity.inputsystem/Documentation~/about-action-control-types.md new file mode 100644 index 0000000000..07e7899b71 --- /dev/null +++ b/Packages/com.unity.inputsystem/Documentation~/about-action-control-types.md @@ -0,0 +1,22 @@ +# About action and control types + +Each action has an **action type** and a **control type**. These settings are displayed in the [Action Properties panel](./action-properties-panel.md) when you select an action in the [Actions Editor window](./actions-editor.md). + +![The Action Properties panel in the Actions Editor Window](Images/ActionProperties.png) + +When you configure an action, you can select an action type and control type that best represents what your action is for, and how you want it to be activated by the [controls](./Controls.md) it is [bound](./bindings.md) to. + +## Action type + +The **action type** influences how the Input System processes state changes for the action, and relates to whether this action represents a discrete on/off button-style interaction or a value that can change gradually over time. + +## Control type + +The **control type** determines the type of value that should be sent to the action, such as an in integer or float value, or a 1D, 2D, or 3D axis. + +The control type that you select has the effect of filtering the available controls to only those that are capable of providing the values appropriate for that control. + +For example, if you select **2D axis** as the control type, only those types of controls that can supply a 2D vector as value are available as options for the binding control path, such as a thumb stick or Dpad. + +There are more specific control types available which further filter the available bindings, such as **Stick**, **Dpad** or **Touch**. If you select one of these control types, the list of available controls is further limited to only those controls of those specific types when you [select a binding for your action](add-duplicate-delete-binding.md). + diff --git a/Packages/com.unity.inputsystem/Documentation~/action-and-control-types.md b/Packages/com.unity.inputsystem/Documentation~/action-and-control-types.md index e054645568..e55e26e335 100644 --- a/Packages/com.unity.inputsystem/Documentation~/action-and-control-types.md +++ b/Packages/com.unity.inputsystem/Documentation~/action-and-control-types.md @@ -1,13 +1,13 @@ # Action and control types - - - -If you select an action in the actions pane of the [Actions Editor window](actions-editor.md), the right-hand pane displays the action-properties-panel.mdn-properties-panel.md) panel. - -![Action Properties](Images/ActionProperties.png) +Actions have an **Action Type** and **Control Type** which you can configure in the [Actions Editor window](actions-editor.md). These settings allow you to configure the basic behaviour of an action. | **Topic** | **Description** | | :------------------------------ | :------------------------------- | -| **[Configure action type](./configure-action-type.md)** | Summary | -| **[Configure control type](./configure-control-type.md.md)** | Summary | +| **[About action and control types](./about-action-control-types.md)** | Learn about what action types and control types are, and the effects that the different settings can have. | +| **[Configure action type](./configure-action-type.md)** | Configure the action's Action Type, which relates to whether an action represents a discrete on/off button-style interaction or a value that can change gradually over time. | +| **[Action type reference](./action-type-reference.md)** | Information about each of the available action type options. | +| **[Configure control type](./configure-control-type.md.md)** | Select the type of control expected by the action. | + +## Additional resources +[Control types reference](./control-types.md) diff --git a/Packages/com.unity.inputsystem/Documentation~/action-bindings.md b/Packages/com.unity.inputsystem/Documentation~/action-bindings.md deleted file mode 100644 index 0b5016d8a1..0000000000 --- a/Packages/com.unity.inputsystem/Documentation~/action-bindings.md +++ /dev/null @@ -1,227 +0,0 @@ ---- -uid: input-system-action-bindings ---- -# Action Bindings - -- [Composite Bindings](#composite-bindings) - - [1D axis](#1d-axis) - - [2D vector](#2d-vector) - - [3D vector](#3d-vector) - - [One Modifier](#one-modifier) - - [Two Modifiers](#two-modifiers) - - [Writing custom Composites](#writing-custom-composites) -- [Working with Bindings](#working-with-bindings) -- [Looking up Bindings](#looking-up-bindings) -- [Changing Bindings](#changing-bindings) - - [Applying overrides](#applying-overrides) - - [Erasing Bindings](#erasing-bindings) - - [Adding Bindings](#adding-bindings) - - [Setting parameters](#setting-parameters) -- [Interactive rebinding](#interactive-rebinding) -- [Saving and loading rebinds](#saving-and-loading-rebinds) - - [Restoring original Bindings](#restoring-original-bindings) - - [Displaying Bindings](#displaying-bindings) -- [Control Schemes](#control-schemes) -- [Details](#details) - - [Binding resolution](#binding-resolution) - - [Conflicting inputs](#conflicting-inputs) - - [Initial state check](#initial-state-check) - - -### Bindings - -* To add a new Binding, select the Add (+) icon on the action you want to add it to, and select the binding type from the menu that appears. -* To delete an existing Binding, either right-click it and select __Delete__ from the context menu. -* To duplicate an existing Binding, either right-click it and select __Duplicate__ from the context menu. - -You can add multiple bindings to an action, which is generally useful for supporting multiple types of input device. For example, in the default set of actions, the "Move" action has a binding to the left gamepad stick and the WSAD keys, which means input through any of these bindings will perform the action. - -![The default "move" action with its multiple bindings highlighted](./Images/ActionWithMultipleBindings.png)
-_The default "Move" action in the Actions Editor window, displaying the multiple bindings associated with it._ - -If you select a Binding, you can edit its properties in the right-hand pane of the window: - -![Binding Properties](Images/BindingProperties.png) - - - - - -An [`InputBinding`](../api/UnityEngine.InputSystem.InputBinding.html) represents a connection between an [Action](actions.md) and one or more [Controls](Controls.md) identified by a [Control path](Controls.md#control-paths). For example, the **right trigger** of a gamepad (a control) might be bound to an an action named "accelerate", so that pulling the right trigger causes a car to accelerate in your game. - -You can add multiple bindings to an action, which is generally useful for supporting multiple types of input device. For example, in the default set of actions, the "Move" action has a binding to the left gamepad stick and the WSAD keys, which means input through any of these bindings will perform the action. - -You can also bind multiple controls from the same device to an action. For example, both the left and right trigger of a gamepad could be mapped to the same action, so that pulling either trigger has the same result in your game. - -![The default "move" action with its multiple bindings highlighted](./Images/ActionWithMultipleBindings.png)
-_The default "Move" action in the Actions Editor window, displaying the multiple bindings associated with it._ - - -Each Binding has the following properties: - -|Property|Description| -|--------|-----------| -|[`path`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_path)|[Control path](Controls.md#control-paths) that identifies the control(s) from which the Action should receive input.

Example: `"/leftStick"`| -|[`overridePath`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_overridePath)|[Control path](Controls.md#control-paths) that overrides `path`. Unlike `path`, `overridePath` is not persistent, so you can use it to non-destructively override the path on a Binding. If it is set to something other than null, it takes effect and overrides `path`. To get the path which is currently in effect (that is, either `path` or `overridePath`), you can query the [`effectivePath`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_effectivePath) property.| -|[`action`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_action)|The name or ID of the Action that the Binding should trigger. Note that this can be null or empty (for instance, for [composites](#composite-bindings)). Not case-sensitive.

Example: `"fire"`| -|[`groups`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_groups)|A semicolon-separated list of Binding groups that the Binding belongs to. Can be null or empty. Binding groups can be anything, but are mostly used for [Control Schemes](#control-schemes). Not case-sensitive.

Example: `"Keyboard&Mouse;Gamepad"`| -|[`interactions`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_interactions)|A semicolon-separated list of [Interactions](Interactions.md) to apply to input on this Binding. Note that Unity appends Interactions applied to the [Action](actions.md) itself (if any) to this list. Not case-sensitive.

Example: `"slowTap;hold(duration=0.75)"`| -|[`processors`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_processors)|A semicolon-separated list of [Processors](Processors.md) to apply to input on this Binding. Note that Unity appends Processors applied to the [Action](actions.md) itself (if any) to this list. Not case-sensitive.

Processors on Bindings apply in addition to Processors on Controls that are providing values. For example, if you put a `stickDeadzone` Processor on a Binding and then bind it to `/leftStick`, you get deadzones applied twice: once from the deadzone Processor sitting on the `leftStick` Control, and once from the Binding.

Example: `"invert;axisDeadzone(min=0.1,max=0.95)"`| -|[`id`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_id)|Unique ID of the Binding. You can use it to identify the Binding when storing Binding overrides in user settings, for example.| -|[`name`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_name)|Optional name of the Binding. Identifies part names inside [Composites](#composite-bindings).

Example: `"Positive"`| -|[`isComposite`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_isComposite)|Whether the Binding acts as a [Composite](#composite-bindings).| -|[`isPartOfComposite`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_isPartOfComposite)|Whether the Binding is part of a [Composite](#composite-bindings).| - -To query the Bindings to a particular Action, you can use [`InputAction.bindings`](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction_bindings). To query a flat list of Bindings for all Actions in an Action Map, you can use [`InputActionMap.bindings`](../api/UnityEngine.InputSystem.InputActionMap.html#UnityEngine_InputSystem_InputActionMap_bindings). - - -### Erasing Bindings - -You can erase a binding by calling [`Erase`](../api/UnityEngine.InputSystem.InputActionSetupExtensions.BindingSyntax.html#UnityEngine_InputSystem_InputActionSetupExtensions_BindingSyntax_Erase_) on the [binding accessor](../api/UnityEngine.InputSystem.InputActionSetupExtensions.BindingSyntax.html). - -```CSharp -// Erase first binding on "fire" action. -playerInput.actions["fire"].ChangeBinding(0).Erase(); - -// Erase "2DVector" composite. This will also erase the part -// bindings of the composite. -playerInput.actions["move"].ChangeCompositeBinding("2DVector").Erase(); - -// Can also do this by using the name given to the composite binding. -playerInput.actions["move"].ChangeCompositeBinding("WASD").Erase(); - -// Erase first binding in "gameplay" action map. -playerInput.actions.FindActionMap("gameplay").ChangeBinding(0).Erase(); -``` - -### Adding Bindings - -New bindings can be added to an Action using [`AddAction`](../api/UnityEngine.InputSystem.InputActionSetupExtensions.html#UnityEngine_InputSystem_InputActionSetupExtensions_AddBinding_UnityEngine_InputSystem_InputAction_System_String_System_String_System_String_System_String_) or [`AddCompositeBinding`](../api/UnityEngine.InputSystem.InputActionSetupExtensions.html#UnityEngine_InputSystem_InputActionSetupExtensions_AddCompositeBinding_UnityEngine_InputSystem_InputAction_System_String_System_String_System_String_). - -```CSharp -// Add a binding for the left mouse button to the "fire" action. -playerInput.actions["fire"].AddBinding("/leftButton"); - -// Add a WASD composite binding to the "move" action. -playerInput.actions["move"] - .AddCompositeBinding("2DVector") - .With("Up", "/w") - .With("Left", "/a") - .With("Down", "/s") - .With("Right", "/d"); -``` - -### Setting parameters - -A Binding may, either through itself or through its associated Action, lead to [processor](Processors.md), [interaction](Interactions.md), and/or [composite](#composite-bindings) objects being created. These objects can have parameters you can configure through in the [Binding properties view](ActionsEditor.md#bindings) of the Action editor or through the API. This configuration will give parameters their default value. - -```CSharp -// Create an action with a "Hold" interaction on it. -// Set the "duration" parameter to 4 seconds. -var action = new InputAction(interactions: "hold(duration=4)"); -``` - -You can query the current value of any such parameter using the [`GetParameterValue`](../api/UnityEngine.InputSystem.InputActionRebindingExtensions.html#UnityEngine_InputSystem_InputActionRebindingExtensions_GetParameterValue_UnityEngine_InputSystem_InputAction_System_String_UnityEngine_InputSystem_InputBinding_) API. - -```CSharp -// This returns a PrimitiveValue?. It will be null if the -// parameter is not found. Otherwise, it is a PrimitiveValue -// which can be converted to a number or boolean. -var p = action.GetParameterValue("duration"); -Debug.Log("'duration' is set to: " + p.Value); -``` - -The above looks for the parameter on any object found on any of the bindings on the action. You can restrict either or both to a more narrow set. - -```CSharp -// Retrieve the value of the "duration" parameter specifically of a -// "Hold" interaction and only look on bindings in the "Gamepad" group. -action.GetParameterValue("hold:duration", InputBinding.MaskByGroup("Gamepad")); -``` - -Alternatively, you can use an expression parameter to encapsulate both the type and the name of the parameter you want to get the value of. This has the advantage of not needing a string parameter but rather references both the type and the name of the parameter in a typesafe way. - -```CSharp -// Retrieve the value of the "duration" parameter of TapInteraction. -// This version returns a float? instead of a PrimitiveValue? as it -// sees the type of "duration" at compile-time. -action.GetParameterValue((TapInteraction x) => x.duration); -``` - -To alter the current value of a parameter, you can use what is referred to as a "parameter override". You can apply these at the level of an individual [`InputAction`](../api/UnityEngine.InputSystem.InputAction.html), or at the level of an entire [`InputActionMap`](../api/UnityEngine.InputSystem.InputActionMap.html), or even at the level of an entire [`InputActionAsset`](../api/UnityEngine.InputSystem.InputActionAsset.html). Such overrides are stored internally and applied automatically even on bindings added later. - -To add an override, use the [`ApplyParameterOverride`](../api/UnityEngine.InputSystem.InputActionRebindingExtensions.html#UnityEngine_InputSystem_InputActionRebindingExtensions_ApplyParameterOverride_UnityEngine_InputSystem_InputAction_System_String_UnityEngine_InputSystem_Utilities_PrimitiveValue_UnityEngine_InputSystem_InputBinding_) API or any of its overloads. - -```CSharp -// Set the "duration" parameter on all bindings of the action to 4. -action.ApplyParameterOverride("duration", 4f); - -// Set the "duration" parameter specifically for "tap" interactions only. -action.ApplyParameterOverride("tap:duration", 0.5f); - -// Set the "duration" parameter on tap interactions but only for bindings -// in the "Gamepad" group. -action.ApplyParameterOverride("tap:duration", 0.5f, InputBinding.MaskByGroup("Gamepad"); - -// Set tap duration for all bindings in an action map. -map.ApplyParameterOverride("tap:duration", 0.5f); - -// Set tap duration for all bindings in an entire asset. -asset.ApplyParameterOverride("tap:duration", 0.5f); - -// Like for GetParameterValue, overloads are available that take -// an expression instead. -action.ApplyParameterOverride((TapInteraction x) => x.duration, 0.4f); -map.ApplyParameterOverride((TapInteraction x) => x.duration, 0.4f); -asset.ApplyParameterOverride((TapInteraction x) => x.duration, 0.4f); -``` - -The new value will be applied immediately and affect all composites, processors, and interactions already in use and targeted by the override. - -Note that if multiple parameter overrides are applied – especially when applying some directly to actions and some to maps or assets –, there may be conflicts between which override to apply. In this case, an attempt is made to chose the "most specific" override to apply. - -```CSharp -// Let's say you have an InputAction `action` that is part of an InputActionAsset asset. -var map = action.actionMap; -var asset = map.asset; - -// And you apply a "tap:duration" override to the action. -action.ApplyParameterOverride("tap:duration", 0.6f); - -// But also apply a "tap:duration" override to the action specifically -// for bindings in the "Gamepad" group. -action.ApplyParameterOverride("tap:duration", 1f, InputBinding.MaskByGroup("Gamepad")); - -// And finally also apply a "tap:duration" override to the entire asset. -asset.ApplyParameterOverride("tap:duration", 0.3f); - -// Now, bindings on `action` in the "Gamepad" group will use a value of 1 for tap durations, -// other bindings on `action` will use 0.6, and every other binding in the asset will use 0.3. -``` - -You can use parameter overrides, for example, to scale mouse delta values on a "Look" action. - -```CSharp -// Set up an example "Look" action. -var look = new InputAction("look", type: InputActionType.Value); -look.AddBinding("/delta", groups: "KeyboardMouse", processors: "scaleVector2"); -look.AddBinding("/rightStick", groups: "Gamepad", processors: "scaleVector2"); - -// Now you can adjust stick sensitivity separately from mouse sensitivity. -look.ApplyParameterOverride("scaleVector2:x", 0.5f, InputBinding.MaskByGroup("KeyboardMouse")); -look.ApplyParameterOverride("scaleVector2:y", 0.5f, InputBinding.MaskByGroup("KeyboardMouse")); - -look.ApplyParameterOverride("scaleVector2:x", 2f, InputBinding.MaskByGroup("Gamepad")); -look.ApplyParameterOverride("scaleVector2:y", 2f, InputBinding.MaskByGroup("Gamepad")); - -// Alternative to using groups, you can also apply overrides directly to specific binding paths. -look.ApplyParameterOverride("scaleVector2:x", 0.5f, new InputBinding("/delta")); -look.ApplyParameterOverride("scaleVector2:y", 0.5f, new InputBinding("/delta")); -``` - ->NOTE: Parameter overrides are *not* persisted along with an asset. - - - - - diff --git a/Packages/com.unity.inputsystem/Documentation~/action-type-reference.md b/Packages/com.unity.inputsystem/Documentation~/action-type-reference.md new file mode 100644 index 0000000000..19087615b5 --- /dev/null +++ b/Packages/com.unity.inputsystem/Documentation~/action-type-reference.md @@ -0,0 +1,18 @@ +# Action Types reference + +With an action selected in the [Actions Editor window](./actions-editor.md), the **Action Type** setting in the [actions panel](./actions-panel.md) allows you to [select the action type](./configure-action-type.md) from the following options: + + +| Value | Description | +| :---------------------------- | :----------------------------- | +| **Button** | Use this for device controls such as keyboard keys, mouse clicks, or gamepad buttons, which have only an on/off state, and no gradual value changes. Provides phase information and conflict resolution. | +| **Value** | Use this for device controls such as mouse movement, a joystick or gamepad stick, or device orientation that provides gradually changing input over a range of values. Provides phase information and conflict resolution. | +| **Pass Through** | Use this for the same types as **Value**, but this type provides no phase information or conflict resolution. | + +### Phase information and conflict resolution + +For **Button** or **Value** action types, the Input System also provides data about the action such as whether it has started and stopped (known as the **Phase** of the action), and [conflict resolution](./binding-conflicts.md) in situations where you have mapped multiple bindings to the same action. + +For **Pass Through** action types, the Input System only provides basic information about the values incoming from the device controls bound to it, and does not provide the extra data relating to the phase of the action, nor does it perform [conflict resolution](./binding-conflicts.md). + +Because pass-through actions don't perform conflict resolution, it means they don't use concept of a specific control driving the action. Instead, any change to any of the controls bound to the action triggers a callback with that Control's value. This is useful if you want to process all input from a set of controls at once on the same action, rather than only the most actuated from the set. diff --git a/Packages/com.unity.inputsystem/Documentation~/actions-editor.md b/Packages/com.unity.inputsystem/Documentation~/actions-editor.md index b7675ef640..d325fcfedb 100644 --- a/Packages/com.unity.inputsystem/Documentation~/actions-editor.md +++ b/Packages/com.unity.inputsystem/Documentation~/actions-editor.md @@ -45,90 +45,6 @@ The Input Actions editor is divided into three panels (marked A, B & C above). > Although you can reorder actions in this window, the ordering is for visual convenience only, and does not affect the order in which the actions are triggered in your code. If multiple actions are performed in the same frame, the order in which they are reported by the input system is undefined. To avoid problems, you should not write code that assumes they will be reported in a particular order. - -## Action type and Control type - -If you select an Action, you can edit its properties in the right-hand pane of the window: - -![Action Properties](Images/ActionProperties.png) - -#### Action Type - -The Action Type setting allows to to select between **Button**, **Value** or **PassThrough**. - -These options relate to whether this action should represent a discrete on/off button-style interaction or a value that can change over time while the control is being used. - -For device controls such as keyboard keys, mouse clicks, or gamepad buttons, select **Button**. For device controls such as mouse movement, a joystick or gamepad stick, or device orientation that provide continuously changing input over a period of time, select **Value**. - -The Button and Value types of action also provides data about the action such as whether it has started and stopped, and conflict resolution in situations where multiple bindings are mapped to the same action. - -The third option, **PassThrough**, is also a value type, and as such is suitable for the same types of device controls as value. The difference is that actions set to PassThrough only provide basic information about the values incoming from the device controls bound to it, and does not provide the extra data relating to the phase of the action, nor does it perform conflict resolution in the case of multiple controls mapped to the same action. - -For more detail about how these types work, see [action types](RespondingToActions.html#action-types) and [default interactions](Interactions.html#default-interaction). - -#### Control Type - -The Control Type setting allows you to select the type of control expected by the action. This limits the controls shown when setting up bindings in the UI and also limits which contols can be bound interactively to the action. - -For example, if you select **2D axis**, only those controls that can supply a 2D vector as value are available as options for the binding control path. - -There are more specific control types available which futher filter the available bindings, such as "Stick", "Dpad" or "Touch". If you select one of these control types, the list of available controls is further limited to only those controls of those specific types when you select a binding for your action (see directly below). - -### Bindings - -* To add a new Binding, select the Add (+) icon on the action you want to add it to, and select the binding type from the menu that appears. -* To delete an existing Binding, either right-click it and select __Delete__ from the context menu. -* To duplicate an existing Binding, either right-click it and select __Duplicate__ from the context menu. - -You can add multiple bindings to an action, which is generally useful for supporting multiple types of input device. For example, in the default set of actions, the "Move" action has a binding to the left gamepad stick and the WSAD keys, which means input through any of these bindings will perform the action. - -![The default "move" action with its multiple bindings highlighted](./Images/ActionWithMultipleBindings.png)
-_The default "Move" action in the Actions Editor window, displaying the multiple bindings associated with it._ - -If you select a Binding, you can edit its properties in the right-hand pane of the window: - -![Binding Properties](Images/BindingProperties.png) - -#### Picking Controls - -The most important property of any Binding is the [control path](Controls.md#control-paths) it's bound to. To edit it, open the __Path__ drop-down list. This displays a Control picker window. - -![Control Picker](Images/InputControlPicker.png) - -In the Control picker window, you can explore a tree of Input Devices and Controls that the Input System recognizes, and bind to these Controls. Unity filters this list by the Action's [`Control Type`](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction_expectedControlType) property. For example, if the Control type is `Vector2`, you can only select a Control that generates two-dimensional values, like a stick. - -The Device and Control tree is organized hierarchically from generic to specific. For example, the __Gamepad__ Control path `/buttonSouth` matches the lower action button on any gamepad. Alternatively, if you navigate to __Gamepad__ > __More Specific Gamepads__ and select __PS4 Controller__, and then choose the Control path `/buttonSouth`, this only matches the "Cross" button on PlayStation gamepads, and doesn't match any other gamepads. - -Instead of browsing the tree to find the Control you want, it's easier to let the Input System listen for input. To do that, select the __Listen__ button. At first, the list of Controls is empty. Once you start pressing buttons or actuating Controls on the Devices you want to bind to, the Control picker window starts listing any Bindings that match the controls you pressed. Select any of these Bindings to view them. - -Finally, you can choose to manually edit the Binding path, instead of using the Control picker. To do that, select the __T__ button next to the Control path popup. This changes the popup to a text field, where you can enter any Binding string. This also allows you to use wildcard (`*`) characters in your Bindings. For example, you can use a Binding path such as `/touch*/press` to bind to any finger being pressed on the touchscreen, instead of manually binding to `/touch0/press`, `/touch1/press` and so on. - -#### Editing Composite Bindings - -Composite Bindings are Bindings consisting of multiple parts, which form a Control together. For instance, a [2D Vector Composite](ActionBindings.md#2d-vector) uses four buttons (left, right, up, down) to simulate a 2D stick input. See the [Composite Bindings](ActionBindings.md#composite-bindings) documentation to learn more. - -![2D Vector Composite](./Images/2DVectorComposite.png) - -To create a Composite Binding, in the Input Action Asset editor window, select the Add (+) icon on the Action you want to add it to, and select the Composite Binding type from the popup menu. - -![Add 2D Vector Composite](./Images/Add2DVectorComposite.png) - -This creates multiple Binding entries for the Action: one for the Composite as a whole, and then, one level below that, one for each Composite part. The Composite itself doesn't have a Binding path property, but its individual parts do, and you can edit these parts like any other Binding. Once you bind all the Composite's parts, the Composite can work together as if you bound a single control to the Action. - -**Note**: The set of Composites displayed in the menu is depends on the value type of the Action. This means that, for example, if the Action is set to type "Button", then only Composites able to return values of type `float` will be shown. - -To change the type of a Composite retroactively, select the Composite, then select the new type from the **Composite Type** drop-down in the **Properties** pane. - -![Composite Type](./Images/CompositeType.png) - -To change the part of the Composite to which a particular Binding is assigned, use the **Composite Part** drop-down in the Binding's properties. - -![Composite Part](./Images/CompositePart.png) - -You can assign multiple Bindings to the same part. You can also duplicate individual part Bindings: right-click the Binding, then select **Duplicate** to create new part Bindings for the Composite. This can be used, for example, to create a single Composite for both "WASD" style controls and arrow keys. - -![Duplicated Part Bindings](./Images/DuplicatedPartBindings.png) - ### Editing Control Schemes Input Action Assets can have multiple [Control Schemes](ActionBindings.md#control-schemes), which let you enable or disable different sets of Bindings for your Actions for different types of Devices. diff --git a/Packages/com.unity.inputsystem/Documentation~/add-duplicate-delete-binding.md b/Packages/com.unity.inputsystem/Documentation~/add-duplicate-delete-binding.md index be1ed9b084..75f31ed89b 100644 --- a/Packages/com.unity.inputsystem/Documentation~/add-duplicate-delete-binding.md +++ b/Packages/com.unity.inputsystem/Documentation~/add-duplicate-delete-binding.md @@ -1 +1,24 @@ # Add, duplicate or delete a binding + +Open the [Actions Editor window](actions-editor.md) to add, duplicate, or delete bindings. + +To add a new Binding: + +1. Select the Add (+) icon on the action you want to add it to +2. Select the appropriate [binding type](binding-types.md) from the menu that appears. + +To delete an existing Binding: + +1. Right-click the action +2. Select __Delete__ from the context menu. + +To duplicate an existing Binding: + +1. Right-click the action +2. Select __Duplicate__ from the context menu. + +You can add multiple bindings to an action, which is generally useful for supporting multiple types of input device. For example, in the default set of actions, the "Move" action has a binding to the left gamepad stick and the WSAD keys, which means input through any of these bindings will perform the action. + +![The default "move" action with its multiple bindings highlighted](./Images/ActionWithMultipleBindings.png)
+_The default "Move" action in the Actions Editor window, displaying the multiple bindings associated with it._ + diff --git a/Packages/com.unity.inputsystem/Documentation~/apply-binding-overrides.md b/Packages/com.unity.inputsystem/Documentation~/apply-binding-overrides.md index fd07739c61..e69de29bb2 100644 --- a/Packages/com.unity.inputsystem/Documentation~/apply-binding-overrides.md +++ b/Packages/com.unity.inputsystem/Documentation~/apply-binding-overrides.md @@ -1,30 +0,0 @@ - -### Apply binding overrides - -You can override aspects of any Binding at run-time non-destructively. Specific properties of [`InputBinding`](../api/UnityEngine.InputSystem.InputBinding.html) have an `override` variant that, if set, will take precedent over the property that they shadow. All `override` properties are of type `String`. - -|Property|Override|Description| -|--------|--------|-----------| -|[`path`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_path)|[`overridePath`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_overridePath)|Replaces the [Control path](./Controls.md#control-paths) that determines which Control(s) are referenced in the binding. If [`overridePath`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_overridePath) is set to an empty string, the binding is effectively disabled.

Example: `"/leftStick"`| -|[`processors`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_processors)|[`overrideProcessors`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_overrideProcessors)|Replaces the [processors](./Processors.md) applied to the binding.

Example: `"invert,normalize(min=0,max=10)"`| -|[`interactions`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_interactions)|[`overrideInteractions`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_overrideInteractions)|Replaces the [interactions](./Interactions.md) applied to the binding.

Example: `"tap(duration=0.5)"`| - ->NOTE: The `override` property values will not be saved along with the Actions (for example, when calling [`InputActionAsset.ToJson()`](../api/UnityEngine.InputSystem.InputActionAsset.html#UnityEngine_InputSystem_InputActionAsset_ToJson)). See [Saving and loading rebinds](#saving-and-loading-rebinds) for details about how to persist user rebinds. - -To set the various `override` properties, you can use the [`ApplyBindingOverride`](../api/UnityEngine.InputSystem.InputActionRebindingExtensions.html#UnityEngine_InputSystem_InputActionRebindingExtensions_ApplyBindingOverride_UnityEngine_InputSystem_InputAction_UnityEngine_InputSystem_InputBinding_) APIs. - -```CSharp -// Rebind the "fire" action to the left trigger on the gamepad. -playerInput.actions["fire"].ApplyBindingOverride("/leftTrigger"); -``` - -In most cases, it is best to locate specific bindings using APIs such as [`GetBindingIndexForControl`](../api/UnityEngine.InputSystem.InputActionRebindingExtensions.html#UnityEngine_InputSystem_InputActionRebindingExtensions_GetBindingIndexForControl_) and to then apply the override to that specific binding. - -```CSharp -// Find the "Jump" binding for the space key. -var jumpAction = playerInput.actions["Jump"]; -var bindingIndex = jumpAction.GetBindingIndexForControl(Keyboard.current.spaceKey); - -// And change it to the enter key. -jumpAction.ApplyBindingOverride(bindingIndex, "/enter"); -``` diff --git a/Packages/com.unity.inputsystem/Documentation~/binding-conflicts.md b/Packages/com.unity.inputsystem/Documentation~/binding-conflicts.md new file mode 100644 index 0000000000..de5664eee5 --- /dev/null +++ b/Packages/com.unity.inputsystem/Documentation~/binding-conflicts.md @@ -0,0 +1,88 @@ + +# Binding conflicts + +A binding conflict is when an [action](./actions.md) with more than one [control](./controls.md) [bound](./bindings.md) to it recieves values from multiple controls. + +## Conflict situations + +Binding conflict situations can arise in two different ways. Either: + +- **Multiple concurrent controls**. Several controls are bound to the same action and more than one is feeding input into the Action at the same time. Example: an Action that is bound to both the left and right trigger on a Gamepad and both triggers are pressed. + +Or: + +- **Multiple input sequences**. The input is part of a sequence of inputs and there are several possible such sequences. Example: one Action is bound to the `B` key and another Action is bound to `Shift-B`. + +## Conflict Resolution + +For [**value** and **button** type actions](./action-and-control-types.md), the Input System continuously monitors all the controls bound to the action, and then chooses the one which is the **most actuated** to be the control driving the action. Most actuated means the largest absolute value is being reported, whether positive or negative in the case of a 1D axis, and regardless of direction in the case of 2D and 3D axes. The value of the most actuated control is reported in callbacks, and triggered whenever the value changes. + +If a different bound control is actuated more, that control becomes the control driving the action. This is useful if you want to allow different Controls to control an Action in the game, but only take input from one Control at the same time. + +[Pass-through type actions](./configure-action-type.md) do not perform conflict resolution, and are intended allow multiple concurrent inputs. + +## Multiple concurrent controls + +For a **Button** or **Value** [action type](./configure-action-type.md), there can only be one control at any time that is "driving" the action. This control is considered the [`activeControl`](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction_activeControl). + +When an action is bound to multiple controls, the active control at any point is the one with the greatest level of ["actuation"](./control-actuation.md) (the one with the largest value returned from [`EvaluateMagnitude`](../api/UnityEngine.InputSystem.InputControl.html#UnityEngine_InputSystem_InputControl_EvaluateMagnitude_)). If a different control exceeds the actuation level of the current active control, it becomes the active control. + +For [composite bindings](./composite-bindings-reference.md), magnitudes of the composite as a whole rather than for individual controls are tracked. However, [`activeControl`](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction_activeControl) will still track individual Controls from the composite. + +## Multiple input sequences (such as keyboard shortcuts) + +>__Note__: The mechanism described here only applies to Actions that are part of the same [action map](./action-maps-panel.md) or [action assets](./action-assets.md). + +Inputs used in combinations with other inputs can also lead to ambiguities. If, for example, the **B** key on the Keyboard is bound both on its own as well as in combination with the **Shift** key, then if you first press **Shift** and then **B**, the latter key press would be a valid input for either of the Actions. + +The way the Input System handles this, is that Bindings are processed in the order of decreasing complexity. This metric is derived automatically from the Binding: + +* A binding that is *not* part of a [composite](composite-bindings-reference.md) is assigned a complexity of 1. +* A binding that *is* part of a [composite](composite-bindings-reference.md) is assigned a complexity equal to the number of part bindings in the composite. + +In our example, this means that a **one-modifier composite** binding to **Shift** + **B** has a higher complexity than a Binding to **B** and gets processed first. + +Additionally, the first Binding that results in the Action changing [phase](./set-callbacks-on-actions.md) will consume the input. This results in other Bindings to the same input not being processed. This means in our example, when the **Shift** + **B** binding consumes the **B** input, the Binding to **B** is skipped. + + +## Disabling Conflict Resolution + +Conflict resolution is always applied to **Button** or **Value** [action types](./configure-action-type.md). However, it can be undesirable in situations when an action is simply used to gather all inputs from bound Controls. For example, if you have a **Button** type action bound to the **A** button on all gamepads, a user holding down **A** on one gamepad means that the **A** button on other gamepads is ignored. + +By using the **Pass Through** action type, conflict resolution is bypassed, which means pressing the **A** button on one gamepad will not result in presses on other gamepads being ignored. + +## API Example + +The following example illustrates how this works at the API level. + +```CSharp +// Create two actions in the same map. +var map = new InputActionMap(); +var bAction = map.AddAction("B"); +var shiftbAction = map.AddAction("ShiftB"); + +// Bind one of the actions to 'B' and the other to 'SHIFT+B'. +bAction.AddBinding("/b"); +shiftbAction.AddCompositeBinding("OneModifier") + .With("Modifier", "/shift") + .With("Binding", "/b"); + +// Print something to the console when the actions are triggered. +bAction.performed += _ => Debug.Log("B action performed"); +shiftbAction.performed += _ => Debug.Log("SHIFT+B action performed"); + +// Start listening to input. +map.Enable(); + +// Now, let's assume the left shift key on the keyboard is pressed (here, we manually +// press it with the InputTestFixture API). +Press(Keyboard.current.leftShiftKey); + +// And then the B is pressed. This is a valid input for both +// bAction as well as shiftbAction. +// +// What will happen now is that shiftbAction will do its processing first. In response, +// it will *perform* the action (i.e. we see the `performed` callback being invoked) and +// thus "consume" the input. bAction will stay silent as it will in turn be skipped over. +Press(keyboard.bKey); +``` \ No newline at end of file diff --git a/Packages/com.unity.inputsystem/Documentation~/binding-initial-state-checks.md b/Packages/com.unity.inputsystem/Documentation~/binding-initial-state-checks.md index 11c6e64966..9a80ddda04 100644 --- a/Packages/com.unity.inputsystem/Documentation~/binding-initial-state-checks.md +++ b/Packages/com.unity.inputsystem/Documentation~/binding-initial-state-checks.md @@ -1,13 +1,14 @@ # Binding initial state checks -After an Action is [enabled](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction_enabled), it will start reacting to input as it comes in. However, at the time the Action is enabled, one or more of the Controls that are [bound](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction_controls) to an action may already have a non-default state at that point. -x +After an action is [enabled](enable-actions.md), it will start reacting to input as it comes in. However, at the time the action is enabled, one or more of the controls that are [bound](./add-duplicate-delete-binding.md) to an action may already have a non-default state, for example if a user was currently pressing a button or pushing a thumb stick. + Using what is referred to as an "initial state check", an Action can be made to respond to such a non-default state as if the state change happened *after* the Action was enabled. The way this works is that in the first input [update](../api/UnityEngine.InputSystem.InputSystem.html#UnityEngine_InputSystem_InputSystem_Update_) after the Action was enabled, all its bound controls are checked in turn. If any of them has a non-default state, the Action responds right away. -This check is implicitly enabled for [Value](RespondingToActions.md#value) actions. If, for example, you have a `Move` Action bound to the left stick on the gamepad and the stick is already pushed in a direction when `Move` is enabled, the character will immediately start walking. +This check is implicitly enabled for actions whose [Action Type](./configure-action-type.md) is set to **Value**. If, for example, you have a "Move" Action bound to the left stick on the gamepad and the stick is already pushed in a direction when "Move" is enabled, the character will immediately start walking. -By default, [Button](RespondingToActions.md#button) and [Pass-Through](RespondingToActions.md#pass-through) type Actions, do not perform this check. A button that is pressed when its respective Action is enabled first needs to be released and then pressed again for it to trigger the Action. +By default, actions whose [Action Type](./configure-action-type.md) is set to **Button** or **Pass-Through**, do not perform this check. A button that is pressed when its respective Action is enabled first needs to be released and then pressed again for it to trigger the Action. The initial state check is usually not useful in such cases, because it can trigger actions if the button is still held down from a previous press when the action was enabled. -However, you can manually enable initial state checks on these types of Actions using the checkbox in the editor: +However, you can manually enable initial state checks on these types of actions by doing the following: -![Initial State Check](./Images/InitialStateCheck.png) +1. Select the action in the [Actions panel](./actions-panel.md) of the [Actions Editor window](./actions-editor.md) +2. Enable the **Initial State Check** option in the [Actions Properties panel](./action-properties-panel.md) to the right. diff --git a/Packages/com.unity.inputsystem/Documentation~/binding-overrides.md b/Packages/com.unity.inputsystem/Documentation~/binding-overrides.md deleted file mode 100644 index 55a9e08440..0000000000 --- a/Packages/com.unity.inputsystem/Documentation~/binding-overrides.md +++ /dev/null @@ -1 +0,0 @@ -# Binding overrides diff --git a/Packages/com.unity.inputsystem/Documentation~/binding-properties-panel.md b/Packages/com.unity.inputsystem/Documentation~/binding-properties-panel.md index 2d5c73154f..5c86ec341c 100644 --- a/Packages/com.unity.inputsystem/Documentation~/binding-properties-panel.md +++ b/Packages/com.unity.inputsystem/Documentation~/binding-properties-panel.md @@ -1,2 +1,43 @@ # Binding properties panel + +[//]: # (TODO: unfinished - dumping info here from other pages, to reformat later) + + + +# 1D + +You can set the following parameters on a 1D axis Composite: + +|Parameter|Description| +|---------|-----------| +|[`whichSideWins`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_whichSideWins)|What happens if both [`positive`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_positive) and [`negative`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_negative) are actuated. See table below.| +|[`minValue`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_minValue)|The value returned if the [`negative`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_negative) side is actuated. Default is -1.| +|[`maxValue`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_maxValue)|The value returned if the [`positive`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_positive) side is actuated. Default is 1.| + +If Controls from both the `positive` and the `negative` side are actuated, then the resulting value of the axis Composite depends on the `whichSideWin` parameter setting. + +|[`WhichSideWins`](../api/UnityEngine.InputSystem.Composites.AxisComposite.WhichSideWins.html)|Description| +|---------------|-----------| +|(0) `Neither`|Neither side has precedence. The Composite returns the midpoint between `minValue` and `maxValue` as a result. At their default settings, this is 0.

This is the default value for this setting.| +|(1) `Positive`|The positive side has precedence and the Composite returns `maxValue`.| +|(2) `Negative`|The negative side has precedence and the Composite returns `minValue`.| + + +# 2D + +In addition, you can set the following parameters on a 2D vector Composite: + +|Parameter|Description| +|---------|-----------| +|[`mode`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.html#UnityEngine_InputSystem_Composites_Vector2Composite_mode)|Whether to treat the inputs as digital or as analog controls.

If this is set to [`Mode.DigitalNormalized`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector2Composite_Mode_DigitalNormalized), inputs are treated as buttons (off if below [`defaultButtonPressPoint`](../api/UnityEngine.InputSystem.InputSettings.html#UnityEngine_InputSystem_InputSettings_defaultButtonPressPoint) and on if equal to or greater). Each input is 0 or 1 depending on whether the button is pressed or not. The vector resulting from the up/down/left/right parts is normalized. The result is a diamond-shaped 2D input range.

If this is set to [`Mode.Digital`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector2Composite_Mode_Digital), the behavior is essentially the same as [`Mode.DigitalNormalized`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector2Composite_Mode_DigitalNormalized) except that the resulting vector is not normalized.

Finally, if this is set to [`Mode.Analog`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector2Composite_Mode_Analog), inputs are treated as analog (i.e. full floating-point values) and, other than [`down`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.html#UnityEngine_InputSystem_Composites_Vector2Composite_down) and [`left`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.html#UnityEngine_InputSystem_Composites_Vector2Composite_left) being inverted, values will be passed through as is.

The default is [`Mode.DigitalNormalized`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector2Composite_Mode_DigitalNormalized).| + + + +## 3D + +In addition, you can set the following parameters on a 3D vector Composite: + +|Parameter|Description| +|---------|-----------| +|[`mode`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_mode)|Whether to treat the inputs as digital or as analog controls.

If this is set to [`Mode.DigitalNormalized`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector3Composite_Mode_DigitalNormalized), inputs are treated as buttons (off if below [`defaultButtonPressPoint`](../api/UnityEngine.InputSystem.InputSettings.html#UnityEngine_InputSystem_InputSettings_defaultButtonPressPoint) and on if equal to or greater). Each input is 0 or 1 depending on whether the button is pressed or not. The vector resulting from the up/down/left/right/forward/backward parts is normalized.

If this is set to [`Mode.Digital`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector3Composite_Mode_Digital), the behavior is essentially the same as [`Mode.DigitalNormalized`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector3Composite_Mode_DigitalNormalized) except that the resulting vector is not normalized.

Finally, if this is set to [`Mode.Analog`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector3Composite_Mode_Analog), inputs are treated as analog (that is, full floating-point values) and, other than [`down`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_down), [`left`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_left), and [`backward`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_backward) being inverted, values will be passed through as they are.

The default is [`Analog`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector3Composite_Mode_Analog).| \ No newline at end of file diff --git a/Packages/com.unity.inputsystem/Documentation~/binding-resolution.md b/Packages/com.unity.inputsystem/Documentation~/binding-resolution.md index fe3eb00c2f..1ae52e105e 100644 --- a/Packages/com.unity.inputsystem/Documentation~/binding-resolution.md +++ b/Packages/com.unity.inputsystem/Documentation~/binding-resolution.md @@ -1,43 +1,40 @@ # Binding resolution -When the Input System accesses the [Controls](Controls.md) bound to an Action for the first time, the Action resolves its Bindings to match them to existing Controls on existing Devices. In this process, the Action calls [`InputSystem.FindControls<>()`](../api/UnityEngine.InputSystem.InputSystem.html#UnityEngine_InputSystem_InputSystem_FindControls__1_System_String_UnityEngine_InputSystem_InputControlList___0___) (filtering for devices assigned to the InputActionMap, if there are any) for the Binding path of each of the Action's bindings. This creates a list of resolved Controls that are now bound to the Action. +Binding resolution refers to when the Input System looks up which actual controls on connected devices should be used by each action, based on their binding control paths. -Note that a single [Binding path](Controls.md#control-paths) can match multiple Controls: +## Why bindings are resolved -* A specific Device path such as `/buttonEast` matches the "Circle" button on a [PlayStation controller](Gamepad.md#playstation-controllers). If you have multiple PlayStation controllers connected, it resolves to the "Circle" button on each of these controllers. +Each [simple binding](./binding-types.md) has a [control path](./control-paths.md), which determines which [control](controls.md) (or controls) should be associated with the action. For [composite bindings](./composite-bindings-reference.md), each of the composites sub-bindings (or **parts**) has a control path. -* An abstract Device path such as `/buttonEast` matches the right action button on any connected gamepad. If you have a PlayStation controller and an [Xbox controller](Gamepad.md#xbox-controllers) connected, it resolves to the "Circle" button on the PlayStation controller, and to the "B" button on the Xbox controller. +Control paths are stored as a string that describes where to find the relevant control or controls for the binding. For example, a control path "`/buttonEast`" refers to the right action button on any connected gamepad. -* A Binding path can also contain wildcards, such as `/button*`. This matches any Control on any gamepad with a name starting with "button", which matches all the four action buttons on any connected gamepad. A different example: `*/{Submit}` matches any Control tagged with the "Submit" [usage](Controls.md#control-usages) on any Device. +Because control paths can refer to specific devices, or more broadly to a device type, and can also contain wildcard characters, and there may be any combinations of input hardware connected, the Input System must **resolve** the bindings at runtime to work out which controls on connected devices are valid for each action. This occurs when the Input System accesses an action for the first time. -If there are multiple Bindings on the same Action that all reference the same Control(s), the Control will effectively feed into the Action multiple times. This is to allow, for example, a single Control to produce different input on the same Action by virtue of being bound in a different fashion (composites, processors, interactions, etc). However, regardless of how many times a Control is bound on any given action, it will only be mentioned once in the Action's [array of `controls`](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction_controls). +## What happens during resolution -To query the Controls that an Action resolves to, you can use [`InputAction.controls`](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction_controls). You can also run this query if the Action is disabled. +During binding resolution, the action automatically calls [`InputSystem.FindControls<>()`](../api/UnityEngine.InputSystem.InputSystem.html#UnityEngine_InputSystem_InputSystem_FindControls__1_System_String_UnityEngine_InputSystem_InputControlList___0___) (filtering for devices assigned to the InputActionMap, if there are any) for the Binding path of each of the Action's bindings. This creates a list of resolved Controls that are now bound to the Action. -To be notified when binding resolution happens, you can listen to [`InputSystem.onActionChange`](../api/UnityEngine.InputSystem.InputSystem.html#UnityEngine_InputSystem_InputSystem_onActionChange) which triggers [`InputActionChange.BoundControlsAboutToChange`](../api/UnityEngine.InputSystem.InputActionChange.html#UnityEngine_InputSystem_InputActionChange_BoundControlsAboutToChange) before modifying Control lists and triggers [`InputActionChange.BoundControlsChanged`](../api/UnityEngine.InputSystem.InputActionChange.html#UnityEngine_InputSystem_InputActionChange_BoundControlsChanged) after having updated them. +Note that a single [binding control path](control-paths.md) can match multiple Controls. For example: -## Binding resolution while Actions are enabled +* A device-specific path such as `/buttonEast` matches the "Circle" button on a [PlayStation controller](Gamepad.md#playstation-controllers). If you have multiple PlayStation controllers connected, it resolves to the "Circle" button on each of these controllers. -In certain situations, the [Controls](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction_controls) bound to an Action have to be updated more than once. For example, if a new [Device](Devices.md) becomes usable with an Action, the Action may now pick up input from additional controls. Also, if Bindings are added, removed, or modified, Control lists will need to be updated. +* An abstract device path such as `/buttonEast` matches the right action button on any connected gamepad. If you have a PlayStation controller and an [Xbox controller](Gamepad.md#xbox-controllers) connected, it resolves to the "Circle" button on the PlayStation controller, and to the "B" button on the Xbox controller. -This updating of Controls usually happens transparently in the background. However, when an Action is [enabled](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction_enabled) and especially when it is [in progress](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction_IsInProgress_), there may be a noticeable effect on the Action. +* A Binding path can also contain wildcards, such as `/button*`. This matches any control on any gamepad with a name starting with "button", which matches all the four action buttons on any connected gamepad. A different example: `*/{Submit}` matches any control tagged with the "Submit" [usage](Controls.md#control-usages) on any device. -Adding or removing a device – either [globally](../api/UnityEngine.InputSystem.InputSystem.html#UnityEngine_InputSystem_InputSystem_devices) or to/from the [device list](../api/UnityEngine.InputSystem.InputActionAsset.html#UnityEngine_InputSystem_InputActionAsset_devices) of an Action – will remain transparent __except__ if an Action is in progress and it is the device of its [active Control](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction_activeControl) that is being removed. In this case, the Action will automatically be [cancelled](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction_canceled). +If there are multiple bindings on the same action that all reference the same control(s), the control will effectively feed into the action multiple times. This is to allow, for example, a single control to produce different input on the same action by virtue of being bound in a different fashion ([composites](./composite-bindings-reference.md), [processors](./processors-on-actions.md), [interactions](./interactions.md), etc). However, regardless of how many times a control is bound on any given action, it will only appear once in the action's [array of `controls`](xref:UnityEngine.InputSystem.InputAction.controls). -Modifying the [binding mask](../api/UnityEngine.InputSystem.InputActionAsset.html#UnityEngine_InputSystem_InputActionAsset_bindingMask) or modifying any of the Bindings (such as through [rebinding](#interactive-rebinding) or by adding or removing bindings) will, however, lead to all enabled Actions being temporarily disabled and then re-enabled and resumed. +To query the Controls that an Action resolves to, you can use [`InputAction.controls`](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction_controls). You can also run this query if the Action is disabled. -## Choosing which Devices to use +To be notified when binding resolution happens, you can listen to [`InputSystem.onActionChange`](xref:UnityEngine.InputSystem.InputSystem.onActionChange) which triggers [`InputActionChange.BoundControlsAboutToChange`](xref:UnityEngine.InputSystem.InputActionChange.BoundControlsAboutToChange) before modifying Control lists and triggers [`InputActionChange.BoundControlsChanged`](xref:UnityEngine.InputSystem.InputActionChange.BoundControlsChanged) after having updated them. ->__Note__: [`InputUser`](UserManagement.md) and [`PlayerInput`](player-input-component.md) make use of this facility automatically. They set [`InputActionMap.devices`](../api/UnityEngine.InputSystem.InputActionMap.html#UnityEngine_InputSystem_InputActionMap_devices) automatically based on the Devices that are paired to the user. +## Binding resolution while actions are enabled -By default, Actions resolve their Bindings against all Devices present in the Input System (that is, [`InputSystem.devices`](../api/UnityEngine.InputSystem.InputSystem.html#UnityEngine_InputSystem_InputSystem_devices)). For example, if there are two gamepads present in the system, a Binding to `/buttonSouth` picks up both gamepads and allows the Action to be used from either. +In certain situations, the controls bound to an action have to be updated more than once. For example, if a new device is plugged in and becomes usable with an action, the action may now pick up input from additional controls. Also, if bindings are added, removed, or modified, control lists will need to be updated. -You can override this behavior by restricting [`InputActionAssets`](../api/UnityEngine.InputSystem.InputActionAsset.html) or individual [`InputActionMaps`](../api/UnityEngine.InputSystem.InputActionMap.html) to a specific set of Devices. If you do this, Binding resolution only takes the Controls of the given Devices into account. +This updating of controls usually happens transparently in the background. However, when an action is [enabled](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction_enabled) and especially when it is [in progress](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction_IsInProgress_), there may be a noticeable effect on the Action. -``` - var actionMap = new InputActionMap(); +Adding or removing a device – either [globally](xref:UnityEngine.InputSystem.InputSystem.devices) or to/from the [device list](xref:UnityEngine.InputSystem.InputActionAsset.devices) of an Action – will remain transparent __except__ if an Action is in progress and it is the device of its [active Control](xref:UnityEngine.InputSystem.InputAction.activeControl) that is being removed. In this case, the Action will automatically be [cancelled](xref:UnityEngine.InputSystem.InputAction.canceled). - // Restrict the action map to just the first gamepad. - actionMap.devices = new[] { Gamepad.all[0] }; -``` +Modifying the [binding mask](xref:UnityEngine.InputSystem.InputActionAsset.bindingMask) or modifying any of the Bindings (such as through [rebinding](./interactive-rebinding.md) or by adding or removing bindings) will, however, lead to all enabled actions being temporarily disabled and then re-enabled and resumed. diff --git a/Packages/com.unity.inputsystem/Documentation~/binding-types.md b/Packages/com.unity.inputsystem/Documentation~/binding-types.md new file mode 100644 index 0000000000..07501d30fe --- /dev/null +++ b/Packages/com.unity.inputsystem/Documentation~/binding-types.md @@ -0,0 +1,16 @@ +# Binding types + +You can configure how bindings map to actions with binding types. The following binding types are available: + +- **Simple**: A single control maps directly to an action. For example, a gamepad stick to a `Move` action, or a gamepad button to a `Jump` action. +- **Composite**: Construct a binding from multiple simple bindings. + +When you [add a binding](add-duplicate-delete-binding.md) you must select the appropriate binding type for your action. + +Some examples of composite bindings are: + +- A **four-way** composite binding, where four keyboard keys map to an action whose [control type](control-types.md) is a 2D vector, so that each of the keys maps to up, down, left, and right respectively. In this scenario, the four key bindings are simple bindings grouped together into into the composite four-way binding. + +- A **modifier** composite binding, where one control represents the main binding, and a second control represents a modifier key which changes the effect of the main binding - such as holding down the control key on a keyboard before also pressing a letter key. In this scenario, the two separate key bindings are simple bindings grouped together into the composite modifier binding. + +For a full list of composite binding types, refer to [Composite bindings](composite-bindings-reference.md). diff --git a/Packages/com.unity.inputsystem/Documentation~/bindings.md b/Packages/com.unity.inputsystem/Documentation~/bindings.md index 34594229e8..353bd6c53b 100644 --- a/Packages/com.unity.inputsystem/Documentation~/bindings.md +++ b/Packages/com.unity.inputsystem/Documentation~/bindings.md @@ -1,3 +1,17 @@ # Bindings -(landing page) \ No newline at end of file +![](Images/ConceptsOverview.png) + +A **binding** represents a connection between an [Action](actions.md) and one or more [Controls](Controls.md) identified by a [Control path](./control-paths.md). + +| **Topic** | **Description** | +| :------------------------------ | :------------------------------- | +| **[Introduction to Bindings](introduction-to-bindings.md)** | Learn the basic concepts of bindings. | +| **[Add, Duplicate or Delete a Binding](add-duplicate-delete-binding.md)** | Learn how to add, duplicate or delete bindings. | +| **[Select a control for Binding](select-control-binding.md)** | Learn how to choose a specific control that a binding is bound to, such as a specific button or stick on a gamepad, or a specific keyboard key. | +| **[Composite Bindings](composite-bindings-reference.md)** | Bindings made up of multiple simple bindings acting together. | +| **[Group bindings to control schemes](group-binding-to-control-scheme.md)** | Group types of related bindings together according to their control type, so that you can enable or disable groups of bindings | +| **[Binding resolution](binding-resolution.md)** | Learn how the Input Systems resolves binding configurations to currently-connected input devices. | +| **[Restrict bindings to specific devices](restrict-bindings-specific-device.md)** | Specify which specific devices a binding should resolve to. | +| **[Binding conflicts](binding-conflicts.md)** | Learn how the Input System resolves conflicting or ambiguous situations, such as when multiple bindings map to the same action. | +| **[Initial state checks](binding-initial-state-checks.md)** | Learn how the Input System deals with if a control is already pressed when an action is enabled, and how to modify this behavior. | \ No newline at end of file diff --git a/Packages/com.unity.inputsystem/Documentation~/changing-bindings.md b/Packages/com.unity.inputsystem/Documentation~/changing-bindings.md deleted file mode 100644 index 09832ad02e..0000000000 --- a/Packages/com.unity.inputsystem/Documentation~/changing-bindings.md +++ /dev/null @@ -1,43 +0,0 @@ - -## Changing Bindings - -In general, you can change existing bindings via the [`InputActionSetupExtensions.ChangeBinding`](../api/UnityEngine.InputSystem.InputActionSetupExtensions.html#UnityEngine_InputSystem_InputActionSetupExtensions_ChangeBinding_UnityEngine_InputSystem_InputAction_System_Int32_) method. This returns an accessor that can be used to modify the properties of the targeted [`InputBinding`](../api/UnityEngine.InputSystem.InputBinding.html). Note that most of the write operations of the accessor are destructive. For non-destructive changes to bindings, see [Applying Overrides](#applying-overrides). - -```CSharp -// Get write access to the second binding of the 'fire' action. -var accessor = playerInput.actions['fire'].ChangeBinding(1); - -// You can also gain access through the InputActionMap. Each -// map contains an array of all its bindings (see InputActionMap.bindings). -// Here we gain access to the third binding in the map. -accessor = playerInput.actions.FindActionMap("gameplay").ChangeBinding(2); -``` - -You can use the resulting accessor to modify properties through methods such as [`WithPath`](../api/UnityEngine.InputSystem.InputActionSetupExtensions.BindingSyntax.html#UnityEngine_InputSystem_InputActionSetupExtensions_BindingSyntax_WithPath_) or [`WithProcessors`](../api/UnityEngine.InputSystem.InputActionSetupExtensions.BindingSyntax.html#UnityEngine_InputSystem_InputActionSetupExtensions_BindingSyntax_WithProcessors_). - -```CSharp -playerInput.actions["fire"].ChangeBinding(1) - // Change path to space key. - .WithPath("/space"); -``` - -You can also use the accessor to iterate through bindings using [`PreviousBinding`](../api/UnityEngine.InputSystem.InputActionSetupExtensions.BindingSyntax.html#UnityEngine_InputSystem_InputActionSetupExtensions_BindingSyntax_PreviousBinding_) and [`NextBinding`](../api/UnityEngine.InputSystem.InputActionSetupExtensions.BindingSyntax.html#UnityEngine_InputSystem_InputActionSetupExtensions_BindingSyntax_NextBinding_). - -```CSharp -// Move accessor to previous binding. -accessor = accessor.PreviousBinding(); - -// Move accessor to next binding. -accessor = accessor.NextBinding(); -``` - -If the given binding is a [composite](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_isComposite), you can address it by its name rather than by index. - -```CSharp -// Change the 2DVector composite of the "move" action. -playerInput.actions["move"].ChangeCompositeBinding("2DVector") - - -// -playerInput.actions["move"].ChangeBinding("WASD") -``` diff --git a/Packages/com.unity.inputsystem/Documentation~/composite-bindings-reference.md b/Packages/com.unity.inputsystem/Documentation~/composite-bindings-reference.md new file mode 100644 index 0000000000..e7258b5e73 --- /dev/null +++ b/Packages/com.unity.inputsystem/Documentation~/composite-bindings-reference.md @@ -0,0 +1,22 @@ +# Composite Bindings reference + +Sometimes, you might want to have several Controls act in unison to mimic a different type of Control. The most common example of this is using the W, A, S, and D keys on the keyboard to form a 2D vector Control equivalent to mouse deltas or gamepad sticks. Another example is to use two keys to form a 1D axis equivalent to a mouse scroll axis. + +Composite Bindings, made up of multiple **sub-bindings** solve this problem. Composites themselves don't bind directly to Controls; instead, they take values from their **sub-bindings** that do, and then synthesize input from those values together into a single virtual control binding. + +To create a composite binding, select the appropriate [composite type](binding-types.md) for your action while [adding a binding in the actions editor](./add-duplicate-delete-binding.md). The types of composite bindings available are as follows: + +## Types of composite bindings + +The **Add binding (+)** menu contains the following options. + +| Value | Description | +| :---------------------------- | :----------------------------- | +| **Add Binding** | Adds a [simple binding](./binding-types.md) and is not a composite | +| **Add Positive/Negative Binding** | Adds a 1D axis composite binding made of two button sub-bindings, one that pulls a 1D axis in its negative direction, and another that pulls it in its positive direction. It is implemented in the [`AxisComposite`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html) class. The output is a `float`.

If Controls from both the `positive` and the `negative` side are actuated, then the resulting value of the axis Composite depends on the **Which side wins** [binding property](./binding-properties-panel.md). | +| **Add Up/Down/Left/Right Composite** | Adds a 2D axis composite binding that represents a 4-way button control like the D-pad on gamepads. Each button sub-binding represents a cardinal direction, is most useful for representing up-down-left-right controls, such as WASD keyboard input. It is implemented in the [`Vector2Composite`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.html) class. The output is a `Vector2`. This composite's [**mode** property](./binding-properties-panel.md) allows you to choose whether the inputs should be treated as digital or analog controls. | +| **Add Up/Down/Left/Right/Forward/Backward Composite** | Adds a 3D composite binding that represents a 6-way button where two combinations each control one axis of a 3D vector. Implemented in the [`Vector3Composite`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html) class. The output is a `Vector3`.

This composite's [**mode** property](./binding-properties-panel.md) allows you to choose whether the inputs should be treated as digital or analog controls. | +| **Add Binding With One Modifier** | Adds a composite with two sub-bindings, named **Binding** and **Modifier**, which requires the user to hold down the **modifier** button in addition to another control from which the actual value of the binding is determined. This can be used, for example, for bindings such as "SHIFT+1". Implemented in the [`OneModifierComposite`](../api/UnityEngine.InputSystem.Composites.OneModifierComposite.html) class. The buttons can be on any Device, and can be toggle buttons or full-range buttons such as gamepad triggers.

The output is a [value of the same type](control-types.md) as the control bound to the sub-binding named **Binding**. | +| **Add Binding With Two Modifiers** | Adds a composite with three sub-bindings, named **Binding**, **Modifier 1** and **Modifier 2**, which requires the user to hold down two modifier buttons in addition to another control from which the actual value of the binding is determined. This can be used, for example, for bindings such as "SHIFT+CTRL+1". Implemented in the [`TwoModifiersComposite`](../api/UnityEngine.InputSystem.Composites.TwoModifiersComposite.html) class. The buttons can be on any Device, and can be toggle buttons or full-range buttons such as gamepad triggers.

The output is a [value of the same type](control-types.md) as the control bound to the sub-binding named **Binding**. | + +> **Note**: You can also [create custom composite bindings from code](./create-custom-composite-binding.md) \ No newline at end of file diff --git a/Packages/com.unity.inputsystem/Documentation~/composite-bindings.md b/Packages/com.unity.inputsystem/Documentation~/composite-bindings.md deleted file mode 100644 index b3fa71f768..0000000000 --- a/Packages/com.unity.inputsystem/Documentation~/composite-bindings.md +++ /dev/null @@ -1,319 +0,0 @@ -# Composite Bindings - -Sometimes, you might want to have several Controls act in unison to mimic a different type of Control. The most common example of this is using the W, A, S, and D keys on the keyboard to form a 2D vector Control equivalent to mouse deltas or gamepad sticks. Another example is to use two keys to form a 1D axis equivalent to a mouse scroll axis. - -This is difficult to implement with normal Bindings. You can bind a [`ButtonControl`](../api/UnityEngine.InputSystem.Controls.ButtonControl.html) to an action expecting a `Vector2`, but doing so results in an exception at runtime when the Input System tries to read a `Vector2` from a Control that can deliver only a `float`. - -Composite Bindings (that is, Bindings that are made up of other Bindings) solve this problem. Composites themselves don't bind directly to Controls; instead, they source values from other Bindings that do, and then synthesize input on the fly from those values. - -To see how to create Composites in the editor UI, see documentation on [editing Composite Bindings](ActionsEditor.md#editing-composite-bindings). - -To create composites in code, you can use the [`AddCompositeBinding`](../api/UnityEngine.InputSystem.InputActionSetupExtensions.html#UnityEngine_InputSystem_InputActionSetupExtensions_AddCompositeBinding_UnityEngine_InputSystem_InputAction_System_String_System_String_System_String_) syntax. - -```CSharp -myAction.AddCompositeBinding("Axis") - .With("Positive", "/rightTrigger") - .With("Negative", "/leftTrigger"); -``` - -Each Composite consists of one Binding that has [`InputBinding.isComposite`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_isComposite) set to true, followed by one or more Bindings that have [`InputBinding.isPartOfComposiste`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_isPartOfComposite) set to true. In other words, several consecutive entries in [`InputActionMap.bindings`](../api/UnityEngine.InputSystem.InputActionMap.html#UnityEngine_InputSystem_InputActionMap_bindings) or [`InputAction.bindings`](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction_bindings) together form a Composite. - -Note that each composite part can be bound arbitrary many times. - -```CSharp -// Make both shoulders and triggers pull on the axis. -myAction.AddCompositeBinding("Axis") - .With("Positive", "/rightTrigger") - .With("Positive", "/rightShoulder") - .With("Negative", "/leftTrigger"); - .With("Negative", "/leftShoulder"); -``` - -Composites can have parameters, just like [Interactions](Interactions.md) and [Processors](Processors.md). - -```CSharp -myAction.AddCompositeBinding("Axis(whichSideWins=1)"); -``` - -There are currently five Composite types that come with the system out of the box: [1D-Axis](#1d-axis), [2D-Vector](#2d-vector), [3D-Vector](#3d-vector), [One Modifier](#one-modifier) and [Two Modifiers](#two-modifiers). Additionally, you can [add your own](#writing-custom-composites) types of Composites. - -### 1D axis - -![Add 1D Axis Composite](./Images/Add1DAxisComposite.png) - -![1D Axis Composite](./Images/1DAxisComposite.png) - -A Composite made of two buttons: one that pulls a 1D axis in its negative direction, and another that pulls it in its positive direction. Implemented in the [`AxisComposite`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html) class. The result is a `float`. - -```CSharp -myAction.AddCompositeBinding("1DAxis") // Or just "Axis" - .With("Positive", "/rightTrigger") - .With("Negative", "/leftTrigger"); -``` - -The axis Composite has two part bindings. - -|Part|Type|Description| -|----|----|-----------| -|[`positive`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_positive)|`Button`|Controls pulling in the positive direction (towards [`maxValue`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_maxValue)).| -|[`negative`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_negative)|`Button`|Controls pulling in the negative direction, (towards [`minValue`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_minValue)).| - -You can set the following parameters on an axis Composite: - -|Parameter|Description| -|---------|-----------| -|[`whichSideWins`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_whichSideWins)|What happens if both [`positive`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_positive) and [`negative`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_negative) are actuated. See table below.| -|[`minValue`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_minValue)|The value returned if the [`negative`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_negative) side is actuated. Default is -1.| -|[`maxValue`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_maxValue)|The value returned if the [`positive`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_positive) side is actuated. Default is 1.| - -If Controls from both the `positive` and the `negative` side are actuated, then the resulting value of the axis Composite depends on the `whichSideWin` parameter setting. - -|[`WhichSideWins`](../api/UnityEngine.InputSystem.Composites.AxisComposite.WhichSideWins.html)|Description| -|---------------|-----------| -|(0) `Neither`|Neither side has precedence. The Composite returns the midpoint between `minValue` and `maxValue` as a result. At their default settings, this is 0.

This is the default value for this setting.| -|(1) `Positive`|The positive side has precedence and the Composite returns `maxValue`.| -|(2) `Negative`|The negative side has precedence and the Composite returns `minValue`.| - ->__Note__: There is no support yet for interpolating between the positive and negative over time. - -### 2D vector - -![Add 2D Vector Composite](./Images/Add2DVectorComposite.png) - -![2D Vector Composite](./Images/2DVectorComposite.png) - -A Composite that represents a 4-way button setup like the D-pad on gamepads. Each button represents a cardinal direction. Implemented in the [`Vector2Composite`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.html) class. The result is a `Vector2`. - -This Composite is most useful for representing up-down-left-right controls, such as WASD keyboard input. - -```CSharp -myAction.AddCompositeBinding("2DVector") // Or "Dpad" - .With("Up", "/w") - .With("Down", "/s") - .With("Left", "/a") - .With("Right", "/d"); - -// To set mode (2=analog, 1=digital, 0=digitalNormalized): -myAction.AddCompositeBinding("2DVector(mode=2)") - .With("Up", "/leftStick/up") - .With("Down", "/leftStick/down") - .With("Left", "/leftStick/left") - .With("Right", "/leftStick/right"); -``` - -The 2D vector Composite has four part Bindings. - -|Part|Type|Description| -|----|----|-----------| -|[`up`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.html#UnityEngine_InputSystem_Composites_Vector2Composite_up)|`Button`|Controls representing `(0,1)` (+Y).| -|[`down`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.html#UnityEngine_InputSystem_Composites_Vector2Composite_down)|`Button`|Controls representing `(0,-1)` (-Y).| -|[`left`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.html#UnityEngine_InputSystem_Composites_Vector2Composite_left)|`Button`|Controls representing `(-1,0)` (-X).| -|[`right`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.html#UnityEngine_InputSystem_Composites_Vector2Composite_right)|`Button`|Controls representing `(1,0)` (+X).| - -In addition, you can set the following parameters on a 2D vector Composite: - -|Parameter|Description| -|---------|-----------| -|[`mode`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.html#UnityEngine_InputSystem_Composites_Vector2Composite_mode)|Whether to treat the inputs as digital or as analog controls.

If this is set to [`Mode.DigitalNormalized`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector2Composite_Mode_DigitalNormalized), inputs are treated as buttons (off if below [`defaultButtonPressPoint`](../api/UnityEngine.InputSystem.InputSettings.html#UnityEngine_InputSystem_InputSettings_defaultButtonPressPoint) and on if equal to or greater). Each input is 0 or 1 depending on whether the button is pressed or not. The vector resulting from the up/down/left/right parts is normalized. The result is a diamond-shaped 2D input range.

If this is set to [`Mode.Digital`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector2Composite_Mode_Digital), the behavior is essentially the same as [`Mode.DigitalNormalized`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector2Composite_Mode_DigitalNormalized) except that the resulting vector is not normalized.

Finally, if this is set to [`Mode.Analog`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector2Composite_Mode_Analog), inputs are treated as analog (i.e. full floating-point values) and, other than [`down`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.html#UnityEngine_InputSystem_Composites_Vector2Composite_down) and [`left`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.html#UnityEngine_InputSystem_Composites_Vector2Composite_left) being inverted, values will be passed through as is.

The default is [`Mode.DigitalNormalized`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector2Composite_Mode_DigitalNormalized).| - ->__Note__: There is no support yet for interpolating between the up/down/left/right over time. - -### 3D vector - -![Add 3D Vector Composite](./Images/Add3DVectorComposite.png) - -![3D Vector Composite](./Images/3DVectorComposite.png) - -A Composite that represents a 6-way button where two combinations each control one axis of a 3D vector. Implemented in the [`Vector3Composite`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html) class. The result is a `Vector3`. - -```CSharp -myAction.AddCompositeBinding("3DVector") - .With("Up", "/w") - .With("Down", "/s") - .With("Left", "/a") - .With("Right", "/d"); - -// To set mode (2=analog, 1=digital, 0=digitalNormalized): -myAction.AddCompositeBinding("3DVector(mode=2)") - .With("Up", "/leftStick/up") - .With("Down", "/leftStick/down") - .With("Left", "/leftStick/left") - .With("Right", "/leftStick/right"); -``` - -The 3D vector Composite has four part Bindings. - -|Part|Type|Description| -|----|----|-----------| -|[`up`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_up)|`Button`|Controls representing `(0,1,0)` (+Y).| -|[`down`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_down)|`Button`|Controls representing `(0,-1,0)` (-Y).| -|[`left`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_left)|`Button`|Controls representing `(-1,0,0)` (-X).| -|[`right`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_right)|`Button`|Controls representing `(1,0,0)` (+X).| -|[`forward`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_forward)|`Button`|Controls representing `(0,0,1)` (+Z).| -|[`backward`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_backward)|`Button`|Controls representing `(0,0,-1)` (-Z).| - -In addition, you can set the following parameters on a 3D vector Composite: - -|Parameter|Description| -|---------|-----------| -|[`mode`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_mode)|Whether to treat the inputs as digital or as analog controls.

If this is set to [`Mode.DigitalNormalized`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector3Composite_Mode_DigitalNormalized), inputs are treated as buttons (off if below [`defaultButtonPressPoint`](../api/UnityEngine.InputSystem.InputSettings.html#UnityEngine_InputSystem_InputSettings_defaultButtonPressPoint) and on if equal to or greater). Each input is 0 or 1 depending on whether the button is pressed or not. The vector resulting from the up/down/left/right/forward/backward parts is normalized.

If this is set to [`Mode.Digital`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector3Composite_Mode_Digital), the behavior is essentially the same as [`Mode.DigitalNormalized`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector3Composite_Mode_DigitalNormalized) except that the resulting vector is not normalized.

Finally, if this is set to [`Mode.Analog`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector3Composite_Mode_Analog), inputs are treated as analog (that is, full floating-point values) and, other than [`down`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_down), [`left`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_left), and [`backward`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_backward) being inverted, values will be passed through as they are.

The default is [`Analog`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector3Composite_Mode_Analog).| - -### One Modifier - -![Add Binding With One Modifier](./Images/AddBindingWithOneModifier.png) - -![One Modifier Composite](./Images/OneModifierComposite.png) - -A Composite that requires the user to hold down a "modifier" button in addition to another control from which the actual value of the Binding is determined. This can be used, for example, for Bindings such as "SHIFT+1". Implemented in the [`OneModifierComposite`](../api/UnityEngine.InputSystem.Composites.OneModifierComposite.html) class. The buttons can be on any Device, and can be toggle buttons or full-range buttons such as gamepad triggers. - -The result is a value of the same type as the controls bound to the [`binding`](../api/UnityEngine.InputSystem.Composites.OneModifierComposite.html#UnityEngine_InputSystem_Composites_OneModifierComposite_binding) part. - -```CSharp -// Add binding for "CTRL+1". -myAction.AddCompositeBinding("OneModifier") - .With("Binding", "/1") - .With("Modifier", "/ctrl") - -// Add binding to mouse delta such that it only takes effect -// while the ALT key is down. -myAction.AddCompositeBinding("OneModifier") - .With("Binding", "/delta") - .With("Modifier", "/alt"); -``` - -The button with one modifier Composite has two part Bindings. - -|Part|Type|Description| -|----|----|-----------| -|[`modifier`](../api/UnityEngine.InputSystem.Composites.OneModifierComposite.html#UnityEngine_InputSystem_Composites_OneModifierComposite_modifier)|`Button`|Modifier that has to be held for `binding` to come through. If the user holds any of the buttons bound to the `modifier` at the same time as the button that triggers the action, the Composite assumes the value of the `modifier` Binding. If the user does not press any button bound to the `modifier`, the Composite remains at default value.| -|[`binding`](../api/UnityEngine.InputSystem.Composites.OneModifierComposite.html#UnityEngine_InputSystem_Composites_OneModifierComposite_binding)|Any|The control(s) whose value the Composite assumes while the user holds down the `modifier` button.| - -This Composite has no parameters. - -### Two Modifiers - -![Add Bindings With Two Modifiers](./Images/AddBindingWithTwoModifiers.png) - -![Two Modifiers Composite](./Images/TwoModifiersComposite.png) - -A Composite that requires the user to hold down two "modifier" buttons in addition to another control from which the actual value of the Binding is determined. This can be used, for example, for Bindings such as "SHIFT+CTRL+1". Implemented in the [`TwoModifiersComposite`](../api/UnityEngine.InputSystem.Composites.TwoModifiersComposite.html) class. The buttons can be on any Device, and can be toggle buttons or full-range buttons such as gamepad triggers. - -The result is a value of the same type as the controls bound to the [`binding`](../api/UnityEngine.InputSystem.Composites.TwoModifiersComposite.html#UnityEngine_InputSystem_Composites_TwoModifiersComposite_binding) part. - -```CSharp -myAction.AddCompositeBinding("TwoModifiers") - .With("Button", "/1") - .With("Modifier1", "/leftCtrl") - .With("Modifier1", "/rightCtrl") - .With("Modifier2", "/leftShift") - .With("Modifier2", "/rightShift"); -``` - -The button with two modifiers Composite has three part Bindings. - -|Part|Type|Description| -|----|----|-----------| -|[`modifier1`](../api/UnityEngine.InputSystem.Composites.TwoModifiersComposite.html#UnityEngine_InputSystem_Composites_TwoModifiersComposite_modifier1)|`Button`|The first modifier the user must hold alongside `modifier2`, for `binding` to come through. If the user does not press any button bound to the `modifier1`, the Composite remains at default value.| -|[`modifier2`](../api/UnityEngine.InputSystem.Composites.TwoModifiersComposite.html#UnityEngine_InputSystem_Composites_TwoModifiersComposite_modifier2)|`Button`|The second modifier the user must hold alongside `modifier1`, for `binding` to come through. If the user does not press any button bound to the `modifier2`, the Composite remains at default value.| -|[`binding`](../api/UnityEngine.InputSystem.Composites.TwoModifiersComposite.html#UnityEngine_InputSystem_Composites_TwoModifiersComposite_binding)|Any|The control(s) whose value the Composite assumes while the user presses both `modifier1` and `modifier2` at the same time.| - -This Composite has no parameters. - -### Writing custom Composites - -You can define new types of Composites, and register them with the API. Unity treats these the same as predefined types, which the Input System internally defines and registers in the same way. - -To define a new type of Composite, create a class based on [`InputBindingComposite`](../api/UnityEngine.InputSystem.InputBindingComposite-1.html). - -> __IMPORTANT__: Composites must be __stateless__. This means that you cannot store local state that changes depending on the input being processed. For __stateful__ processing on Bindings, see [interactions](./Interactions.md#writing-custom-interactions). - -```CSharp -// Use InputBindingComposite as a base class for a composite that returns -// values of type TValue. -// NOTE: It is possible to define a composite that returns different kinds of values -// but doing so requires deriving directly from InputBindingComposite. -#if UNITY_EDITOR -[InitializeOnLoad] // Automatically register in editor. -#endif -// Determine how GetBindingDisplayString() formats the composite by applying -// the DisplayStringFormat attribute. -[DisplayStringFormat("{firstPart}+{secondPart}")] -public class CustomComposite : InputBindingComposite -{ - // Each part binding is represented as a field of type int and annotated with - // InputControlAttribute. Setting "layout" restricts the controls that - // are made available for picking in the UI. - // - // On creation, the int value is set to an integer identifier for the binding - // part. This identifier can read values from InputBindingCompositeContext. - // See ReadValue() below. - [InputControl(layout = "Button")] - public int firstPart; - - [InputControl(layout = "Button")] - public int secondPart; - - // Any public field that is not annotated with InputControlAttribute is considered - // a parameter of the composite. This can be set graphically in the UI and also - // in the data (e.g. "custom(floatParameter=2.0)"). - public float floatParameter; - public bool boolParameter; - - // This method computes the resulting input value of the composite based - // on the input from its part bindings. - public override float ReadValue(ref InputBindingCompositeContext context) - { - var firstPartValue = context.ReadValue(firstPart); - var secondPartValue = context.ReadValue(secondPart); - - //... do some processing and return value - } - - // This method computes the current actuation of the binding as a whole. - public override float EvaluateMagnitude(ref InputBindingCompositeContext context) - { - // Compute normalized [0..1] magnitude value for current actuation level. - } - - static CustomComposite() - { - // Can give custom name or use default (type name with "Composite" clipped off). - // Same composite can be registered multiple times with different names to introduce - // aliases. - // - // NOTE: Registering from the static constructor using InitializeOnLoad and - // RuntimeInitializeOnLoadMethod is only one way. You can register the - // composite from wherever it works best for you. Note, however, that - // the registration has to take place before the composite is first used - // in a binding. Also, for the composite to show in the editor, it has - // to be registered from code that runs in edit mode. - InputSystem.RegisterBindingComposite(); - } - - [RuntimeInitializeOnLoadMethod(RuntimeInitializeLoadType.BeforeSceneLoad)] - static void Init() {} // Trigger static constructor. -} -``` - -The Composite should now appear in the editor UI when you add a Binding, and you can now use it in scripts. - -```CSharp - myAction.AddCompositeBinding("custom(floatParameter=2.0)") - .With("firstpart", "/buttonSouth") - .With("secondpart", "/buttonNorth"); -``` - -To define a custom parameter editor for the Composite, you can derive from [`InputParameterEditor`](../api/UnityEngine.InputSystem.Editor.InputParameterEditor-1.html). - -```CSharp -#if UNITY_EDITOR -public class CustomParameterEditor : InputParameterEditor -{ - public override void OnGUI() - { - EditorGUILayout.Label("Custom stuff"); - target.floatParameter = EditorGUILayout.FloatField("Some Parameter", target.floatParameter); - } -} -#endif -``` \ No newline at end of file diff --git a/Packages/com.unity.inputsystem/Documentation~/configure-action-type.md b/Packages/com.unity.inputsystem/Documentation~/configure-action-type.md index 55b6fb5430..4f34c1c277 100644 --- a/Packages/com.unity.inputsystem/Documentation~/configure-action-type.md +++ b/Packages/com.unity.inputsystem/Documentation~/configure-action-type.md @@ -1,2 +1,12 @@ -# Configure Action Type +# Configure Action type + +The action type influences how the Input System processes state changes for the action, and relates to whether this action represents a discrete on/off button-style interaction or a value that can change gradually over time. + +Configuring an action's **Action Type** is typically done when you create a new action, however you can also change the action type of an existing action. + +To configure an action's action type: + +1. [Create a new action](./create-edit-delete-actions.md) or select an existing in the [Actions Editor window](./actions-editor.md). +2. With the action selected, in the right-hand [Action Properties panel](./action-properties-panel.md), under **Action**, click the **Action Type** dropdown menu. +3. Select the action type from the available [action type options](action-type-reference.md). diff --git a/Packages/com.unity.inputsystem/Documentation~/configure-bindings-from-code.md b/Packages/com.unity.inputsystem/Documentation~/configure-bindings-from-code.md index e69de29bb2..7782475216 100644 --- a/Packages/com.unity.inputsystem/Documentation~/configure-bindings-from-code.md +++ b/Packages/com.unity.inputsystem/Documentation~/configure-bindings-from-code.md @@ -0,0 +1,557 @@ +# Configure bindings from code + + +[//]: # (TODO: Most of these examples should be moved to API docs and this page should provide an overview linking to those API pages.) + + +Each Binding has the following properties: + +|Property|Description| +|--------|-----------| +|[`path`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_path)|[Control path](Controls.md#control-paths) that identifies the control(s) from which the Action should receive input.

Example: `"/leftStick"`| +|[`overridePath`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_overridePath)|[Control path](Controls.md#control-paths) that overrides `path`. Unlike `path`, `overridePath` is not persistent, so you can use it to non-destructively override the path on a Binding. If it is set to something other than null, it takes effect and overrides `path`. To get the path which is currently in effect (that is, either `path` or `overridePath`), you can query the [`effectivePath`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_effectivePath) property.| +|[`action`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_action)|The name or ID of the Action that the Binding should trigger. Note that this can be null or empty (for instance, for [composites](#composite-bindings)). Not case-sensitive.

Example: `"fire"`| +|[`groups`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_groups)|A semicolon-separated list of Binding groups that the Binding belongs to. Can be null or empty. Binding groups can be anything, but are mostly used for [Control Schemes](#control-schemes). Not case-sensitive.

Example: `"Keyboard&Mouse;Gamepad"`| +|[`interactions`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_interactions)|A semicolon-separated list of [Interactions](Interactions.md) to apply to input on this Binding. Note that Unity appends Interactions applied to the [Action](actions.md) itself (if any) to this list. Not case-sensitive.

Example: `"slowTap;hold(duration=0.75)"`| +|[`processors`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_processors)|A semicolon-separated list of [Processors](Processors.md) to apply to input on this Binding. Note that Unity appends Processors applied to the [Action](actions.md) itself (if any) to this list. Not case-sensitive.

Processors on Bindings apply in addition to Processors on Controls that are providing values. For example, if you put a `stickDeadzone` Processor on a Binding and then bind it to `/leftStick`, you get deadzones applied twice: once from the deadzone Processor sitting on the `leftStick` Control, and once from the Binding.

Example: `"invert;axisDeadzone(min=0.1,max=0.95)"`| +|[`id`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_id)|Unique ID of the Binding. You can use it to identify the Binding when storing Binding overrides in user settings, for example.| +|[`name`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_name)|Optional name of the Binding. Identifies part names inside [Composites](#composite-bindings).

Example: `"Positive"`| +|[`isComposite`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_isComposite)|Whether the Binding acts as a [Composite](#composite-bindings).| +|[`isPartOfComposite`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_isPartOfComposite)|Whether the Binding is part of a [Composite](#composite-bindings).| + +To query the Bindings to a particular Action, you can use [`InputAction.bindings`](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction_bindings). To query a flat list of Bindings for all Actions in an Action Map, you can use [`InputActionMap.bindings`](../api/UnityEngine.InputSystem.InputActionMap.html#UnityEngine_InputSystem_InputActionMap_bindings). + + +### Erasing Bindings + +You can erase a binding by calling [`Erase`](../api/UnityEngine.InputSystem.InputActionSetupExtensions.BindingSyntax.html#UnityEngine_InputSystem_InputActionSetupExtensions_BindingSyntax_Erase_) on the [binding accessor](../api/UnityEngine.InputSystem.InputActionSetupExtensions.BindingSyntax.html). + +```CSharp +// Erase first binding on "fire" action. +playerInput.actions["fire"].ChangeBinding(0).Erase(); + +// Erase "2DVector" composite. This will also erase the part +// bindings of the composite. +playerInput.actions["move"].ChangeCompositeBinding("2DVector").Erase(); + +// Can also do this by using the name given to the composite binding. +playerInput.actions["move"].ChangeCompositeBinding("WASD").Erase(); + +// Erase first binding in "gameplay" action map. +playerInput.actions.FindActionMap("gameplay").ChangeBinding(0).Erase(); +``` + +### Adding Bindings + +New bindings can be added to an Action using [`AddAction`](../api/UnityEngine.InputSystem.InputActionSetupExtensions.html#UnityEngine_InputSystem_InputActionSetupExtensions_AddBinding_UnityEngine_InputSystem_InputAction_System_String_System_String_System_String_System_String_) or [`AddCompositeBinding`](../api/UnityEngine.InputSystem.InputActionSetupExtensions.html#UnityEngine_InputSystem_InputActionSetupExtensions_AddCompositeBinding_UnityEngine_InputSystem_InputAction_System_String_System_String_System_String_). + +```CSharp +// Add a binding for the left mouse button to the "fire" action. +playerInput.actions["fire"].AddBinding("/leftButton"); + +// Add a WASD composite binding to the "move" action. +playerInput.actions["move"] + .AddCompositeBinding("2DVector") + .With("Up", "/w") + .With("Left", "/a") + .With("Down", "/s") + .With("Right", "/d"); +``` + +### Setting parameters + +A Binding may, either through itself or through its associated Action, lead to [processor](Processors.md), [interaction](Interactions.md), and/or [composite](#composite-bindings) objects being created. These objects can have parameters you can configure through in the [Binding properties view](ActionsEditor.md#bindings) of the Action editor or through the API. This configuration will give parameters their default value. + +```CSharp +// Create an action with a "Hold" interaction on it. +// Set the "duration" parameter to 4 seconds. +var action = new InputAction(interactions: "hold(duration=4)"); +``` + +You can query the current value of any such parameter using the [`GetParameterValue`](../api/UnityEngine.InputSystem.InputActionRebindingExtensions.html#UnityEngine_InputSystem_InputActionRebindingExtensions_GetParameterValue_UnityEngine_InputSystem_InputAction_System_String_UnityEngine_InputSystem_InputBinding_) API. + +```CSharp +// This returns a PrimitiveValue?. It will be null if the +// parameter is not found. Otherwise, it is a PrimitiveValue +// which can be converted to a number or boolean. +var p = action.GetParameterValue("duration"); +Debug.Log("'duration' is set to: " + p.Value); +``` + +The above looks for the parameter on any object found on any of the bindings on the action. You can restrict either or both to a more narrow set. + +```CSharp +// Retrieve the value of the "duration" parameter specifically of a +// "Hold" interaction and only look on bindings in the "Gamepad" group. +action.GetParameterValue("hold:duration", InputBinding.MaskByGroup("Gamepad")); +``` + +Alternatively, you can use an expression parameter to encapsulate both the type and the name of the parameter you want to get the value of. This has the advantage of not needing a string parameter but rather references both the type and the name of the parameter in a typesafe way. + +```CSharp +// Retrieve the value of the "duration" parameter of TapInteraction. +// This version returns a float? instead of a PrimitiveValue? as it +// sees the type of "duration" at compile-time. +action.GetParameterValue((TapInteraction x) => x.duration); +``` + +To alter the current value of a parameter, you can use what is referred to as a "parameter override". You can apply these at the level of an individual [`InputAction`](../api/UnityEngine.InputSystem.InputAction.html), or at the level of an entire [`InputActionMap`](../api/UnityEngine.InputSystem.InputActionMap.html), or even at the level of an entire [`InputActionAsset`](../api/UnityEngine.InputSystem.InputActionAsset.html). Such overrides are stored internally and applied automatically even on bindings added later. + +To add an override, use the [`ApplyParameterOverride`](../api/UnityEngine.InputSystem.InputActionRebindingExtensions.html#UnityEngine_InputSystem_InputActionRebindingExtensions_ApplyParameterOverride_UnityEngine_InputSystem_InputAction_System_String_UnityEngine_InputSystem_Utilities_PrimitiveValue_UnityEngine_InputSystem_InputBinding_) API or any of its overloads. + +```CSharp +// Set the "duration" parameter on all bindings of the action to 4. +action.ApplyParameterOverride("duration", 4f); + +// Set the "duration" parameter specifically for "tap" interactions only. +action.ApplyParameterOverride("tap:duration", 0.5f); + +// Set the "duration" parameter on tap interactions but only for bindings +// in the "Gamepad" group. +action.ApplyParameterOverride("tap:duration", 0.5f, InputBinding.MaskByGroup("Gamepad"); + +// Set tap duration for all bindings in an action map. +map.ApplyParameterOverride("tap:duration", 0.5f); + +// Set tap duration for all bindings in an entire asset. +asset.ApplyParameterOverride("tap:duration", 0.5f); + +// Like for GetParameterValue, overloads are available that take +// an expression instead. +action.ApplyParameterOverride((TapInteraction x) => x.duration, 0.4f); +map.ApplyParameterOverride((TapInteraction x) => x.duration, 0.4f); +asset.ApplyParameterOverride((TapInteraction x) => x.duration, 0.4f); +``` + +The new value will be applied immediately and affect all composites, processors, and interactions already in use and targeted by the override. + +Note that if multiple parameter overrides are applied – especially when applying some directly to actions and some to maps or assets –, there may be conflicts between which override to apply. In this case, an attempt is made to chose the "most specific" override to apply. + +```CSharp +// Let's say you have an InputAction `action` that is part of an InputActionAsset asset. +var map = action.actionMap; +var asset = map.asset; + +// And you apply a "tap:duration" override to the action. +action.ApplyParameterOverride("tap:duration", 0.6f); + +// But also apply a "tap:duration" override to the action specifically +// for bindings in the "Gamepad" group. +action.ApplyParameterOverride("tap:duration", 1f, InputBinding.MaskByGroup("Gamepad")); + +// And finally also apply a "tap:duration" override to the entire asset. +asset.ApplyParameterOverride("tap:duration", 0.3f); + +// Now, bindings on `action` in the "Gamepad" group will use a value of 1 for tap durations, +// other bindings on `action` will use 0.6, and every other binding in the asset will use 0.3. +``` + +You can use parameter overrides, for example, to scale mouse delta values on a "Look" action. + +```CSharp +// Set up an example "Look" action. +var look = new InputAction("look", type: InputActionType.Value); +look.AddBinding("/delta", groups: "KeyboardMouse", processors: "scaleVector2"); +look.AddBinding("/rightStick", groups: "Gamepad", processors: "scaleVector2"); + +// Now you can adjust stick sensitivity separately from mouse sensitivity. +look.ApplyParameterOverride("scaleVector2:x", 0.5f, InputBinding.MaskByGroup("KeyboardMouse")); +look.ApplyParameterOverride("scaleVector2:y", 0.5f, InputBinding.MaskByGroup("KeyboardMouse")); + +look.ApplyParameterOverride("scaleVector2:x", 2f, InputBinding.MaskByGroup("Gamepad")); +look.ApplyParameterOverride("scaleVector2:y", 2f, InputBinding.MaskByGroup("Gamepad")); + +// Alternative to using groups, you can also apply overrides directly to specific binding paths. +look.ApplyParameterOverride("scaleVector2:x", 0.5f, new InputBinding("/delta")); +look.ApplyParameterOverride("scaleVector2:y", 0.5f, new InputBinding("/delta")); +``` + +>NOTE: Parameter overrides are *not* persisted along with an asset. + + + + + + + + +# Composite Bindings + +To create composites in code, you can use the [`AddCompositeBinding`](../api/UnityEngine.InputSystem.InputActionSetupExtensions.html#UnityEngine_InputSystem_InputActionSetupExtensions_AddCompositeBinding_UnityEngine_InputSystem_InputAction_System_String_System_String_System_String_) syntax. + +```CSharp +myAction.AddCompositeBinding("Axis") + .With("Positive", "/rightTrigger") + .With("Negative", "/leftTrigger"); +``` + +Each Composite consists of one Binding that has [`InputBinding.isComposite`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_isComposite) set to true, followed by one or more Bindings that have [`InputBinding.isPartOfComposiste`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_isPartOfComposite) set to true. In other words, several consecutive entries in [`InputActionMap.bindings`](../api/UnityEngine.InputSystem.InputActionMap.html#UnityEngine_InputSystem_InputActionMap_bindings) or [`InputAction.bindings`](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction_bindings) together form a Composite. + +Note that each composite part can be bound arbitrary many times. + +```CSharp +// Make both shoulders and triggers pull on the axis. +myAction.AddCompositeBinding("Axis") + .With("Positive", "/rightTrigger") + .With("Positive", "/rightShoulder") + .With("Negative", "/leftTrigger"); + .With("Negative", "/leftShoulder"); +``` + +Composites can have parameters, just like [Interactions](Interactions.md) and [Processors](Processors.md). + +```CSharp +myAction.AddCompositeBinding("Axis(whichSideWins=1)"); +``` + +There are currently five Composite types that come with the system out of the box: [1D-Axis](#1d-axis), [2D-Vector](#2d-vector), [3D-Vector](#3d-vector), [One Modifier](#one-modifier) and [Two Modifiers](#two-modifiers). Additionally, you can [add your own](#writing-custom-composites) types of Composites. + +### 1D axis + +A Composite made of two buttons: one that pulls a 1D axis in its negative direction, and another that pulls it in its positive direction. Implemented in the [`AxisComposite`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html) class. The result is a `float`. + +```CSharp +myAction.AddCompositeBinding("1DAxis") // Or just "Axis" + .With("Positive", "/rightTrigger") + .With("Negative", "/leftTrigger"); +``` + +The axis Composite has two part bindings. + +|Part|Type|Description| +|----|----|-----------| +|[`positive`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_positive)|`Button`|Controls pulling in the positive direction (towards [`maxValue`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_maxValue)).| +|[`negative`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_negative)|`Button`|Controls pulling in the negative direction, (towards [`minValue`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_minValue)).| + +You can set the following parameters on an axis Composite: + +|Parameter|Description| +|---------|-----------| +|[`whichSideWins`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_whichSideWins)|What happens if both [`positive`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_positive) and [`negative`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_negative) are actuated. See table below.| +|[`minValue`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_minValue)|The value returned if the [`negative`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_negative) side is actuated. Default is -1.| +|[`maxValue`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_maxValue)|The value returned if the [`positive`](../api/UnityEngine.InputSystem.Composites.AxisComposite.html#UnityEngine_InputSystem_Composites_AxisComposite_positive) side is actuated. Default is 1.| + +If Controls from both the `positive` and the `negative` side are actuated, then the resulting value of the axis Composite depends on the `whichSideWin` parameter setting. + +|[`WhichSideWins`](../api/UnityEngine.InputSystem.Composites.AxisComposite.WhichSideWins.html)|Description| +|---------------|-----------| +|(0) `Neither`|Neither side has precedence. The Composite returns the midpoint between `minValue` and `maxValue` as a result. At their default settings, this is 0.

This is the default value for this setting.| +|(1) `Positive`|The positive side has precedence and the Composite returns `maxValue`.| +|(2) `Negative`|The negative side has precedence and the Composite returns `minValue`.| + +>__Note__: There is no support yet for interpolating between the positive and negative over time. + +### 2D vector + +A Composite that represents a 4-way button setup like the D-pad on gamepads. Each button represents a cardinal direction. Implemented in the [`Vector2Composite`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.html) class. The result is a `Vector2`. + +This Composite is most useful for representing up-down-left-right controls, such as WASD keyboard input. + +```CSharp +myAction.AddCompositeBinding("2DVector") // Or "Dpad" + .With("Up", "/w") + .With("Down", "/s") + .With("Left", "/a") + .With("Right", "/d"); + +// To set mode (2=analog, 1=digital, 0=digitalNormalized): +myAction.AddCompositeBinding("2DVector(mode=2)") + .With("Up", "/leftStick/up") + .With("Down", "/leftStick/down") + .With("Left", "/leftStick/left") + .With("Right", "/leftStick/right"); +``` + +The 2D vector Composite has four part Bindings. + +|Part|Type|Description| +|----|----|-----------| +|[`up`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.html#UnityEngine_InputSystem_Composites_Vector2Composite_up)|`Button`|Controls representing `(0,1)` (+Y).| +|[`down`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.html#UnityEngine_InputSystem_Composites_Vector2Composite_down)|`Button`|Controls representing `(0,-1)` (-Y).| +|[`left`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.html#UnityEngine_InputSystem_Composites_Vector2Composite_left)|`Button`|Controls representing `(-1,0)` (-X).| +|[`right`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.html#UnityEngine_InputSystem_Composites_Vector2Composite_right)|`Button`|Controls representing `(1,0)` (+X).| + +In addition, you can set the following parameters on a 2D vector Composite: + +|Parameter|Description| +|---------|-----------| +|[`mode`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.html#UnityEngine_InputSystem_Composites_Vector2Composite_mode)|Whether to treat the inputs as digital or as analog controls.

If this is set to [`Mode.DigitalNormalized`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector2Composite_Mode_DigitalNormalized), inputs are treated as buttons (off if below [`defaultButtonPressPoint`](../api/UnityEngine.InputSystem.InputSettings.html#UnityEngine_InputSystem_InputSettings_defaultButtonPressPoint) and on if equal to or greater). Each input is 0 or 1 depending on whether the button is pressed or not. The vector resulting from the up/down/left/right parts is normalized. The result is a diamond-shaped 2D input range.

If this is set to [`Mode.Digital`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector2Composite_Mode_Digital), the behavior is essentially the same as [`Mode.DigitalNormalized`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector2Composite_Mode_DigitalNormalized) except that the resulting vector is not normalized.

Finally, if this is set to [`Mode.Analog`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector2Composite_Mode_Analog), inputs are treated as analog (i.e. full floating-point values) and, other than [`down`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.html#UnityEngine_InputSystem_Composites_Vector2Composite_down) and [`left`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.html#UnityEngine_InputSystem_Composites_Vector2Composite_left) being inverted, values will be passed through as is.

The default is [`Mode.DigitalNormalized`](../api/UnityEngine.InputSystem.Composites.Vector2Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector2Composite_Mode_DigitalNormalized).| + +>__Note__: There is no support yet for interpolating between the up/down/left/right over time. + +### 3D vector + +A Composite that represents a 6-way button where two combinations each control one axis of a 3D vector. Implemented in the [`Vector3Composite`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html) class. The result is a `Vector3`. + +```CSharp +myAction.AddCompositeBinding("3DVector") + .With("Up", "/w") + .With("Down", "/s") + .With("Left", "/a") + .With("Right", "/d"); + +// To set mode (2=analog, 1=digital, 0=digitalNormalized): +myAction.AddCompositeBinding("3DVector(mode=2)") + .With("Up", "/leftStick/up") + .With("Down", "/leftStick/down") + .With("Left", "/leftStick/left") + .With("Right", "/leftStick/right"); +``` + +The 3D vector Composite has four part Bindings. + +|Part|Type|Description| +|----|----|-----------| +|[`up`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_up)|`Button`|Controls representing `(0,1,0)` (+Y).| +|[`down`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_down)|`Button`|Controls representing `(0,-1,0)` (-Y).| +|[`left`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_left)|`Button`|Controls representing `(-1,0,0)` (-X).| +|[`right`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_right)|`Button`|Controls representing `(1,0,0)` (+X).| +|[`forward`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_forward)|`Button`|Controls representing `(0,0,1)` (+Z).| +|[`backward`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_backward)|`Button`|Controls representing `(0,0,-1)` (-Z).| + +In addition, you can set the following parameters on a 3D vector Composite: + +|Parameter|Description| +|---------|-----------| +|[`mode`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_mode)|Whether to treat the inputs as digital or as analog controls.

If this is set to [`Mode.DigitalNormalized`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector3Composite_Mode_DigitalNormalized), inputs are treated as buttons (off if below [`defaultButtonPressPoint`](../api/UnityEngine.InputSystem.InputSettings.html#UnityEngine_InputSystem_InputSettings_defaultButtonPressPoint) and on if equal to or greater). Each input is 0 or 1 depending on whether the button is pressed or not. The vector resulting from the up/down/left/right/forward/backward parts is normalized.

If this is set to [`Mode.Digital`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector3Composite_Mode_Digital), the behavior is essentially the same as [`Mode.DigitalNormalized`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector3Composite_Mode_DigitalNormalized) except that the resulting vector is not normalized.

Finally, if this is set to [`Mode.Analog`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector3Composite_Mode_Analog), inputs are treated as analog (that is, full floating-point values) and, other than [`down`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_down), [`left`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_left), and [`backward`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.html#UnityEngine_InputSystem_Composites_Vector3Composite_backward) being inverted, values will be passed through as they are.

The default is [`Analog`](../api/UnityEngine.InputSystem.Composites.Vector3Composite.Mode.html#UnityEngine_InputSystem_Composites_Vector3Composite_Mode_Analog).| + +### One Modifier + + +A Composite that requires the user to hold down a "modifier" button in addition to another control from which the actual value of the Binding is determined. This can be used, for example, for Bindings such as "SHIFT+1". Implemented in the [`OneModifierComposite`](../api/UnityEngine.InputSystem.Composites.OneModifierComposite.html) class. The buttons can be on any Device, and can be toggle buttons or full-range buttons such as gamepad triggers. + +The result is a value of the same type as the controls bound to the [`binding`](../api/UnityEngine.InputSystem.Composites.OneModifierComposite.html#UnityEngine_InputSystem_Composites_OneModifierComposite_binding) part. + +```CSharp +// Add binding for "CTRL+1". +myAction.AddCompositeBinding("OneModifier") + .With("Binding", "/1") + .With("Modifier", "/ctrl") + +// Add binding to mouse delta such that it only takes effect +// while the ALT key is down. +myAction.AddCompositeBinding("OneModifier") + .With("Binding", "/delta") + .With("Modifier", "/alt"); +``` + +The button with one modifier Composite has two part Bindings. + +|Part|Type|Description| +|----|----|-----------| +|[`modifier`](../api/UnityEngine.InputSystem.Composites.OneModifierComposite.html#UnityEngine_InputSystem_Composites_OneModifierComposite_modifier)|`Button`|Modifier that has to be held for `binding` to come through. If the user holds any of the buttons bound to the `modifier` at the same time as the button that triggers the action, the Composite assumes the value of the `modifier` Binding. If the user does not press any button bound to the `modifier`, the Composite remains at default value.| +|[`binding`](../api/UnityEngine.InputSystem.Composites.OneModifierComposite.html#UnityEngine_InputSystem_Composites_OneModifierComposite_binding)|Any|The control(s) whose value the Composite assumes while the user holds down the `modifier` button.| + +This Composite has no parameters. + +### Two Modifiers + + +A Composite that requires the user to hold down two "modifier" buttons in addition to another control from which the actual value of the Binding is determined. This can be used, for example, for Bindings such as "SHIFT+CTRL+1". Implemented in the [`TwoModifiersComposite`](../api/UnityEngine.InputSystem.Composites.TwoModifiersComposite.html) class. The buttons can be on any Device, and can be toggle buttons or full-range buttons such as gamepad triggers. + +The result is a value of the same type as the controls bound to the [`binding`](../api/UnityEngine.InputSystem.Composites.TwoModifiersComposite.html#UnityEngine_InputSystem_Composites_TwoModifiersComposite_binding) part. + +```CSharp +myAction.AddCompositeBinding("TwoModifiers") + .With("Button", "/1") + .With("Modifier1", "/leftCtrl") + .With("Modifier1", "/rightCtrl") + .With("Modifier2", "/leftShift") + .With("Modifier2", "/rightShift"); +``` + +The button with two modifiers Composite has three part Bindings. + +|Part|Type|Description| +|----|----|-----------| +|[`modifier1`](../api/UnityEngine.InputSystem.Composites.TwoModifiersComposite.html#UnityEngine_InputSystem_Composites_TwoModifiersComposite_modifier1)|`Button`|The first modifier the user must hold alongside `modifier2`, for `binding` to come through. If the user does not press any button bound to the `modifier1`, the Composite remains at default value.| +|[`modifier2`](../api/UnityEngine.InputSystem.Composites.TwoModifiersComposite.html#UnityEngine_InputSystem_Composites_TwoModifiersComposite_modifier2)|`Button`|The second modifier the user must hold alongside `modifier1`, for `binding` to come through. If the user does not press any button bound to the `modifier2`, the Composite remains at default value.| +|[`binding`](../api/UnityEngine.InputSystem.Composites.TwoModifiersComposite.html#UnityEngine_InputSystem_Composites_TwoModifiersComposite_binding)|Any|The control(s) whose value the Composite assumes while the user presses both `modifier1` and `modifier2` at the same time.| + +This Composite has no parameters. + +### Writing custom Composites + +You can define new types of Composites, and register them with the API. Unity treats these the same as predefined types, which the Input System internally defines and registers in the same way. + +To define a new type of Composite, create a class based on [`InputBindingComposite`](../api/UnityEngine.InputSystem.InputBindingComposite-1.html). + +> __IMPORTANT__: Composites must be __stateless__. This means that you cannot store local state that changes depending on the input being processed. For __stateful__ processing on Bindings, see [interactions](./Interactions.md#writing-custom-interactions). + +```CSharp +// Use InputBindingComposite as a base class for a composite that returns +// values of type TValue. +// NOTE: It is possible to define a composite that returns different kinds of values +// but doing so requires deriving directly from InputBindingComposite. +#if UNITY_EDITOR +[InitializeOnLoad] // Automatically register in editor. +#endif +// Determine how GetBindingDisplayString() formats the composite by applying +// the DisplayStringFormat attribute. +[DisplayStringFormat("{firstPart}+{secondPart}")] +public class CustomComposite : InputBindingComposite +{ + // Each part binding is represented as a field of type int and annotated with + // InputControlAttribute. Setting "layout" restricts the controls that + // are made available for picking in the UI. + // + // On creation, the int value is set to an integer identifier for the binding + // part. This identifier can read values from InputBindingCompositeContext. + // See ReadValue() below. + [InputControl(layout = "Button")] + public int firstPart; + + [InputControl(layout = "Button")] + public int secondPart; + + // Any public field that is not annotated with InputControlAttribute is considered + // a parameter of the composite. This can be set graphically in the UI and also + // in the data (e.g. "custom(floatParameter=2.0)"). + public float floatParameter; + public bool boolParameter; + + // This method computes the resulting input value of the composite based + // on the input from its part bindings. + public override float ReadValue(ref InputBindingCompositeContext context) + { + var firstPartValue = context.ReadValue(firstPart); + var secondPartValue = context.ReadValue(secondPart); + + //... do some processing and return value + } + + // This method computes the current actuation of the binding as a whole. + public override float EvaluateMagnitude(ref InputBindingCompositeContext context) + { + // Compute normalized [0..1] magnitude value for current actuation level. + } + + static CustomComposite() + { + // Can give custom name or use default (type name with "Composite" clipped off). + // Same composite can be registered multiple times with different names to introduce + // aliases. + // + // NOTE: Registering from the static constructor using InitializeOnLoad and + // RuntimeInitializeOnLoadMethod is only one way. You can register the + // composite from wherever it works best for you. Note, however, that + // the registration has to take place before the composite is first used + // in a binding. Also, for the composite to show in the editor, it has + // to be registered from code that runs in edit mode. + InputSystem.RegisterBindingComposite(); + } + + [RuntimeInitializeOnLoadMethod(RuntimeInitializeLoadType.BeforeSceneLoad)] + static void Init() {} // Trigger static constructor. +} +``` + +The Composite should now appear in the editor UI when you add a Binding, and you can now use it in scripts. + +```CSharp + myAction.AddCompositeBinding("custom(floatParameter=2.0)") + .With("firstpart", "/buttonSouth") + .With("secondpart", "/buttonNorth"); +``` + +To define a custom parameter editor for the Composite, you can derive from [`InputParameterEditor`](../api/UnityEngine.InputSystem.Editor.InputParameterEditor-1.html). + +```CSharp +#if UNITY_EDITOR +public class CustomParameterEditor : InputParameterEditor +{ + public override void OnGUI() + { + EditorGUILayout.Label("Custom stuff"); + target.floatParameter = EditorGUILayout.FloatField("Some Parameter", target.floatParameter); + } +} +#endif +``` + + +## Changing Bindings + +In general, you can change existing bindings via the [`InputActionSetupExtensions.ChangeBinding`](../api/UnityEngine.InputSystem.InputActionSetupExtensions.html#UnityEngine_InputSystem_InputActionSetupExtensions_ChangeBinding_UnityEngine_InputSystem_InputAction_System_Int32_) method. This returns an accessor that can be used to modify the properties of the targeted [`InputBinding`](../api/UnityEngine.InputSystem.InputBinding.html). Note that most of the write operations of the accessor are destructive. For non-destructive changes to bindings, see [Applying Overrides](#applying-overrides). + +```CSharp +// Get write access to the second binding of the 'fire' action. +var accessor = playerInput.actions['fire'].ChangeBinding(1); + +// You can also gain access through the InputActionMap. Each +// map contains an array of all its bindings (see InputActionMap.bindings). +// Here we gain access to the third binding in the map. +accessor = playerInput.actions.FindActionMap("gameplay").ChangeBinding(2); +``` + +You can use the resulting accessor to modify properties through methods such as [`WithPath`](../api/UnityEngine.InputSystem.InputActionSetupExtensions.BindingSyntax.html#UnityEngine_InputSystem_InputActionSetupExtensions_BindingSyntax_WithPath_) or [`WithProcessors`](../api/UnityEngine.InputSystem.InputActionSetupExtensions.BindingSyntax.html#UnityEngine_InputSystem_InputActionSetupExtensions_BindingSyntax_WithProcessors_). + +```CSharp +playerInput.actions["fire"].ChangeBinding(1) + // Change path to space key. + .WithPath("/space"); +``` + +You can also use the accessor to iterate through bindings using [`PreviousBinding`](../api/UnityEngine.InputSystem.InputActionSetupExtensions.BindingSyntax.html#UnityEngine_InputSystem_InputActionSetupExtensions_BindingSyntax_PreviousBinding_) and [`NextBinding`](../api/UnityEngine.InputSystem.InputActionSetupExtensions.BindingSyntax.html#UnityEngine_InputSystem_InputActionSetupExtensions_BindingSyntax_NextBinding_). + +```CSharp +// Move accessor to previous binding. +accessor = accessor.PreviousBinding(); + +// Move accessor to next binding. +accessor = accessor.NextBinding(); +``` + +If the given binding is a [composite](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_isComposite), you can address it by its name rather than by index. + +```CSharp +// Change the 2DVector composite of the "move" action. +playerInput.actions["move"].ChangeCompositeBinding("2DVector") + + +// +playerInput.actions["move"].ChangeBinding("WASD") +``` + + + +## Set a binding's control scheme from code + +Control schemes allow you to group types of bindings together according to their control type, so that you can enable or disable groups of bindings. For example, you might want to enable all keyboard and mouse bindings if the user presses a keyboard button or moves the mouse. + + +Unity stores these on the [`InputBinding`](../api/UnityEngine.InputSystem.InputBinding.html) class as a semicolon-separated string in the [`InputBinding.groups`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_groups) property, and you can use them for any arbitrary grouping of bindings. To enable different sets of binding groups for an [`InputActionMap`](../api/UnityEngine.InputSystem.InputActionMap.html) or [`InputActionAsset`](../api/UnityEngine.InputSystem.InputActionAsset.html), you can use the [`InputActionMap.bindingMask`](../api/UnityEngine.InputSystem.InputActionMap.html#UnityEngine_InputSystem_InputActionMap_bindingMask)/[`InputActionAsset.bindingMask`](../api/UnityEngine.InputSystem.InputActionAsset.html#UnityEngine_InputSystem_InputActionAsset_bindingMask) property. The Input System uses this to implement the concept of grouping Bindings into different [`InputControlSchemes`](../api/UnityEngine.InputSystem.InputControlScheme.html). + +Control Schemes use Binding groups to map Bindings in an [`InputActionMap`](../api/UnityEngine.InputSystem.InputActionMap.html) or [`InputActionAsset`](../api/UnityEngine.InputSystem.InputActionAsset.html) to different types of Devices. The [`PlayerInput`](player-input-component.md) class uses these to enable a matching Control Scheme for a new [user](UserManagement.md) joining the game, based on the Device they are playing on. + + + +### Apply binding overrides + +You can override aspects of any Binding at run-time non-destructively. Specific properties of [`InputBinding`](../api/UnityEngine.InputSystem.InputBinding.html) have an `override` variant that, if set, will take precedent over the property that they shadow. All `override` properties are of type `String`. + +|Property|Override|Description| +|--------|--------|-----------| +|[`path`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_path)|[`overridePath`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_overridePath)|Replaces the [Control path](./Controls.md#control-paths) that determines which Control(s) are referenced in the binding. If [`overridePath`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_overridePath) is set to an empty string, the binding is effectively disabled.

Example: `"/leftStick"`| +|[`processors`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_processors)|[`overrideProcessors`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_overrideProcessors)|Replaces the [processors](./Processors.md) applied to the binding.

Example: `"invert,normalize(min=0,max=10)"`| +|[`interactions`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_interactions)|[`overrideInteractions`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_overrideInteractions)|Replaces the [interactions](./Interactions.md) applied to the binding.

Example: `"tap(duration=0.5)"`| + +>NOTE: The `override` property values will not be saved along with the Actions (for example, when calling [`InputActionAsset.ToJson()`](../api/UnityEngine.InputSystem.InputActionAsset.html#UnityEngine_InputSystem_InputActionAsset_ToJson)). See [Saving and loading rebinds](#saving-and-loading-rebinds) for details about how to persist user rebinds. + +To set the various `override` properties, you can use the [`ApplyBindingOverride`](../api/UnityEngine.InputSystem.InputActionRebindingExtensions.html#UnityEngine_InputSystem_InputActionRebindingExtensions_ApplyBindingOverride_UnityEngine_InputSystem_InputAction_UnityEngine_InputSystem_InputBinding_) APIs. + +```CSharp +// Rebind the "fire" action to the left trigger on the gamepad. +playerInput.actions["fire"].ApplyBindingOverride("/leftTrigger"); +``` + +In most cases, it is best to locate specific bindings using APIs such as [`GetBindingIndexForControl`](../api/UnityEngine.InputSystem.InputActionRebindingExtensions.html#UnityEngine_InputSystem_InputActionRebindingExtensions_GetBindingIndexForControl_) and to then apply the override to that specific binding. + +```CSharp +// Find the "Jump" binding for the space key. +var jumpAction = playerInput.actions["Jump"]; +var bindingIndex = jumpAction.GetBindingIndexForControl(Keyboard.current.spaceKey); + +// And change it to the enter key. +jumpAction.ApplyBindingOverride(bindingIndex, "/enter"); +``` diff --git a/Packages/com.unity.inputsystem/Documentation~/configure-control-type.md b/Packages/com.unity.inputsystem/Documentation~/configure-control-type.md index 1fb82cfb5b..7ed65a9a21 100644 --- a/Packages/com.unity.inputsystem/Documentation~/configure-control-type.md +++ b/Packages/com.unity.inputsystem/Documentation~/configure-control-type.md @@ -1 +1,16 @@ -# Configure Control Type + +# Configure Control type + +The **Control Type** setting allows you to select the type of control expected by the action. This limits the types of [composite bindings](composite-bindings-reference.md) and [control types](control-types.md) shown when setting up bindings in the UI, and also limits which controls can be bound interactively to the action. This makes it simpler to select appropriate options when setting up bindings. + +Configuring an action's **Control Type** is typically done when you create a new action, however you can also change the control type of an existing action. + +To configure an action's action type: + +1. [Create a new action](./create-edit-delete-actions.md) or select an existing in the [Actions Editor window](./actions-editor.md). +2. With the action selected, in the right-hand [Action Properties panel](./action-properties-panel.md), under **Action**, click the **Action Type** dropdown menu. +3. Select the action type from the available [action type options](action-type-reference.md). + +## Additional resources +[Control types reference](./control-types.md) + diff --git a/Packages/com.unity.inputsystem/Documentation~/control-schemes-devices-menu.md b/Packages/com.unity.inputsystem/Documentation~/control-schemes-devices-menu.md new file mode 100644 index 0000000000..1085043ade --- /dev/null +++ b/Packages/com.unity.inputsystem/Documentation~/control-schemes-devices-menu.md @@ -0,0 +1,2 @@ +# Control Schemes and Devices menu + diff --git a/Packages/com.unity.inputsystem/Documentation~/control-types.md b/Packages/com.unity.inputsystem/Documentation~/control-types.md index 21649411f9..63f4dbc1ed 100644 --- a/Packages/com.unity.inputsystem/Documentation~/control-types.md +++ b/Packages/com.unity.inputsystem/Documentation~/control-types.md @@ -1,8 +1,6 @@ # Control types -All controls are based on the [`InputControl`](../api/UnityEngine.InputSystem.InputControl.html) base class. Most concrete implementations are based on [`InputControl`](../api/UnityEngine.InputSystem.InputControl-1.html). - -The Input System provides the following types of controls out of the box: +The Input System provides the following types of controls: |Control Type|Description|Example| |------------|-----------|-------| @@ -18,3 +16,6 @@ The Input System provides the following types of controls out of the box: |[`TouchControl`](../api/UnityEngine.InputSystem.Controls.TouchControl.html)|A control that represents all the properties of a touch on a [touch screen](Touch.md).|[`Touchscreen.primaryTouch`](../api/UnityEngine.InputSystem.Touchscreen.html#UnityEngine_InputSystem_Touchscreen_primaryTouch)| You can browse the set of all registered control layouts in the [input debugger](Debugging.md#debugging-layouts). + +All controls are based on the [`InputControl`](../api/UnityEngine.InputSystem.InputControl.html) base class. Most concrete implementations are based on [`InputControl`](../api/UnityEngine.InputSystem.InputControl-1.html). + diff --git a/Packages/com.unity.inputsystem/Documentation~/create-custom-composite-binding.md b/Packages/com.unity.inputsystem/Documentation~/create-custom-composite-binding.md new file mode 100644 index 0000000000..fb113c7367 --- /dev/null +++ b/Packages/com.unity.inputsystem/Documentation~/create-custom-composite-binding.md @@ -0,0 +1,99 @@ + +# Create custom composite bindings + +You can define new types of Composites, and register them with the API. Unity treats these the same as predefined types, which the Input System internally defines and registers in the same way. + +To define a new type of Composite, create a class based on [`InputBindingComposite`](../api/UnityEngine.InputSystem.InputBindingComposite-1.html). + +> __IMPORTANT__: Composites must be __stateless__. This means that you cannot store local state that changes depending on the input being processed. For __stateful__ processing on Bindings, see [interactions](./Interactions.md#writing-custom-interactions). + +```CSharp +// Use InputBindingComposite as a base class for a composite that returns +// values of type TValue. +// NOTE: It is possible to define a composite that returns different kinds of values +// but doing so requires deriving directly from InputBindingComposite. +#if UNITY_EDITOR +[InitializeOnLoad] // Automatically register in editor. +#endif +// Determine how GetBindingDisplayString() formats the composite by applying +// the DisplayStringFormat attribute. +[DisplayStringFormat("{firstPart}+{secondPart}")] +public class CustomComposite : InputBindingComposite +{ + // Each part binding is represented as a field of type int and annotated with + // InputControlAttribute. Setting "layout" restricts the controls that + // are made available for picking in the UI. + // + // On creation, the int value is set to an integer identifier for the binding + // part. This identifier can read values from InputBindingCompositeContext. + // See ReadValue() below. + [InputControl(layout = "Button")] + public int firstPart; + + [InputControl(layout = "Button")] + public int secondPart; + + // Any public field that is not annotated with InputControlAttribute is considered + // a parameter of the composite. This can be set graphically in the UI and also + // in the data (e.g. "custom(floatParameter=2.0)"). + public float floatParameter; + public bool boolParameter; + + // This method computes the resulting input value of the composite based + // on the input from its part bindings. + public override float ReadValue(ref InputBindingCompositeContext context) + { + var firstPartValue = context.ReadValue(firstPart); + var secondPartValue = context.ReadValue(secondPart); + + //... do some processing and return value + } + + // This method computes the current actuation of the binding as a whole. + public override float EvaluateMagnitude(ref InputBindingCompositeContext context) + { + // Compute normalized [0..1] magnitude value for current actuation level. + } + + static CustomComposite() + { + // Can give custom name or use default (type name with "Composite" clipped off). + // Same composite can be registered multiple times with different names to introduce + // aliases. + // + // NOTE: Registering from the static constructor using InitializeOnLoad and + // RuntimeInitializeOnLoadMethod is only one way. You can register the + // composite from wherever it works best for you. Note, however, that + // the registration has to take place before the composite is first used + // in a binding. Also, for the composite to show in the editor, it has + // to be registered from code that runs in edit mode. + InputSystem.RegisterBindingComposite(); + } + + [RuntimeInitializeOnLoadMethod(RuntimeInitializeLoadType.BeforeSceneLoad)] + static void Init() {} // Trigger static constructor. +} +``` + +The Composite should now appear in the editor UI when you add a Binding, and you can now use it in scripts. + +```CSharp + myAction.AddCompositeBinding("custom(floatParameter=2.0)") + .With("firstpart", "/buttonSouth") + .With("secondpart", "/buttonNorth"); +``` + +To define a custom parameter editor for the Composite, you can derive from [`InputParameterEditor`](../api/UnityEngine.InputSystem.Editor.InputParameterEditor-1.html). + +```CSharp +#if UNITY_EDITOR +public class CustomParameterEditor : InputParameterEditor +{ + public override void OnGUI() + { + EditorGUILayout.Label("Custom stuff"); + target.floatParameter = EditorGUILayout.FloatField("Some Parameter", target.floatParameter); + } +} +#endif +``` \ No newline at end of file diff --git a/Packages/com.unity.inputsystem/Documentation~/dealing-with-binding-conflicts.md b/Packages/com.unity.inputsystem/Documentation~/dealing-with-binding-conflicts.md deleted file mode 100644 index 966323b829..0000000000 --- a/Packages/com.unity.inputsystem/Documentation~/dealing-with-binding-conflicts.md +++ /dev/null @@ -1,124 +0,0 @@ - -### Dealing with binding conflicts - - -There are two situations where a given input may lead to ambiguity: - -1. Several Controls are bound to the same Action and more than one is feeding input into the Action at the same time. Example: an Action that is bound to both the left and right trigger on a Gamepad and both triggers are pressed. -2. The input is part of a sequence of inputs and there are several possible such sequences. Example: one Action is bound to the `B` key and another Action is bound to `Shift-B`. - -#### Multiple, concurrently used Controls - ->__Note:__ This section does not apply to [`PassThrough`](RespondingToActions.md#pass-through) Actions as they are by design meant to allow multiple concurrent inputs. - -For a [`Button`](RespondingToActions.md#button) or [`Value`](RespondingToActions.md#value) Action, there can only be one Control at any time that is "driving" the Action. This Control is considered the [`activeControl`](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction_activeControl). - -When an Action is bound to multiple Controls, the [`activeControl`](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction_activeControl) at any point is the one with the greatest level of ["actuation"](Controls.md#control-actuation), that is, the largest value returned from [`EvaluateMagnitude`](../api/UnityEngine.InputSystem.InputControl.html#UnityEngine_InputSystem_InputControl_EvaluateMagnitude_). If a Control exceeds the actuation level of the current [`activeControl`](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction_activeControl), it will itself become the active Control. - -The following example demonstrates this mechanism with a [`Button`](RespondingToActions.md#button) Action and also demonstrates the difference to a [`PassThrough`](RespondingToActions.md#pass-through) Action. - -```CSharp -// Create a button and a pass-through action and bind each of them -// to both triggers on the gamepad. -var buttonAction = new InputAction(type: InputActionType.Button, - binding: "/*Trigger"); -var passThroughAction = new InputAction(type: InputActionType.PassThrough, - binding: "/*Trigger"); - -buttonAction.performed += c => Debug.Log("${c.control.name} pressed (Button)"); -passThroughAction.performed += c => Debug.Log("${c.control.name} changed (Pass-Through)"); - -buttonAction.Enable(); -passThroughAction.Enable(); - -// Press the left trigger all the way down. -// This will trigger both buttonAction and passThroughAction. Both will -// see leftTrigger becoming the activeControl. -Set(gamepad.leftTrigger, 1f); - -// Will log -// "leftTrigger pressed (Button)" and -// "leftTrigger changed (Pass-Through)" - -// Press the right trigger halfway down. -// This will *not* trigger or otherwise change buttonAction as the right trigger -// is actuated *less* than the left one that is already driving action. -// However, passThrough action is not performing such tracking and will thus respond -// directly to the value change. It will perform and make rightTrigger its activeControl. -Set(gamepad.rightTrigger, 0.5f); - -// Will log -// "rightTrigger changed (Pass-Through)" - -// Release the left trigger. -// For buttonAction, this will mean that now all controls feeding into the action have -// been released and thus the button releases. activeControl will go back to null. -// For passThrough action, this is just another value change. So, the action performs -// and its active control changes to leftTrigger. -Set(gamepad.leftTrigger, 0f); - -// Will log -// "leftTrigger changed (Pass-Through)" -``` - -For [composite bindings](#composite-bindings), magnitudes of the composite as a whole rather than for individual Controls are tracked. However, [`activeControl`](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction_activeControl) will stick track individual Controls from the composite. - -##### Disabling Conflict Resolution - -Conflict resolution is always applied to [Button](RespondingToActions.md#button) and [Value](RespondingToActions.md#value) type Actions. However, it can be undesirable in situations when an Action is simply used to gather any and all inputs from bound Controls. For example, the following Action would monitor the A button of all available gamepads: - -```CSharp -var action = new InputAction(type: InputActionType.PassThrough, binding: "/buttonSouth"); -action.Enable(); -``` - -By using the [Pass-Through](RespondingToActions.md#pass-through) Action type, conflict resolution is bypassed and thus, pressing the A button on one gamepad will not result in a press on a different gamepad being ignored. - -#### Multiple input sequences (such as keyboard shortcuts) - ->__Note__: The mechanism described here only applies to Actions that are part of the same [`InputActionMap`](../api/UnityEngine.InputSystem.InputActionMap.html) or [`InputActionAsset`](../api/UnityEngine.InputSystem.InputActionAsset.html). - -Inputs that are used in combinations with other inputs may also lead to ambiguities. If, for example, the `b` key on the Keyboard is bound both on its own as well as in combination with the `shift` key, then if you first press `shift` and then `b`, the latter key press would be a valid input for either of the Actions. - -The way this is handled is that Bindings will be processed in the order of decreasing "complexity". This metric is derived automatically from the Binding: - -* A binding that is *not* part of a [composite](#composite-bindings) is assigned a complexity of 1. -* A binding that *is* part of a [composite](#composite-bindings) is assigned a complexity equal to the number of part bindings in the composite. - -In our example, this means that a [`OneModifier`](#one-modifier) composite Binding to `Shift+B` has a higher "complexity" than a Binding to `B` and thus is processed first. - -Additionally, the first Binding that results in the Action changing [phase](RespondingToActions.md#action-callbacks) will "consume" the input. This consuming will result in other Bindings to the same input not being processed. So in our example, when `Shift+B` "consumes" the `B` input, the Binding to `B` will be skipped. - -The following example illustrates how this works at the API level. - -```CSharp -// Create two actions in the same map. -var map = new InputActionMap(); -var bAction = map.AddAction("B"); -var shiftbAction = map.AddAction("ShiftB"); - -// Bind one of the actions to 'B' and the other to 'SHIFT+B'. -bAction.AddBinding("/b"); -shiftbAction.AddCompositeBinding("OneModifier") - .With("Modifier", "/shift") - .With("Binding", "/b"); - -// Print something to the console when the actions are triggered. -bAction.performed += _ => Debug.Log("B action performed"); -shiftbAction.performed += _ => Debug.Log("SHIFT+B action performed"); - -// Start listening to input. -map.Enable(); - -// Now, let's assume the left shift key on the keyboard is pressed (here, we manually -// press it with the InputTestFixture API). -Press(Keyboard.current.leftShiftKey); - -// And then the B is pressed. This is a valid input for both -// bAction as well as shiftbAction. -// -// What will happen now is that shiftbAction will do its processing first. In response, -// it will *perform* the action (i.e. we see the `performed` callback being invoked) and -// thus "consume" the input. bAction will stay silent as it will in turn be skipped over. -Press(keyboard.bKey); -``` \ No newline at end of file diff --git a/Packages/com.unity.inputsystem/Documentation~/edit-composite-bindings.md b/Packages/com.unity.inputsystem/Documentation~/edit-composite-bindings.md new file mode 100644 index 0000000000..0a3ed4164b --- /dev/null +++ b/Packages/com.unity.inputsystem/Documentation~/edit-composite-bindings.md @@ -0,0 +1,41 @@ +# Edit composite bindings + +You can add, edit, and delete [composite bindings](composite-bindings-reference.md) in the [Actions Editor window](actions-editor.md). + +When you [add a composite binding](./add-duplicate-delete-binding.md), the Input System creates a set of individual sub-bindings, or **parts** to match the type of composite. For example, a 2D Vector composite has four parts, up, down, left and right. These are visible in the hierarchy of the selected action in the Actions panel. Each part is a **simple binding** as described in [binding types](./binding-types.md). + +A new composite binding's parts are initially unassigned, and display "No Binding" in the actions panel. + +## Assign bindings to each part of the composite + +To assign bindings to each part of the composite: + +1. In the Actions panel, select the Action whose composite binding you want to edit. +2. Expand the Action's hierarchy as necessary to display the composite binding and its parts. +3. Select the part you want to configure +4. In the Binding Properties panel, [select a control for this part](./select-control-binding.md) using the Path field. + +## Change a composite's type + +A composite binding's type controls the selection of parts it has, and what value it outputs. To change a composite's type: + +1. In the Actions panel, select the Action whose type you want to change. +2. Expand the Action's hierarchy as necessary to display the composite binding. +3. Select the composite binding. +4. In the Binding Properties panel, select a new **Composite Type**. + +Changing a composite binding's type will change which parts it has, and any configurations on parts that are removed are lost. + +## Add or remove extra parts of the composite + +You can assign multiple Bindings to the same part, and duplicate, cut, copy and paste individual part bindings. To do this: + +1. In the Actions panel, select the Action whose composite binding you want to edit. +2. Expand the Action's hierarchy as necessary to display the composite binding and its parts. +3. Select the part you want to duplicate or remove +4. Right-click the part, and select Duplicate, Delete, Copy, Cut, or Paste + +By duplicating bindings and then editing the new duplicates, you can bind multiple contrls to the same composite part. For example, to create a single 2D composite which receives input from the WSAD keys and the arrow keys on a keyboard. + +![Duplicated Part Bindings](./Images/DuplicatedPartBindings.png)
+*A composite 2D vector binding with duplicated parts, allowing multiple keyboard keys to activate the same part of the composite.* diff --git a/Packages/com.unity.inputsystem/Documentation~/group-binding-to-control-scheme.md b/Packages/com.unity.inputsystem/Documentation~/group-binding-to-control-scheme.md index 0af06f784d..daf6c43da3 100644 --- a/Packages/com.unity.inputsystem/Documentation~/group-binding-to-control-scheme.md +++ b/Packages/com.unity.inputsystem/Documentation~/group-binding-to-control-scheme.md @@ -1,5 +1,14 @@ -## Group Bindings to Control Schemes +# Group Bindings to Control Schemes -A Binding can belong to any number of Binding groups. Unity stores these on the [`InputBinding`](../api/UnityEngine.InputSystem.InputBinding.html) class as a semicolon-separated string in the [`InputBinding.groups`](../api/UnityEngine.InputSystem.InputBinding.html#UnityEngine_InputSystem_InputBinding_groups) property, and you can use them for any arbitrary grouping of bindings. To enable different sets of binding groups for an [`InputActionMap`](../api/UnityEngine.InputSystem.InputActionMap.html) or [`InputActionAsset`](../api/UnityEngine.InputSystem.InputActionAsset.html), you can use the [`InputActionMap.bindingMask`](../api/UnityEngine.InputSystem.InputActionMap.html#UnityEngine_InputSystem_InputActionMap_bindingMask)/[`InputActionAsset.bindingMask`](../api/UnityEngine.InputSystem.InputActionAsset.html#UnityEngine_InputSystem_InputActionAsset_bindingMask) property. The Input System uses this to implement the concept of grouping Bindings into different [`InputControlSchemes`](../api/UnityEngine.InputSystem.InputControlScheme.html). +[Control schemes](control-schemes.md) allow you to group types of bindings together according to their control type, so that you can enable or disable groups of bindings. For example, for games that support both gamepads and keyboard & mouse, you might want to enable all keyboard and mouse bindings if the user presses any keyboard button or uses the mouse. -Control Schemes use Binding groups to map Bindings in an [`InputActionMap`](../api/UnityEngine.InputSystem.InputActionMap.html) or [`InputActionAsset`](../api/UnityEngine.InputSystem.InputActionAsset.html) to different types of Devices. The [`PlayerInput`](player-input-component.md) class uses these to enable a matching Control Scheme for a new [user](UserManagement.md) joining the game, based on the Device they are playing on. +You can select which [control schemes](control-schemes.md) a binding belongs to in the [Actions Editor window](./actions-editor.md). + +To do so: + +1. In the Actions panel, select the Action whose bindings you want to edit. +2. Expand the Action's hierarchy as necessary to display the bindings. +3. Select a binding to edit. For composite bindings, you must select one or more of its sub-bindings. +4. In the Binding Properties panel, under **Use in control scheme**, enable or disable the control schemes that you want this binding to belong to. + +You can edit the control schemes listed under **Use in control scheme**, by using the [Control Schemes menu](./control-schemes-devices-menu.md) at the top left of the [Actions Editor window](./actions-editor.md). \ No newline at end of file diff --git a/Packages/com.unity.inputsystem/Documentation~/introduction-to-bindings.md b/Packages/com.unity.inputsystem/Documentation~/introduction-to-bindings.md new file mode 100644 index 0000000000..971ce842c7 --- /dev/null +++ b/Packages/com.unity.inputsystem/Documentation~/introduction-to-bindings.md @@ -0,0 +1,13 @@ +# Introduction to bindings + +![](Images/ConceptsOverview.png) + +A **binding** represents a connection between an [Action](actions.md) and one or more [Controls](Controls.md) identified by a [Control path](./control-paths.md). For example, the right trigger of a gamepad (a control) might be bound to an an action named `accelerate`, so that pulling the right trigger causes a car to accelerate in your game. + +You can add multiple bindings to an action, which is generally useful for supporting multiple types of input device. For example, in the default set of actions, the "Move" action has a binding to the left gamepad stick and the WSAD keys, which means input through any of these bindings will perform the action. + +You can also bind multiple controls from the same device to an action. For example, both the left and right trigger of a gamepad could be mapped to the same action, so that pulling either trigger has the same result in your game. + +![The default "move" action with its multiple bindings highlighted](./Images/ActionWithMultipleBindings.png)
+_The default "Move" action in the Actions Editor window, displaying the multiple bindings associated with it._ + diff --git a/Packages/com.unity.inputsystem/Documentation~/pick-control-binding.md b/Packages/com.unity.inputsystem/Documentation~/pick-control-binding.md deleted file mode 100644 index 90d4999033..0000000000 --- a/Packages/com.unity.inputsystem/Documentation~/pick-control-binding.md +++ /dev/null @@ -1 +0,0 @@ -# Pick a control for a binding \ No newline at end of file diff --git a/Packages/com.unity.inputsystem/Documentation~/respond-to-input-at-runtime.md b/Packages/com.unity.inputsystem/Documentation~/respond-to-input-at-runtime.md index d0f595c898..b4f6da2c5f 100644 --- a/Packages/com.unity.inputsystem/Documentation~/respond-to-input-at-runtime.md +++ b/Packages/com.unity.inputsystem/Documentation~/respond-to-input-at-runtime.md @@ -13,25 +13,6 @@ For other situations where input is less frequent and directed to various differ ---- (TODO the below info was part of "responding to actions" but is most likely duplicate info found on other pages. need to check before removing.) -### Action types - -Each Action can be one of three different [Action types](../api/UnityEngine.InputSystem.InputActionType.html). You can select the Action type in the Input Action editor window, or by specifying the `type` parameter when calling the [`InputAction()`](../api/UnityEngine.InputSystem.InputAction.html#UnityEngine_InputSystem_InputAction__ctor_System_String_UnityEngine_InputSystem_InputActionType_System_String_System_String_System_String_System_String_) constructor. The Action type influences how the Input System processes state changes for the Action. The default Action type is `Value`. - -#### Value - -This is the default Action type. Use this for any inputs which should track continuous changes to the state of a Control. - - [`Value`](../api/UnityEngine.InputSystem.InputActionType.html#UnityEngine_InputSystem_InputActionType_Value) type actions continuously monitor all the Controls which are bound to the Action, and then choose the one which is the most actuated to be the Control driving the Action, and report the values from that Control in callbacks, triggered whenever the value changes. If a different bound Control actuated more, then that Control becomes the Control driving the Action, and the Action starts reporting values from that Control. This process is called [conflict resolution](ActionBindings.md#conflicting-inputs). This is useful if you want to allow different Controls to control an Action in the game, but only take input from one Control at the same time. - -When the Action initially enables, it performs an [initial state check](ActionBindings.md#initial-state-check) of all bound Controls. If any of them is actuated, the Action then triggers a callback with the current value. - -#### Button - -This is very similar to [`Value`](../api/UnityEngine.InputSystem.InputActionType.html#UnityEngine_InputSystem_InputActionType_Value), but [`Button`](../api/UnityEngine.InputSystem.InputActionType.html#UnityEngine_InputSystem_InputActionType_Button) type Actions can only be bound to [`ButtonControl`](../api/UnityEngine.InputSystem.Controls.ButtonControl.html) Controls, and don't perform an initial state check like [`Value`](../api/UnityEngine.InputSystem.InputActionType.html#UnityEngine_InputSystem_InputActionType_Value) Actions do (see the Value section above). Use this for inputs that trigger an Action once every time they are pressed. The initial state check is usually not useful in such cases, because it can trigger actions if the button is still held down from a previous press when the Action was enabled. - -#### Pass-Through - - [`Pass-Through`](../api/UnityEngine.InputSystem.InputActionType.html#UnityEngine_InputSystem_InputActionType_PassThrough) Actions bypass the [conflict resolution](ActionBindings.md#conflicting-inputs) process described above for `Value` Actions and don't use the concept of a specific Control driving the Action. Instead, any change to any bound Control triggers a callback with that Control's value. This is useful if you want to process all input from a set of Controls. ### Debugging Actions diff --git a/Packages/com.unity.inputsystem/Documentation~/restrict-binding-specific-device.md b/Packages/com.unity.inputsystem/Documentation~/restrict-binding-specific-device.md new file mode 100644 index 0000000000..a685f870a0 --- /dev/null +++ b/Packages/com.unity.inputsystem/Documentation~/restrict-binding-specific-device.md @@ -0,0 +1,13 @@ +# Restrict bindings to specific devices + +By default, actions [resolve their bindings](./binding-resolution.md) against all devices present that the Input System is aware of (that is, those listed in [`InputSystem.devices`](../api/UnityEngine.InputSystem.InputSystem.html#UnityEngine_InputSystem_InputSystem_devices)). For example, if there are two gamepads connected, a binding to `/buttonSouth` picks up both gamepads and allows the action to be performed from either gamepad. + +You can override this behavior by restricting an [action asset](./action-assets.md) or individual [action maps](./create-edit-delete-action-maps.md) to a specific set of Devices. If you do this, binding resolution only takes the controls of the specified devices into account. + +To restrict an action map to just the first gamepad: + +1. Set the `.devices` property of the action map to an array containing a reference to the first item in the `Gamepad.all` array. For example:

`actionMap.devices = new[] { Gamepad.all[0] };` + + +> [!NOTE] +> The Input System's [user management](user-management.md) feature and [Player Input component](player-input-component.md) make use of this automatically. They set the [`InputActionMap.devices`](../api/UnityEngine.InputSystem.InputActionMap.html#UnityEngine_InputSystem_InputActionMap_devices) for each player automatically, based on the device that is paired to each user. diff --git a/Packages/com.unity.inputsystem/Documentation~/select-control-binding.md b/Packages/com.unity.inputsystem/Documentation~/select-control-binding.md new file mode 100644 index 0000000000..7cafb141e2 --- /dev/null +++ b/Packages/com.unity.inputsystem/Documentation~/select-control-binding.md @@ -0,0 +1,52 @@ +# Select a control for a binding + +The [control path](control-paths.md) identifies the specific control that a binding is bound to, such as a specific button or stick on a gamepad, or a specific keyboard key. + +There are three ways to specify the control path for a binding in the [Actions Editor window](./actions-editor.md). These are: + +- Select the control path from a list, +- Select the control path using the listen feature, or +- Enter the path directly by typing text + +All three options are described below. For all these options, you must first: + +1. Open the [Actions Editor window](./actions-editor.md) +2. Select the **action** you want to edit from the [actions panel](./actions-panel.md) +3. Expand the action to reveal its bindings, or [add a new binding](./add-duplicate-delete-binding.md) +4. Select the **binding** you want to edit + +With a binding selected, you can then select the control path using any of these options. + +## Select the control path from a list + +To select the control path for a binding from a list of available controls: + + 1. Select the **Path** dropdown menu.

This displays a hierarchially arranged tree of input devices and controls that the Input System recognizes, which you can browse to find the control you want to bind. + + 2. Select the control you want from the list. + +![Control Picker](Images/InputControlPicker.png) + +Unity filters this list by the Action's [`Control Type`](./control-types.md) property. For example, if the Control type is `Vector2`, you can only select a Control that generates two-dimensional values, like a stick. + +The Device and Control tree is organized hierarchically from generic to specific. For example, the __Gamepad__ Control path `/buttonSouth` matches the lower action button on any gamepad. Alternatively, if you navigate to __Gamepad__ > __More Specific Gamepads__ and select __PS4 Controller__, and then choose the Control path `/buttonSouth`, this only matches the "Cross" button on PlayStation gamepads, and doesn't match any other gamepads. + +## Select the control path using the listen feature + +Instead of browsing the tree to find the Control you want, if you have the device connected that you want to bind, it can be easier to let the Input System listen for input from that device. To do this: + +1. Select the __Listen__ button. +2. Press the button or actuate the control on the device you want to bind to. +3. While the control picker is in listen mode, all buttons or controls you actuate appear in a list. +4. Select the binding from the list to finalise the binding. + + +## Enter the path directly by typing text + +You can choose to manually type the Binding path as text instead of using the Control picker. To do this: + +1. Select the __T__ button next to the Control path popup. This changes the **path** field from a popup menu to a text field, where you can enter any Binding string. +2. Type the control path's binding string into the text field. See [control paths](./control-paths.md) for more details about valid syntax for this field. + +Entering control paths as text also allows you to use wildcard (`*`) characters in your Bindings. For example, you can use a Binding path such as `/touch*/press` to bind to any finger pressed on the touchscreen, instead of manually binding to `/touch0/press`, `/touch1/press` and each other numbered touch. + diff --git a/Packages/com.unity.inputsystem/Documentation~/set-binding-parameters.md b/Packages/com.unity.inputsystem/Documentation~/set-binding-parameters.md deleted file mode 100644 index 40f4838660..0000000000 --- a/Packages/com.unity.inputsystem/Documentation~/set-binding-parameters.md +++ /dev/null @@ -1 +0,0 @@ -# Set binding parameters \ No newline at end of file