Fix InputMap.action_erase_event() failing to erase events correctly.

This commit is contained in:
Marcel Admiraal 2021-05-13 18:13:24 +01:00
parent d0aaf4a1fd
commit 7104229a85
7 changed files with 74 additions and 59 deletions

View File

@ -88,7 +88,7 @@ bool InputEvent::action_match(const Ref<InputEvent> &p_event, bool *p_pressed, f
return false;
}
bool InputEvent::shortcut_match(const Ref<InputEvent> &p_event) const {
bool InputEvent::is_match(const Ref<InputEvent> &p_event, bool p_exact_match) const {
return false;
}
@ -110,7 +110,7 @@ void InputEvent::_bind_methods() {
ClassDB::bind_method(D_METHOD("as_text"), &InputEvent::as_text);
ClassDB::bind_method(D_METHOD("shortcut_match", "event"), &InputEvent::shortcut_match);
ClassDB::bind_method(D_METHOD("is_match", "event", "exact_match"), &InputEvent::is_match, DEFVAL(true));
ClassDB::bind_method(D_METHOD("is_action_type"), &InputEvent::is_action_type);
@ -194,6 +194,23 @@ void InputEventWithModifiers::set_modifiers_from_event(const InputEventWithModif
set_meta_pressed(event->is_meta_pressed());
}
uint32_t InputEventWithModifiers::get_modifiers_mask() const {
uint32_t mask = 0;
if (is_ctrl_pressed()) {
mask |= KEY_MASK_CTRL;
}
if (is_shift_pressed()) {
mask |= KEY_MASK_SHIFT;
}
if (is_alt_pressed()) {
mask |= KEY_MASK_ALT;
}
if (is_meta_pressed()) {
mask |= KEY_MASK_META;
}
return mask;
}
String InputEventWithModifiers::as_text() const {
Vector<String> mod_names;
@ -313,39 +330,11 @@ bool InputEventKey::is_echo() const {
}
uint32_t InputEventKey::get_keycode_with_modifiers() const {
uint32_t sc = keycode;
if (is_ctrl_pressed()) {
sc |= KEY_MASK_CTRL;
}
if (is_alt_pressed()) {
sc |= KEY_MASK_ALT;
}
if (is_shift_pressed()) {
sc |= KEY_MASK_SHIFT;
}
if (is_meta_pressed()) {
sc |= KEY_MASK_META;
}
return sc;
return keycode | get_modifiers_mask();
}
uint32_t InputEventKey::get_physical_keycode_with_modifiers() const {
uint32_t sc = physical_keycode;
if (is_ctrl_pressed()) {
sc |= KEY_MASK_CTRL;
}
if (is_alt_pressed()) {
sc |= KEY_MASK_ALT;
}
if (is_shift_pressed()) {
sc |= KEY_MASK_SHIFT;
}
if (is_meta_pressed()) {
sc |= KEY_MASK_META;
}
return sc;
return physical_keycode | get_modifiers_mask();
}
String InputEventKey::as_text() const {
@ -442,16 +431,14 @@ bool InputEventKey::action_match(const Ref<InputEvent> &p_event, bool *p_pressed
return match;
}
bool InputEventKey::shortcut_match(const Ref<InputEvent> &p_event) const {
bool InputEventKey::is_match(const Ref<InputEvent> &p_event, bool p_exact_match) const {
Ref<InputEventKey> key = p_event;
if (key.is_null()) {
return false;
}
uint32_t code = get_keycode_with_modifiers();
uint32_t event_code = key->get_keycode_with_modifiers();
return code == event_code;
return keycode == key->keycode &&
(!p_exact_match || get_modifiers_mask() == key->get_modifiers_mask());
}
void InputEventKey::_bind_methods() {
@ -599,6 +586,16 @@ bool InputEventMouseButton::action_match(const Ref<InputEvent> &p_event, bool *p
return match;
}
bool InputEventMouseButton::is_match(const Ref<InputEvent> &p_event, bool p_exact_match) const {
Ref<InputEventMouseButton> mb = p_event;
if (mb.is_null()) {
return false;
}
return button_index == mb->button_index &&
(!p_exact_match || get_modifiers_mask() == mb->get_modifiers_mask());
}
static const char *_mouse_button_descriptions[9] = {
TTRC("Left Mouse Button"),
TTRC("Right Mouse Button"),
@ -904,6 +901,16 @@ bool InputEventJoypadMotion::action_match(const Ref<InputEvent> &p_event, bool *
return match;
}
bool InputEventJoypadMotion::is_match(const Ref<InputEvent> &p_event, bool p_exact_match) const {
Ref<InputEventJoypadMotion> jm = p_event;
if (jm.is_null()) {
return false;
}
return axis == jm->axis &&
(!p_exact_match || ((axis_value < 0) == (jm->axis_value < 0)));
}
static const char *_joy_axis_descriptions[JOY_AXIS_MAX] = {
TTRC("Left Stick X-Axis, Joystick 0 X-Axis"),
TTRC("Left Stick Y-Axis, Joystick 0 Y-Axis"),
@ -987,7 +994,7 @@ bool InputEventJoypadButton::action_match(const Ref<InputEvent> &p_event, bool *
return match;
}
bool InputEventJoypadButton::shortcut_match(const Ref<InputEvent> &p_event) const {
bool InputEventJoypadButton::is_match(const Ref<InputEvent> &p_event, bool p_exact_match) const {
Ref<InputEventJoypadButton> button = p_event;
if (button.is_null()) {
return false;
@ -1229,7 +1236,7 @@ float InputEventAction::get_strength() const {
return strength;
}
bool InputEventAction::shortcut_match(const Ref<InputEvent> &p_event) const {
bool InputEventAction::is_match(const Ref<InputEvent> &p_event, bool p_exact_match) const {
if (p_event.is_null()) {
return false;
}

View File

@ -142,7 +142,8 @@ public:
virtual Ref<InputEvent> xformed_by(const Transform2D &p_xform, const Vector2 &p_local_ofs = Vector2()) const;
virtual bool action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float *p_raw_strength, float p_deadzone) const;
virtual bool shortcut_match(const Ref<InputEvent> &p_event) const;
virtual bool is_match(const Ref<InputEvent> &p_event, bool p_exact_match = true) const;
virtual bool is_action_type() const;
virtual bool accumulate(const Ref<InputEvent> &p_event) { return false; }
@ -212,6 +213,8 @@ public:
void set_modifiers_from_event(const InputEventWithModifiers *event);
uint32_t get_modifiers_mask() const;
virtual String as_text() const override;
virtual String to_string() override;
@ -252,7 +255,7 @@ public:
uint32_t get_physical_keycode_with_modifiers() const;
virtual bool action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float *p_raw_strength, float p_deadzone) const override;
virtual bool shortcut_match(const Ref<InputEvent> &p_event) const override;
virtual bool is_match(const Ref<InputEvent> &p_event, bool p_exact_match = true) const override;
virtual bool is_action_type() const override { return true; }
@ -313,7 +316,9 @@ public:
bool is_double_click() const;
virtual Ref<InputEvent> xformed_by(const Transform2D &p_xform, const Vector2 &p_local_ofs = Vector2()) const override;
virtual bool action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float *p_raw_strength, float p_deadzone) const override;
virtual bool is_match(const Ref<InputEvent> &p_event, bool p_exact_match = true) const override;
virtual bool is_action_type() const override { return true; }
virtual String as_text() const override;
@ -373,6 +378,7 @@ public:
virtual bool is_pressed() const override;
virtual bool action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float *p_raw_strength, float p_deadzone) const override;
virtual bool is_match(const Ref<InputEvent> &p_event, bool p_exact_match = true) const override;
virtual bool is_action_type() const override { return true; }
virtual String as_text() const override;
@ -401,9 +407,10 @@ public:
float get_pressure() const;
virtual bool action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float *p_raw_strength, float p_deadzone) const override;
virtual bool shortcut_match(const Ref<InputEvent> &p_event) const override;
virtual bool is_match(const Ref<InputEvent> &p_event, bool p_exact_match = true) const override;
virtual bool is_action_type() const override { return true; }
virtual String as_text() const override;
virtual String to_string() override;
@ -491,9 +498,10 @@ public:
virtual bool is_action(const StringName &p_action) const;
virtual bool action_match(const Ref<InputEvent> &p_event, bool *p_pressed, float *p_strength, float *p_raw_strength, float p_deadzone) const override;
virtual bool is_match(const Ref<InputEvent> &p_event, bool p_exact_match = true) const override;
virtual bool shortcut_match(const Ref<InputEvent> &p_event) const override;
virtual bool is_action_type() const override { return true; }
virtual String as_text() const override;
virtual String to_string() override;

View File

@ -130,12 +130,9 @@ List<Ref<InputEvent>>::Element *InputMap::_find_event(Action &p_action, const Re
for (List<Ref<InputEvent>>::Element *E = p_action.inputs.front(); E; E = E->next()) {
const Ref<InputEvent> e = E->get();
//if (e.type != Ref<InputEvent>::KEY && e.device != p_event.device) -- unsure about the KEY comparison, why is this here?
// continue;
int device = e->get_device();
if (device == ALL_DEVICES || device == p_event->get_device()) {
if (p_exact_match && e->shortcut_match(p_event)) {
if (p_exact_match && e->is_match(p_event, true)) {
return E;
} else if (!p_exact_match && e->action_match(p_event, p_pressed, p_strength, p_raw_strength, p_action.deadzone)) {
return E;

View File

@ -90,6 +90,18 @@
Returns [code]true[/code] if this input event is an echo event (only for events of type [InputEventKey]).
</description>
</method>
<method name="is_match" qualifiers="const">
<return type="bool">
</return>
<argument index="0" name="event" type="InputEvent">
</argument>
<argument index="1" name="exact_match" type="bool" default="true">
</argument>
<description>
Returns [code]true[/code] if the specified [code]event[/code] matches this event. Only valid for action events i.e key ([InputEventKey]), button ([InputEventMouseButton] or [InputEventJoypadButton]), axis [InputEventJoypadMotion] or action ([InputEventAction]) events.
If [code]exact_match[/code] is [code]false[/code], it ignores the input modifiers for [InputEventKey] and [InputEventMouseButton] events, and the direction for [InputEventJoypadMotion] events.
</description>
</method>
<method name="is_pressed" qualifiers="const">
<return type="bool">
</return>
@ -97,15 +109,6 @@
Returns [code]true[/code] if this input event is pressed. Not relevant for events of type [InputEventMouseMotion] or [InputEventScreenDrag].
</description>
</method>
<method name="shortcut_match" qualifiers="const">
<return type="bool">
</return>
<argument index="0" name="event" type="InputEvent">
</argument>
<description>
Returns [code]true[/code] if the given input event is checking for the same key ([InputEventKey]), button ([InputEventJoypadButton]) or action ([InputEventAction]).
</description>
</method>
<method name="xformed_by" qualifiers="const">
<return type="InputEvent">
</return>

View File

@ -1709,7 +1709,7 @@ void EditorSettings::set_builtin_action_override(const String &p_name, const Arr
// Check equality of each event.
for (List<Ref<InputEvent>>::Element *E = builtin_events.front(); E; E = E->next()) {
if (!E->get()->shortcut_match(p_events[event_idx])) {
if (!E->get()->is_match(p_events[event_idx])) {
same_as_builtin = false;
break;
}

View File

@ -289,7 +289,7 @@ void EditorSettingsDialog::_update_shortcuts() {
event_strings.push_back(I->get()->as_text());
// Only check if the events have been the same so far - once one fails, we don't need to check any more.
if (same_as_defaults && !key_default_events[count]->shortcut_match(I->get())) {
if (same_as_defaults && !key_default_events[count]->is_match(I->get())) {
same_as_defaults = false;
}
count++;

View File

@ -42,7 +42,7 @@ Ref<InputEvent> Shortcut::get_shortcut() const {
}
bool Shortcut::is_shortcut(const Ref<InputEvent> &p_event) const {
return shortcut.is_valid() && shortcut->shortcut_match(p_event);
return shortcut.is_valid() && shortcut->is_match(p_event, true);
}
String Shortcut::get_as_text() const {