Am new to the new Input System so maybe am overlooking something simple, but I’ve created an action in the Input Action Asset, bound it to a key, and used the default “Button” with no Interactions (it says none are needed to use as a standard button). It calls a method that just prints “key pressed”. I get 2 triggers when the key is pressed and 2 when released, it should only be 1 when pressed, and nothing when released. If I set the Interactions/Trigger Behaviors, same results, extra presses everywhere. Press Point settings make no difference. What’s the deal?
You’re most likely getting multiple callbacks for all the different events in the button actuation sequence. How are you hooking up your listeners for the inpuit action?
If you’re using “Invoke UnityEvents”, you will get at least 3 calls for every button press:
- Started phase
- Performed phase
- Cancelled phase
You can disambiguate between them by reading the InputAction.CallbackContext object you get in your function. It has a phase property: https://docs.unity3d.com/Packages/com.unity.inputsystem@1.0/api/UnityEngine.InputSystem.InputAction.CallbackContext.html#UnityEngine_InputSystem_InputAction_CallbackContext_phase
Alternatively you can use C# events and control precisely which action phase you want a callback for.
The InputActionPhase sounds like it should work, but I don’t know how to access it. Right now the function has no arguments, and if I put an InputActionPhase argument in, the function no longer shows up in the Inspector event chooser.
The screenshot shows it selected, there’s no arguments, and it works, but it’s getting the multiple phases like you said. The code is just
public void testKeyInput()
{
print("key P pressed");
}
so, is there an easy addition to that so I can test which phase it’s in? Does it need a dedicated listener? I thought just the method could be called, but I guess because there are multiple calls to it, I’d need a specific listener.
I also would be fine with C# events, but would need to look that up. Wanted to see how it works with Unity Events first.
You need to use a parameter of type InputAction.CallbackContext then reassign the function in the UnityEvent with the dynamic parameter.
public void testKeyInput(InputAction.CallbackContext context)
{
print("key P pressed in phase " + context.phase.ToString());
}
Ah! Got it. I missed seeing the function in the Event function list at first because it’s in the Dynamic section, not in the Static section where I’m used to looking for them. It was 3am so I blame that haha. Works great and I should be able to figure the rest out, the new system looks like a big improvement once things are set up. Thanks!
public void testKeyInput(InputAction.CallbackContext context)
{
if (context.started == true) // "== true" is just for readability
{
print("key P pressed");
}
else if (context.canceled == true)
{
print("key P released");
}
}