godotengine / godot

Godot Engine – Multi-platform 2D and 3D game engine
https://godotengine.org
MIT License
91.46k stars 21.27k forks source link

Joystick Motion not triggering Pressed signal on Button when assigned via Shortcut #99331

Open hrkm opened 1 week ago

hrkm commented 1 week ago

Tested versions

4.3.stable.mono (official download)

System information

Godot v4.3.stable.mono - Windows 10.0.19045 - Vulkan (Mobile) - dedicated NVIDIA GeForce RTX 3090 (NVIDIA; 32.0.15.6109) - Intel(R) Core(TM) i9-10900K CPU @ 3.70GHz (20 Threads)

Issue description

When you attach InputEventAction shortcut to a Button, the button will not trigger it's pressed signal in response to that shortcut if the shortcut is triggered by gamepads joystick. At the same time if you log in the Input.IsActionPressed for the same InputEventAction in the _Process function, it correctly detects the action as pressed from joystick motion event.

I also tried using InputEventJoypadMotion in the Shortcut (instead of InputEventAction), but this also did not trigger the Shortcut.

Steps to reproduce

See attached project. There's single button with ui_up action assigned via Shortcut. The pressed signal for the button logs "UP", and in the _Process the same action is checked and if detected as pressed spam-prints "UP in _Process" line.

Upon launching, if you press up arrow on keyboard or up arrow on the gamepad DPAD, you will see in logs:

"UP"
"UP in _Process"
"UP in _Process"
"UP in _Process"
... (repeats the same as long as you keep the action pressed)

If you instead use the joystick and move it upwards, the logs will only show:

"UP in _Process"
"UP in _Process"
"UP in _Process"
... (repeats the same as long as you keep the action pressed)

The button does not respond to the action being pressed, even though the action is clearly marked as pressed from the other code path.

Minimal reproduction project (MRP)

joystickinputrepro.zip

hrkm commented 1 week ago

I have found a similar issue in https://github.com/godotengine/godot/issues/95588, but in that one the reporter claims the controller does not work at all - and in my case I can see the controller works as expected in the _Process function. I'm testing with PS5 DualSense controller.

hrkm commented 1 week ago

I think it boils down further to Input.IsActionJustPressed which does not respond to axis changes, but is triggered by DPAD / keyboard presses.

hrkm commented 1 week ago

Which is probably because that handler is based on physics frames as defined in https://github.com/godotengine/godot/blob/5efd124ca10bf46df62fa2441d80589777e54a5a/core/input/input.cpp#L403-L406 which I'm guessing might not be reporting for axis / joypad motion event?

hrkm commented 1 week ago

Further down, the pressed is only being assigned if there was a value in cache https://github.com/godotengine/godot/blob/5efd124ca10bf46df62fa2441d80589777e54a5a/core/input/input.cpp#L890-L893 but the cache is possibly never set to true based on the device state, since it's axis motion, not a button press https://github.com/godotengine/godot/blob/5efd124ca10bf46df62fa2441d80589777e54a5a/core/input/input.cpp#L1390

hrkm commented 1 week ago

Looking at the entirety though it should have also worked for axis changes? https://github.com/godotengine/godot/blob/5efd124ca10bf46df62fa2441d80589777e54a5a/core/input/input.cpp#L875-L897