mirror of
https://github.com/godotengine/godot.git
synced 2025-01-22 10:32:54 -05:00
Merge pull request #98792 from MJacred/fix_remove_joy_mapping
Fix `Input::remove_joy_mapping`
This commit is contained in:
commit
49481c12bc
3 changed files with 62 additions and 7 deletions
|
@ -1602,9 +1602,6 @@ void Input::parse_mapping(const String &p_mapping) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
CharString uid;
|
|
||||||
uid.resize(17);
|
|
||||||
|
|
||||||
mapping.uid = entry[0];
|
mapping.uid = entry[0];
|
||||||
mapping.name = entry[1];
|
mapping.name = entry[1];
|
||||||
|
|
||||||
|
@ -1712,15 +1709,72 @@ void Input::add_joy_mapping(const String &p_mapping, bool p_update_existing) {
|
||||||
}
|
}
|
||||||
|
|
||||||
void Input::remove_joy_mapping(const String &p_guid) {
|
void Input::remove_joy_mapping(const String &p_guid) {
|
||||||
|
// One GUID can exist multiple times in `map_db`, and
|
||||||
|
// `add_joy_mapping` can choose not to update the existing mapping,
|
||||||
|
// so the indices can be all over the place. Therefore we need to remember them.
|
||||||
|
Vector<int> removed_idx;
|
||||||
|
int min_removed_idx = -1;
|
||||||
|
int max_removed_idx = -1;
|
||||||
|
int fallback_mapping_offset = 0;
|
||||||
|
|
||||||
for (int i = map_db.size() - 1; i >= 0; i--) {
|
for (int i = map_db.size() - 1; i >= 0; i--) {
|
||||||
if (p_guid == map_db[i].uid) {
|
if (p_guid == map_db[i].uid) {
|
||||||
map_db.remove_at(i);
|
map_db.remove_at(i);
|
||||||
|
|
||||||
|
if (max_removed_idx == -1) {
|
||||||
|
max_removed_idx = i;
|
||||||
|
}
|
||||||
|
min_removed_idx = i;
|
||||||
|
removed_idx.push_back(i);
|
||||||
|
|
||||||
|
if (i < fallback_mapping) {
|
||||||
|
fallback_mapping_offset++;
|
||||||
|
} else if (i == fallback_mapping) {
|
||||||
|
fallback_mapping = -1;
|
||||||
|
WARN_PRINT_ONCE(vformat("Removed fallback joypad input mapping \"%s\". This could lead to joypads not working as intended.", p_guid));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (min_removed_idx == -1) {
|
||||||
|
return; // Nothing removed.
|
||||||
|
}
|
||||||
|
|
||||||
|
if (fallback_mapping > 0) {
|
||||||
|
// Fix the shifted index.
|
||||||
|
fallback_mapping -= fallback_mapping_offset;
|
||||||
|
}
|
||||||
|
|
||||||
|
int removed_idx_size = removed_idx.size();
|
||||||
|
|
||||||
|
// Update joypad mapping references: some
|
||||||
|
// * should use the fallback_mapping (if set; if not, they get unmapped), or
|
||||||
|
// * need their mapping reference fixed, because the deletion(s) offset them.
|
||||||
for (KeyValue<int, Joypad> &E : joy_names) {
|
for (KeyValue<int, Joypad> &E : joy_names) {
|
||||||
Joypad &joy = E.value;
|
Joypad &joy = E.value;
|
||||||
if (joy.uid == p_guid) {
|
if (joy.mapping < min_removed_idx) {
|
||||||
_set_joypad_mapping(joy, -1);
|
continue; // Not affected.
|
||||||
|
}
|
||||||
|
|
||||||
|
if (joy.mapping > max_removed_idx) {
|
||||||
|
_set_joypad_mapping(joy, joy.mapping - removed_idx_size);
|
||||||
|
continue; // Simple offset fix.
|
||||||
|
}
|
||||||
|
|
||||||
|
// removed_idx is in reverse order (ie. high to low), because the first loop is in reverse order.
|
||||||
|
for (int i = 0; i < removed_idx.size(); i++) {
|
||||||
|
if (removed_idx[i] == joy.mapping) {
|
||||||
|
// Set to fallback_mapping, if defined, else unmap the joypad.
|
||||||
|
// Currently, the fallback_mapping is only set internally, and only for Android.
|
||||||
|
_set_joypad_mapping(joy, fallback_mapping);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if (removed_idx[i] < joy.mapping) {
|
||||||
|
// Complex offset fix:
|
||||||
|
// This mapping was shifted by `(removed_idx_size - i)` deletions.
|
||||||
|
_set_joypad_mapping(joy, joy.mapping - (removed_idx_size - i));
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -184,7 +184,7 @@ private:
|
||||||
|
|
||||||
HashSet<uint32_t> ignored_device_ids;
|
HashSet<uint32_t> ignored_device_ids;
|
||||||
|
|
||||||
int fallback_mapping = -1;
|
int fallback_mapping = -1; // Index of the guid in map_db.
|
||||||
|
|
||||||
CursorShape default_shape = CURSOR_ARROW;
|
CursorShape default_shape = CURSOR_ARROW;
|
||||||
|
|
||||||
|
|
|
@ -311,7 +311,8 @@
|
||||||
<return type="void" />
|
<return type="void" />
|
||||||
<param index="0" name="guid" type="String" />
|
<param index="0" name="guid" type="String" />
|
||||||
<description>
|
<description>
|
||||||
Removes all mappings from the internal database that match the given GUID.
|
Removes all mappings from the internal database that match the given GUID. All currently connected joypads that use this GUID will become unmapped.
|
||||||
|
On Android, Godot will map to an internal fallback mapping.
|
||||||
</description>
|
</description>
|
||||||
</method>
|
</method>
|
||||||
<method name="set_accelerometer">
|
<method name="set_accelerometer">
|
||||||
|
|
Loading…
Reference in a new issue