Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add signals for InputEventAction to the Input singleton #75971

Open
wants to merge 1 commit into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
25 changes: 25 additions & 0 deletions core/input/input.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -89,6 +89,22 @@ Input::MouseMode Input::get_mouse_mode() const {
return get_mouse_mode_func();
}

void Input::_notification(int p_what) {
switch (p_what) {
case NOTIFICATION_POSTINITIALIZE: {
if (!InputMap::get_singleton()) {
return;
}
for (const KeyValue<StringName, InputMap::Action> &E : InputMap::get_singleton()->get_action_map()) {
Copy link
Member

@AThousandShips AThousandShips Apr 12, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You need to check that the InputMap is created, it isn't always, it isn't when running tests for example, so you need to check that InputMap::get_singleton() returns non-null

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thank-you for providing that fix information. I for sure would not have figured that out on my own

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No problem! I had to dig a little before I realised why this could happen myself

MethodInfo signal_pressed(Variant::NIL, vformat("%s_pressed", E.key));
add_user_signal(signal_pressed);
MethodInfo signal_released(Variant::NIL, vformat("%s_released", E.key));
add_user_signal(signal_released);
}
} break;
}
}

void Input::_bind_methods() {
ClassDB::bind_method(D_METHOD("is_anything_pressed"), &Input::is_anything_pressed);
ClassDB::bind_method(D_METHOD("is_key_pressed", "keycode"), &Input::is_key_pressed);
Expand Down Expand Up @@ -165,6 +181,7 @@ void Input::_bind_methods() {
BIND_ENUM_CONSTANT(CURSOR_HSPLIT);
BIND_ENUM_CONSTANT(CURSOR_HELP);

ADD_SIGNAL(MethodInfo("action_toggled", PropertyInfo(Variant::STRING, "action"), PropertyInfo(Variant::BOOL, "pressed")));
ADD_SIGNAL(MethodInfo("joy_connection_changed", PropertyInfo(Variant::INT, "device"), PropertyInfo(Variant::BOOL, "connected")));
}

Expand Down Expand Up @@ -680,6 +697,14 @@ void Input::_parse_input_event_impl(const Ref<InputEvent> &p_event, bool p_is_em
action.raw_strength = 0.0f;
action.exact = InputMap::get_singleton()->event_is_action(p_event, E.key, true);
action_state[E.key] = action;
// For any action
emit_signal("action_toggled", E.key, action.pressed);
// For specific actions defined in 'InputMap'
if (action.pressed) {
emit_signal(vformat("%s_pressed", E.key));
} else {
emit_signal(vformat("%s_released", E.key));
}
}
action_state[E.key].strength = p_event->get_action_strength(E.key);
action_state[E.key].raw_strength = p_event->get_action_raw_strength(E.key);
Expand Down
1 change: 1 addition & 0 deletions core/input/input.h
Original file line number Diff line number Diff line change
Expand Up @@ -240,6 +240,7 @@ class Input : public Object {
EventDispatchFunc event_dispatch_function = nullptr;

protected:
void _notification(int p_what);
static void _bind_methods();

public:
Expand Down
8 changes: 8 additions & 0 deletions doc/classes/Input.xml
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
</brief_description>
<description>
A singleton that deals with inputs. This includes key presses, mouse buttons and movement, joypads, and input actions. Actions and their events can be set in the [b]Input Map[/b] tab in the [b]Project &gt; Project Settings[/b], or with the [InputMap] class.
[b]Note:[/b] For every [InputEventAction] in the [InputMap] there exists a [code]*_pressed[/code] and [code]*_released[/code] signal that can be connected to using [method Object.connect].
</description>
<tutorials>
<link title="Inputs documentation index">$DOCS_URL/tutorials/inputs/index.html</link>
Expand Down Expand Up @@ -390,6 +391,13 @@
</member>
</members>
<signals>
<signal name="action_toggled">
<param index="0" name="action" type="String" />
<param index="1" name="pressed" type="bool" />
<description>
Emitted when an action is pressed or released. Only works for default actions, or those added in the project settings.
</description>
</signal>
<signal name="joy_connection_changed">
<param index="0" name="device" type="int" />
<param index="1" name="connected" type="bool" />
Expand Down