Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
godotengine
GitHub Repository: godotengine/godot
Path: blob/master/core/input/input_event.cpp
9903 views
1
/**************************************************************************/
2
/* input_event.cpp */
3
/**************************************************************************/
4
/* This file is part of: */
5
/* GODOT ENGINE */
6
/* https://godotengine.org */
7
/**************************************************************************/
8
/* Copyright (c) 2014-present Godot Engine contributors (see AUTHORS.md). */
9
/* Copyright (c) 2007-2014 Juan Linietsky, Ariel Manzur. */
10
/* */
11
/* Permission is hereby granted, free of charge, to any person obtaining */
12
/* a copy of this software and associated documentation files (the */
13
/* "Software"), to deal in the Software without restriction, including */
14
/* without limitation the rights to use, copy, modify, merge, publish, */
15
/* distribute, sublicense, and/or sell copies of the Software, and to */
16
/* permit persons to whom the Software is furnished to do so, subject to */
17
/* the following conditions: */
18
/* */
19
/* The above copyright notice and this permission notice shall be */
20
/* included in all copies or substantial portions of the Software. */
21
/* */
22
/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */
23
/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */
24
/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. */
25
/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */
26
/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */
27
/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */
28
/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */
29
/**************************************************************************/
30
31
#include "input_event.h"
32
33
#include "core/input/input_map.h"
34
#include "core/input/shortcut.h"
35
#include "core/os/keyboard.h"
36
#include "core/os/os.h"
37
38
void InputEvent::set_device(int p_device) {
39
device = p_device;
40
emit_changed();
41
}
42
43
int InputEvent::get_device() const {
44
return device;
45
}
46
47
bool InputEvent::is_action(const StringName &p_action, bool p_exact_match) const {
48
return InputMap::get_singleton()->event_is_action(Ref<InputEvent>(const_cast<InputEvent *>(this)), p_action, p_exact_match);
49
}
50
51
bool InputEvent::is_action_pressed(const StringName &p_action, bool p_allow_echo, bool p_exact_match) const {
52
bool pressed_state;
53
bool valid = InputMap::get_singleton()->event_get_action_status(Ref<InputEvent>(const_cast<InputEvent *>(this)), p_action, p_exact_match, &pressed_state, nullptr, nullptr);
54
return valid && pressed_state && (p_allow_echo || !is_echo());
55
}
56
57
bool InputEvent::is_action_released(const StringName &p_action, bool p_exact_match) const {
58
bool pressed_state;
59
bool valid = InputMap::get_singleton()->event_get_action_status(Ref<InputEvent>(const_cast<InputEvent *>(this)), p_action, p_exact_match, &pressed_state, nullptr, nullptr);
60
return valid && !pressed_state;
61
}
62
63
float InputEvent::get_action_strength(const StringName &p_action, bool p_exact_match) const {
64
float strength;
65
bool valid = InputMap::get_singleton()->event_get_action_status(Ref<InputEvent>(const_cast<InputEvent *>(this)), p_action, p_exact_match, nullptr, &strength, nullptr);
66
return valid ? strength : 0.0f;
67
}
68
69
float InputEvent::get_action_raw_strength(const StringName &p_action, bool p_exact_match) const {
70
float raw_strength;
71
bool valid = InputMap::get_singleton()->event_get_action_status(Ref<InputEvent>(const_cast<InputEvent *>(this)), p_action, p_exact_match, nullptr, nullptr, &raw_strength);
72
return valid ? raw_strength : 0.0f;
73
}
74
75
bool InputEvent::is_canceled() const {
76
return canceled;
77
}
78
79
bool InputEvent::is_pressed() const {
80
return pressed && !canceled;
81
}
82
83
bool InputEvent::is_released() const {
84
return !pressed && !canceled;
85
}
86
87
bool InputEvent::is_echo() const {
88
return false;
89
}
90
91
Ref<InputEvent> InputEvent::xformed_by(const Transform2D &p_xform, const Vector2 &p_local_ofs) const {
92
return Ref<InputEvent>(const_cast<InputEvent *>(this));
93
}
94
95
bool InputEvent::action_match(const Ref<InputEvent> &p_event, bool p_exact_match, float p_deadzone, bool *r_pressed, float *r_strength, float *r_raw_strength) const {
96
return false;
97
}
98
99
bool InputEvent::is_match(const Ref<InputEvent> &p_event, bool p_exact_match) const {
100
return false;
101
}
102
103
bool InputEvent::is_action_type() const {
104
return false;
105
}
106
107
void InputEvent::_bind_methods() {
108
ClassDB::bind_method(D_METHOD("set_device", "device"), &InputEvent::set_device);
109
ClassDB::bind_method(D_METHOD("get_device"), &InputEvent::get_device);
110
111
ClassDB::bind_method(D_METHOD("is_action", "action", "exact_match"), &InputEvent::is_action, DEFVAL(false));
112
ClassDB::bind_method(D_METHOD("is_action_pressed", "action", "allow_echo", "exact_match"), &InputEvent::is_action_pressed, DEFVAL(false), DEFVAL(false));
113
ClassDB::bind_method(D_METHOD("is_action_released", "action", "exact_match"), &InputEvent::is_action_released, DEFVAL(false));
114
ClassDB::bind_method(D_METHOD("get_action_strength", "action", "exact_match"), &InputEvent::get_action_strength, DEFVAL(false));
115
116
ClassDB::bind_method(D_METHOD("is_canceled"), &InputEvent::is_canceled);
117
ClassDB::bind_method(D_METHOD("is_pressed"), &InputEvent::is_pressed);
118
ClassDB::bind_method(D_METHOD("is_released"), &InputEvent::is_released);
119
ClassDB::bind_method(D_METHOD("is_echo"), &InputEvent::is_echo);
120
121
ClassDB::bind_method(D_METHOD("as_text"), &InputEvent::as_text);
122
123
ClassDB::bind_method(D_METHOD("is_match", "event", "exact_match"), &InputEvent::is_match, DEFVAL(true));
124
125
ClassDB::bind_method(D_METHOD("is_action_type"), &InputEvent::is_action_type);
126
127
ClassDB::bind_method(D_METHOD("accumulate", "with_event"), &InputEvent::accumulate);
128
129
ClassDB::bind_method(D_METHOD("xformed_by", "xform", "local_ofs"), &InputEvent::xformed_by, DEFVAL(Vector2()));
130
131
ADD_PROPERTY(PropertyInfo(Variant::INT, "device"), "set_device", "get_device");
132
133
BIND_CONSTANT(DEVICE_ID_EMULATION);
134
}
135
136
///////////////////////////////////
137
138
void InputEventFromWindow::_bind_methods() {
139
ClassDB::bind_method(D_METHOD("set_window_id", "id"), &InputEventFromWindow::set_window_id);
140
ClassDB::bind_method(D_METHOD("get_window_id"), &InputEventFromWindow::get_window_id);
141
ADD_PROPERTY(PropertyInfo(Variant::INT, "window_id"), "set_window_id", "get_window_id");
142
}
143
144
void InputEventFromWindow::set_window_id(int64_t p_id) {
145
window_id = p_id;
146
emit_changed();
147
}
148
149
int64_t InputEventFromWindow::get_window_id() const {
150
return window_id;
151
}
152
153
///////////////////////////////////
154
155
void InputEventWithModifiers::set_command_or_control_autoremap(bool p_enabled) {
156
if (command_or_control_autoremap == p_enabled) {
157
return;
158
}
159
command_or_control_autoremap = p_enabled;
160
if (command_or_control_autoremap) {
161
if (OS::get_singleton()->has_feature("macos") || OS::get_singleton()->has_feature("web_macos") || OS::get_singleton()->has_feature("web_ios")) {
162
ctrl_pressed = false;
163
meta_pressed = true;
164
} else {
165
ctrl_pressed = true;
166
meta_pressed = false;
167
}
168
} else {
169
ctrl_pressed = false;
170
meta_pressed = false;
171
}
172
notify_property_list_changed();
173
emit_changed();
174
}
175
176
bool InputEventWithModifiers::is_command_or_control_autoremap() const {
177
return command_or_control_autoremap;
178
}
179
180
bool InputEventWithModifiers::is_command_or_control_pressed() const {
181
if (OS::get_singleton()->has_feature("macos") || OS::get_singleton()->has_feature("web_macos") || OS::get_singleton()->has_feature("web_ios")) {
182
return meta_pressed;
183
} else {
184
return ctrl_pressed;
185
}
186
}
187
188
void InputEventWithModifiers::set_shift_pressed(bool p_enabled) {
189
shift_pressed = p_enabled;
190
emit_changed();
191
}
192
193
bool InputEventWithModifiers::is_shift_pressed() const {
194
return shift_pressed;
195
}
196
197
void InputEventWithModifiers::set_alt_pressed(bool p_enabled) {
198
alt_pressed = p_enabled;
199
emit_changed();
200
}
201
202
bool InputEventWithModifiers::is_alt_pressed() const {
203
return alt_pressed;
204
}
205
206
void InputEventWithModifiers::set_ctrl_pressed(bool p_enabled) {
207
ERR_FAIL_COND_MSG(command_or_control_autoremap, "Command or Control autoremapping is enabled, cannot set Control directly!");
208
ctrl_pressed = p_enabled;
209
emit_changed();
210
}
211
212
bool InputEventWithModifiers::is_ctrl_pressed() const {
213
return ctrl_pressed;
214
}
215
216
void InputEventWithModifiers::set_meta_pressed(bool p_enabled) {
217
ERR_FAIL_COND_MSG(command_or_control_autoremap, "Command or Control autoremapping is enabled, cannot set Meta directly!");
218
meta_pressed = p_enabled;
219
emit_changed();
220
}
221
222
bool InputEventWithModifiers::is_meta_pressed() const {
223
return meta_pressed;
224
}
225
226
void InputEventWithModifiers::set_modifiers_from_event(const InputEventWithModifiers *event) {
227
set_alt_pressed(event->is_alt_pressed());
228
set_shift_pressed(event->is_shift_pressed());
229
set_ctrl_pressed(event->is_ctrl_pressed());
230
set_meta_pressed(event->is_meta_pressed());
231
}
232
233
BitField<KeyModifierMask> InputEventWithModifiers::get_modifiers_mask() const {
234
BitField<KeyModifierMask> mask = {};
235
if (is_ctrl_pressed()) {
236
mask.set_flag(KeyModifierMask::CTRL);
237
}
238
if (is_shift_pressed()) {
239
mask.set_flag(KeyModifierMask::SHIFT);
240
}
241
if (is_alt_pressed()) {
242
mask.set_flag(KeyModifierMask::ALT);
243
}
244
if (is_meta_pressed()) {
245
mask.set_flag(KeyModifierMask::META);
246
}
247
if (is_command_or_control_autoremap()) {
248
if (OS::get_singleton()->has_feature("macos") || OS::get_singleton()->has_feature("web_macos") || OS::get_singleton()->has_feature("web_ios")) {
249
mask.set_flag(KeyModifierMask::META);
250
} else {
251
mask.set_flag(KeyModifierMask::CTRL);
252
}
253
}
254
return mask;
255
}
256
257
String InputEventWithModifiers::as_text() const {
258
Vector<String> mod_names;
259
260
if (is_ctrl_pressed()) {
261
mod_names.push_back(find_keycode_name(Key::CTRL));
262
}
263
if (is_shift_pressed()) {
264
mod_names.push_back(find_keycode_name(Key::SHIFT));
265
}
266
if (is_alt_pressed()) {
267
mod_names.push_back(find_keycode_name(Key::ALT));
268
}
269
if (is_meta_pressed()) {
270
mod_names.push_back(find_keycode_name(Key::META));
271
}
272
273
if (!mod_names.is_empty()) {
274
return String("+").join(mod_names);
275
} else {
276
return "";
277
}
278
}
279
280
String InputEventWithModifiers::to_string() {
281
return as_text();
282
}
283
284
void InputEventWithModifiers::_bind_methods() {
285
ClassDB::bind_method(D_METHOD("set_command_or_control_autoremap", "enable"), &InputEventWithModifiers::set_command_or_control_autoremap);
286
ClassDB::bind_method(D_METHOD("is_command_or_control_autoremap"), &InputEventWithModifiers::is_command_or_control_autoremap);
287
288
ClassDB::bind_method(D_METHOD("is_command_or_control_pressed"), &InputEventWithModifiers::is_command_or_control_pressed);
289
290
ClassDB::bind_method(D_METHOD("set_alt_pressed", "pressed"), &InputEventWithModifiers::set_alt_pressed);
291
ClassDB::bind_method(D_METHOD("is_alt_pressed"), &InputEventWithModifiers::is_alt_pressed);
292
293
ClassDB::bind_method(D_METHOD("set_shift_pressed", "pressed"), &InputEventWithModifiers::set_shift_pressed);
294
ClassDB::bind_method(D_METHOD("is_shift_pressed"), &InputEventWithModifiers::is_shift_pressed);
295
296
ClassDB::bind_method(D_METHOD("set_ctrl_pressed", "pressed"), &InputEventWithModifiers::set_ctrl_pressed);
297
ClassDB::bind_method(D_METHOD("is_ctrl_pressed"), &InputEventWithModifiers::is_ctrl_pressed);
298
299
ClassDB::bind_method(D_METHOD("set_meta_pressed", "pressed"), &InputEventWithModifiers::set_meta_pressed);
300
ClassDB::bind_method(D_METHOD("is_meta_pressed"), &InputEventWithModifiers::is_meta_pressed);
301
302
ClassDB::bind_method(D_METHOD("get_modifiers_mask"), &InputEventWithModifiers::get_modifiers_mask);
303
304
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "command_or_control_autoremap"), "set_command_or_control_autoremap", "is_command_or_control_autoremap");
305
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "alt_pressed"), "set_alt_pressed", "is_alt_pressed");
306
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "shift_pressed"), "set_shift_pressed", "is_shift_pressed");
307
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "ctrl_pressed"), "set_ctrl_pressed", "is_ctrl_pressed");
308
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "meta_pressed"), "set_meta_pressed", "is_meta_pressed");
309
}
310
311
void InputEventWithModifiers::_validate_property(PropertyInfo &p_property) const {
312
if (command_or_control_autoremap) {
313
// Cannot be used with Meta/Command or Control!
314
if (p_property.name == "meta_pressed") {
315
p_property.usage ^= PROPERTY_USAGE_STORAGE;
316
p_property.usage ^= PROPERTY_USAGE_EDITOR;
317
}
318
if (p_property.name == "ctrl_pressed") {
319
p_property.usage ^= PROPERTY_USAGE_STORAGE;
320
p_property.usage ^= PROPERTY_USAGE_EDITOR;
321
}
322
} else {
323
if (p_property.name == "command_or_control_autoremap") {
324
p_property.usage ^= PROPERTY_USAGE_STORAGE;
325
}
326
}
327
}
328
329
///////////////////////////////////
330
331
void InputEventKey::set_pressed(bool p_pressed) {
332
pressed = p_pressed;
333
emit_changed();
334
}
335
336
void InputEventKey::set_keycode(Key p_keycode) {
337
keycode = p_keycode;
338
emit_changed();
339
}
340
341
Key InputEventKey::get_keycode() const {
342
return keycode;
343
}
344
345
void InputEventKey::set_key_label(Key p_key_label) {
346
key_label = p_key_label;
347
emit_changed();
348
}
349
350
Key InputEventKey::get_key_label() const {
351
return key_label;
352
}
353
354
void InputEventKey::set_physical_keycode(Key p_keycode) {
355
physical_keycode = p_keycode;
356
emit_changed();
357
}
358
359
Key InputEventKey::get_physical_keycode() const {
360
return physical_keycode;
361
}
362
363
void InputEventKey::set_unicode(char32_t p_unicode) {
364
unicode = p_unicode;
365
emit_changed();
366
}
367
368
char32_t InputEventKey::get_unicode() const {
369
return unicode;
370
}
371
372
void InputEventKey::set_location(KeyLocation p_key_location) {
373
location = p_key_location;
374
emit_changed();
375
}
376
377
KeyLocation InputEventKey::get_location() const {
378
return location;
379
}
380
381
void InputEventKey::set_echo(bool p_enable) {
382
echo = p_enable;
383
emit_changed();
384
}
385
386
bool InputEventKey::is_echo() const {
387
return echo;
388
}
389
390
Key InputEventKey::get_keycode_with_modifiers() const {
391
return keycode | get_modifiers_mask();
392
}
393
394
Key InputEventKey::get_physical_keycode_with_modifiers() const {
395
return physical_keycode | get_modifiers_mask();
396
}
397
398
Key InputEventKey::get_key_label_with_modifiers() const {
399
return key_label | get_modifiers_mask();
400
}
401
402
String InputEventKey::as_text_physical_keycode() const {
403
String kc;
404
405
if (physical_keycode != Key::NONE) {
406
kc = keycode_get_string(physical_keycode);
407
} else {
408
kc = "(" + RTR("Unset") + ")";
409
}
410
411
if (kc.is_empty()) {
412
return kc;
413
}
414
415
String mods_text = InputEventWithModifiers::as_text();
416
return mods_text.is_empty() ? kc : mods_text + "+" + kc;
417
}
418
419
String InputEventKey::as_text_keycode() const {
420
String kc;
421
422
if (keycode != Key::NONE) {
423
kc = keycode_get_string(keycode);
424
} else {
425
kc = "(" + RTR("Unset") + ")";
426
}
427
428
if (kc.is_empty()) {
429
return kc;
430
}
431
432
String mods_text = InputEventWithModifiers::as_text();
433
return mods_text.is_empty() ? kc : mods_text + "+" + kc;
434
}
435
436
String InputEventKey::as_text_key_label() const {
437
String kc;
438
439
if (key_label != Key::NONE) {
440
kc = keycode_get_string(key_label);
441
} else {
442
kc = "(" + RTR("Unset") + ")";
443
}
444
445
if (kc.is_empty()) {
446
return kc;
447
}
448
449
String mods_text = InputEventWithModifiers::as_text();
450
return mods_text.is_empty() ? kc : mods_text + "+" + kc;
451
}
452
453
String InputEventKey::as_text_location() const {
454
String loc;
455
456
switch (location) {
457
case KeyLocation::LEFT:
458
loc = "left";
459
break;
460
case KeyLocation::RIGHT:
461
loc = "right";
462
break;
463
default:
464
break;
465
}
466
467
return loc;
468
}
469
470
String InputEventKey::as_text() const {
471
String kc;
472
473
if (keycode == Key::NONE && physical_keycode == Key::NONE && key_label != Key::NONE) {
474
kc = keycode_get_string(key_label) + " (Unicode)";
475
} else if (keycode != Key::NONE) {
476
kc = keycode_get_string(keycode);
477
} else if (physical_keycode != Key::NONE) {
478
kc = keycode_get_string(physical_keycode) + " (" + RTR("Physical") + ")";
479
} else {
480
kc = "(" + RTR("Unset") + ")";
481
}
482
483
if (kc.is_empty()) {
484
return kc;
485
}
486
487
String mods_text = InputEventWithModifiers::as_text();
488
return mods_text.is_empty() ? kc : mods_text + "+" + kc;
489
}
490
491
String InputEventKey::to_string() {
492
String p = is_pressed() ? "true" : "false";
493
String e = is_echo() ? "true" : "false";
494
495
String kc = "";
496
String physical = "false";
497
498
String loc = as_text_location();
499
if (loc.is_empty()) {
500
loc = "unspecified";
501
}
502
503
if (keycode == Key::NONE && physical_keycode == Key::NONE && unicode != 0) {
504
kc = "U+" + String::num_uint64(unicode, 16) + " (" + String::chr(unicode) + ")";
505
} else if (keycode != Key::NONE) {
506
kc = itos((int64_t)keycode) + " (" + keycode_get_string(keycode) + ")";
507
} else if (physical_keycode != Key::NONE) {
508
kc = itos((int64_t)physical_keycode) + " (" + keycode_get_string(physical_keycode) + ")";
509
physical = "true";
510
} else {
511
kc = "(" + RTR("Unset") + ")";
512
}
513
514
String mods = InputEventWithModifiers::as_text();
515
mods = mods.is_empty() ? "none" : mods;
516
517
return vformat("InputEventKey: keycode=%s, mods=%s, physical=%s, location=%s, pressed=%s, echo=%s", kc, mods, physical, loc, p, e);
518
}
519
520
Ref<InputEventKey> InputEventKey::create_reference(Key p_keycode, bool p_physical) {
521
Ref<InputEventKey> ie;
522
ie.instantiate();
523
if (p_physical) {
524
ie->set_physical_keycode(p_keycode & KeyModifierMask::CODE_MASK);
525
} else {
526
ie->set_keycode(p_keycode & KeyModifierMask::CODE_MASK);
527
}
528
529
char32_t ch = char32_t(p_keycode & KeyModifierMask::CODE_MASK);
530
if (ch < 0xd800 || (ch > 0xdfff && ch <= 0x10ffff)) {
531
ie->set_unicode(ch);
532
}
533
534
if ((p_keycode & KeyModifierMask::SHIFT) != Key::NONE) {
535
ie->set_shift_pressed(true);
536
}
537
if ((p_keycode & KeyModifierMask::ALT) != Key::NONE) {
538
ie->set_alt_pressed(true);
539
}
540
if ((p_keycode & KeyModifierMask::CMD_OR_CTRL) != Key::NONE) {
541
ie->set_command_or_control_autoremap(true);
542
if ((p_keycode & KeyModifierMask::CTRL) != Key::NONE || (p_keycode & KeyModifierMask::META) != Key::NONE) {
543
WARN_PRINT("Invalid Key Modifiers: Command or Control autoremapping is enabled, Meta and Control values are ignored!");
544
}
545
} else {
546
if ((p_keycode & KeyModifierMask::CTRL) != Key::NONE) {
547
ie->set_ctrl_pressed(true);
548
}
549
if ((p_keycode & KeyModifierMask::META) != Key::NONE) {
550
ie->set_meta_pressed(true);
551
}
552
}
553
554
return ie;
555
}
556
557
bool InputEventKey::action_match(const Ref<InputEvent> &p_event, bool p_exact_match, float p_deadzone, bool *r_pressed, float *r_strength, float *r_raw_strength) const {
558
Ref<InputEventKey> key = p_event;
559
if (key.is_null()) {
560
return false;
561
}
562
563
bool match;
564
if (keycode == Key::NONE && physical_keycode == Key::NONE && key_label != Key::NONE) {
565
match = key_label == key->key_label;
566
} else if (keycode != Key::NONE) {
567
match = keycode == key->keycode;
568
} else if (physical_keycode != Key::NONE) {
569
match = physical_keycode == key->physical_keycode;
570
if (location != KeyLocation::UNSPECIFIED) {
571
match &= location == key->location;
572
}
573
} else {
574
match = false;
575
}
576
577
Key action_mask = (Key)(int64_t)get_modifiers_mask();
578
Key key_mask = (Key)(int64_t)key->get_modifiers_mask();
579
if (key->is_pressed()) {
580
match &= (action_mask & key_mask) == action_mask;
581
}
582
if (p_exact_match) {
583
match &= action_mask == key_mask;
584
}
585
if (match) {
586
bool key_pressed = key->is_pressed();
587
if (r_pressed != nullptr) {
588
*r_pressed = key_pressed;
589
}
590
float strength = key_pressed ? 1.0f : 0.0f;
591
if (r_strength != nullptr) {
592
*r_strength = strength;
593
}
594
if (r_raw_strength != nullptr) {
595
*r_raw_strength = strength;
596
}
597
}
598
return match;
599
}
600
601
bool InputEventKey::is_match(const Ref<InputEvent> &p_event, bool p_exact_match) const {
602
Ref<InputEventKey> key = p_event;
603
if (key.is_null()) {
604
return false;
605
}
606
607
if (keycode == Key::NONE && physical_keycode == Key::NONE && key_label != Key::NONE) {
608
return (key_label == key->key_label) &&
609
(!p_exact_match || get_modifiers_mask() == key->get_modifiers_mask());
610
} else if (keycode != Key::NONE) {
611
return (keycode == key->keycode) &&
612
(!p_exact_match || get_modifiers_mask() == key->get_modifiers_mask());
613
} else if (physical_keycode != Key::NONE) {
614
if (location != KeyLocation::UNSPECIFIED && location != key->location) {
615
return false;
616
}
617
return (physical_keycode == key->physical_keycode) &&
618
(!p_exact_match || get_modifiers_mask() == key->get_modifiers_mask());
619
} else {
620
return false;
621
}
622
}
623
624
void InputEventKey::_bind_methods() {
625
ClassDB::bind_method(D_METHOD("set_pressed", "pressed"), &InputEventKey::set_pressed);
626
627
ClassDB::bind_method(D_METHOD("set_keycode", "keycode"), &InputEventKey::set_keycode);
628
ClassDB::bind_method(D_METHOD("get_keycode"), &InputEventKey::get_keycode);
629
630
ClassDB::bind_method(D_METHOD("set_physical_keycode", "physical_keycode"), &InputEventKey::set_physical_keycode);
631
ClassDB::bind_method(D_METHOD("get_physical_keycode"), &InputEventKey::get_physical_keycode);
632
633
ClassDB::bind_method(D_METHOD("set_key_label", "key_label"), &InputEventKey::set_key_label);
634
ClassDB::bind_method(D_METHOD("get_key_label"), &InputEventKey::get_key_label);
635
636
ClassDB::bind_method(D_METHOD("set_unicode", "unicode"), &InputEventKey::set_unicode);
637
ClassDB::bind_method(D_METHOD("get_unicode"), &InputEventKey::get_unicode);
638
639
ClassDB::bind_method(D_METHOD("set_location", "location"), &InputEventKey::set_location);
640
ClassDB::bind_method(D_METHOD("get_location"), &InputEventKey::get_location);
641
642
ClassDB::bind_method(D_METHOD("set_echo", "echo"), &InputEventKey::set_echo);
643
644
ClassDB::bind_method(D_METHOD("get_keycode_with_modifiers"), &InputEventKey::get_keycode_with_modifiers);
645
ClassDB::bind_method(D_METHOD("get_physical_keycode_with_modifiers"), &InputEventKey::get_physical_keycode_with_modifiers);
646
ClassDB::bind_method(D_METHOD("get_key_label_with_modifiers"), &InputEventKey::get_key_label_with_modifiers);
647
648
ClassDB::bind_method(D_METHOD("as_text_keycode"), &InputEventKey::as_text_keycode);
649
ClassDB::bind_method(D_METHOD("as_text_physical_keycode"), &InputEventKey::as_text_physical_keycode);
650
ClassDB::bind_method(D_METHOD("as_text_key_label"), &InputEventKey::as_text_key_label);
651
ClassDB::bind_method(D_METHOD("as_text_location"), &InputEventKey::as_text_location);
652
653
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "pressed"), "set_pressed", "is_pressed");
654
ADD_PROPERTY(PropertyInfo(Variant::INT, "keycode"), "set_keycode", "get_keycode");
655
ADD_PROPERTY(PropertyInfo(Variant::INT, "physical_keycode"), "set_physical_keycode", "get_physical_keycode");
656
ADD_PROPERTY(PropertyInfo(Variant::INT, "key_label"), "set_key_label", "get_key_label");
657
ADD_PROPERTY(PropertyInfo(Variant::INT, "unicode"), "set_unicode", "get_unicode");
658
ADD_PROPERTY(PropertyInfo(Variant::INT, "location", PROPERTY_HINT_ENUM, "Unspecified,Left,Right"), "set_location", "get_location");
659
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "echo"), "set_echo", "is_echo");
660
}
661
662
///////////////////////////////////
663
664
void InputEventMouse::set_button_mask(BitField<MouseButtonMask> p_mask) {
665
button_mask = p_mask;
666
emit_changed();
667
}
668
669
BitField<MouseButtonMask> InputEventMouse::get_button_mask() const {
670
return button_mask;
671
}
672
673
void InputEventMouse::set_position(const Vector2 &p_pos) {
674
pos = p_pos;
675
}
676
677
Vector2 InputEventMouse::get_position() const {
678
return pos;
679
}
680
681
void InputEventMouse::set_global_position(const Vector2 &p_global_pos) {
682
global_pos = p_global_pos;
683
}
684
685
Vector2 InputEventMouse::get_global_position() const {
686
return global_pos;
687
}
688
689
void InputEventMouse::_bind_methods() {
690
ClassDB::bind_method(D_METHOD("set_button_mask", "button_mask"), &InputEventMouse::set_button_mask);
691
ClassDB::bind_method(D_METHOD("get_button_mask"), &InputEventMouse::get_button_mask);
692
693
ClassDB::bind_method(D_METHOD("set_position", "position"), &InputEventMouse::set_position);
694
ClassDB::bind_method(D_METHOD("get_position"), &InputEventMouse::get_position);
695
696
ClassDB::bind_method(D_METHOD("set_global_position", "global_position"), &InputEventMouse::set_global_position);
697
ClassDB::bind_method(D_METHOD("get_global_position"), &InputEventMouse::get_global_position);
698
699
ADD_PROPERTY(PropertyInfo(Variant::INT, "button_mask"), "set_button_mask", "get_button_mask");
700
ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "position", PROPERTY_HINT_NONE, "suffix:px"), "set_position", "get_position");
701
ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "global_position", PROPERTY_HINT_NONE, "suffix:px"), "set_global_position", "get_global_position");
702
}
703
704
///////////////////////////////////
705
706
void InputEventMouseButton::set_factor(float p_factor) {
707
factor = p_factor;
708
}
709
710
float InputEventMouseButton::get_factor() const {
711
return factor;
712
}
713
714
void InputEventMouseButton::set_button_index(MouseButton p_index) {
715
button_index = p_index;
716
emit_changed();
717
}
718
719
MouseButton InputEventMouseButton::get_button_index() const {
720
return button_index;
721
}
722
723
void InputEventMouseButton::set_pressed(bool p_pressed) {
724
pressed = p_pressed;
725
}
726
727
void InputEventMouseButton::set_canceled(bool p_canceled) {
728
canceled = p_canceled;
729
}
730
731
void InputEventMouseButton::set_double_click(bool p_double_click) {
732
double_click = p_double_click;
733
}
734
735
bool InputEventMouseButton::is_double_click() const {
736
return double_click;
737
}
738
739
Ref<InputEvent> InputEventMouseButton::xformed_by(const Transform2D &p_xform, const Vector2 &p_local_ofs) const {
740
Vector2 g = get_global_position();
741
Vector2 l = p_xform.xform(get_position() + p_local_ofs);
742
743
Ref<InputEventMouseButton> mb;
744
mb.instantiate();
745
746
mb->set_device(get_device());
747
mb->set_window_id(get_window_id());
748
mb->set_modifiers_from_event(this);
749
750
mb->set_position(l);
751
mb->set_global_position(g);
752
753
mb->set_button_mask(get_button_mask());
754
mb->set_pressed(pressed);
755
mb->set_canceled(canceled);
756
mb->set_double_click(double_click);
757
mb->set_factor(factor);
758
mb->set_button_index(button_index);
759
760
mb->merge_meta_from(this);
761
762
return mb;
763
}
764
765
bool InputEventMouseButton::action_match(const Ref<InputEvent> &p_event, bool p_exact_match, float p_deadzone, bool *r_pressed, float *r_strength, float *r_raw_strength) const {
766
Ref<InputEventMouseButton> mb = p_event;
767
if (mb.is_null()) {
768
return false;
769
}
770
771
bool match = button_index == mb->button_index;
772
Key action_modifiers_mask = (Key)(int64_t)get_modifiers_mask();
773
Key button_modifiers_mask = (Key)(int64_t)mb->get_modifiers_mask();
774
if (mb->is_pressed()) {
775
match &= (action_modifiers_mask & button_modifiers_mask) == action_modifiers_mask;
776
}
777
if (p_exact_match) {
778
match &= action_modifiers_mask == button_modifiers_mask;
779
}
780
if (match) {
781
bool mb_pressed = mb->is_pressed();
782
if (r_pressed != nullptr) {
783
*r_pressed = mb_pressed;
784
}
785
float strength = mb_pressed ? 1.0f : 0.0f;
786
if (r_strength != nullptr) {
787
*r_strength = strength;
788
}
789
if (r_raw_strength != nullptr) {
790
*r_raw_strength = strength;
791
}
792
}
793
794
return match;
795
}
796
797
bool InputEventMouseButton::is_match(const Ref<InputEvent> &p_event, bool p_exact_match) const {
798
Ref<InputEventMouseButton> mb = p_event;
799
if (mb.is_null()) {
800
return false;
801
}
802
803
return button_index == mb->button_index &&
804
(!p_exact_match || get_modifiers_mask() == mb->get_modifiers_mask());
805
}
806
807
static const char *_mouse_button_descriptions[9] = {
808
TTRC("Left Mouse Button"),
809
TTRC("Right Mouse Button"),
810
TTRC("Middle Mouse Button"),
811
TTRC("Mouse Wheel Up"),
812
TTRC("Mouse Wheel Down"),
813
TTRC("Mouse Wheel Left"),
814
TTRC("Mouse Wheel Right"),
815
TTRC("Mouse Thumb Button 1"),
816
TTRC("Mouse Thumb Button 2")
817
};
818
819
String InputEventMouseButton::as_text() const {
820
// Modifiers
821
String mods_text = InputEventWithModifiers::as_text();
822
String full_string = mods_text.is_empty() ? "" : mods_text + "+";
823
824
// Button
825
MouseButton idx = get_button_index();
826
switch (idx) {
827
case MouseButton::LEFT:
828
case MouseButton::RIGHT:
829
case MouseButton::MIDDLE:
830
case MouseButton::WHEEL_UP:
831
case MouseButton::WHEEL_DOWN:
832
case MouseButton::WHEEL_LEFT:
833
case MouseButton::WHEEL_RIGHT:
834
case MouseButton::MB_XBUTTON1:
835
case MouseButton::MB_XBUTTON2:
836
full_string += RTR(_mouse_button_descriptions[(size_t)idx - 1]); // button index starts from 1, array index starts from 0, so subtract 1
837
break;
838
default:
839
full_string += RTR("Button") + " #" + itos((int64_t)idx);
840
break;
841
}
842
843
// Double Click
844
if (double_click) {
845
full_string += " (" + RTR("Double Click") + ")";
846
}
847
848
return full_string;
849
}
850
851
String InputEventMouseButton::to_string() {
852
String p = is_pressed() ? "true" : "false";
853
String canceled_state = is_canceled() ? "true" : "false";
854
String d = double_click ? "true" : "false";
855
856
MouseButton idx = get_button_index();
857
String button_string = itos((int64_t)idx);
858
859
switch (idx) {
860
case MouseButton::LEFT:
861
case MouseButton::RIGHT:
862
case MouseButton::MIDDLE:
863
case MouseButton::WHEEL_UP:
864
case MouseButton::WHEEL_DOWN:
865
case MouseButton::WHEEL_LEFT:
866
case MouseButton::WHEEL_RIGHT:
867
case MouseButton::MB_XBUTTON1:
868
case MouseButton::MB_XBUTTON2:
869
button_string += vformat(" (%s)", TTRGET(_mouse_button_descriptions[(size_t)idx - 1])); // button index starts from 1, array index starts from 0, so subtract 1
870
break;
871
default:
872
break;
873
}
874
875
String mods = InputEventWithModifiers::as_text();
876
mods = mods.is_empty() ? "none" : mods;
877
878
// Work around the fact vformat can only take 5 substitutions but 6 need to be passed.
879
String index_and_mods = vformat("button_index=%s, mods=%s", button_index, mods);
880
return vformat("InputEventMouseButton: %s, pressed=%s, canceled=%s, position=(%s), button_mask=%d, double_click=%s", index_and_mods, p, canceled_state, String(get_position()), get_button_mask(), d);
881
}
882
883
void InputEventMouseButton::_bind_methods() {
884
ClassDB::bind_method(D_METHOD("set_factor", "factor"), &InputEventMouseButton::set_factor);
885
ClassDB::bind_method(D_METHOD("get_factor"), &InputEventMouseButton::get_factor);
886
887
ClassDB::bind_method(D_METHOD("set_button_index", "button_index"), &InputEventMouseButton::set_button_index);
888
ClassDB::bind_method(D_METHOD("get_button_index"), &InputEventMouseButton::get_button_index);
889
890
ClassDB::bind_method(D_METHOD("set_pressed", "pressed"), &InputEventMouseButton::set_pressed);
891
ClassDB::bind_method(D_METHOD("set_canceled", "canceled"), &InputEventMouseButton::set_canceled);
892
893
ClassDB::bind_method(D_METHOD("set_double_click", "double_click"), &InputEventMouseButton::set_double_click);
894
ClassDB::bind_method(D_METHOD("is_double_click"), &InputEventMouseButton::is_double_click);
895
896
ADD_PROPERTY(PropertyInfo(Variant::FLOAT, "factor"), "set_factor", "get_factor");
897
ADD_PROPERTY(PropertyInfo(Variant::INT, "button_index"), "set_button_index", "get_button_index");
898
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "canceled"), "set_canceled", "is_canceled");
899
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "pressed"), "set_pressed", "is_pressed");
900
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "double_click"), "set_double_click", "is_double_click");
901
}
902
903
///////////////////////////////////
904
905
void InputEventMouseMotion::set_tilt(const Vector2 &p_tilt) {
906
tilt = p_tilt;
907
}
908
909
Vector2 InputEventMouseMotion::get_tilt() const {
910
return tilt;
911
}
912
913
void InputEventMouseMotion::set_pressure(float p_pressure) {
914
pressure = p_pressure;
915
}
916
917
float InputEventMouseMotion::get_pressure() const {
918
return pressure;
919
}
920
921
void InputEventMouseMotion::set_pen_inverted(bool p_inverted) {
922
pen_inverted = p_inverted;
923
}
924
925
bool InputEventMouseMotion::get_pen_inverted() const {
926
return pen_inverted;
927
}
928
929
void InputEventMouseMotion::set_relative(const Vector2 &p_relative) {
930
relative = p_relative;
931
}
932
933
Vector2 InputEventMouseMotion::get_relative() const {
934
return relative;
935
}
936
937
void InputEventMouseMotion::set_relative_screen_position(const Vector2 &p_relative) {
938
screen_relative = p_relative;
939
}
940
941
Vector2 InputEventMouseMotion::get_relative_screen_position() const {
942
return screen_relative;
943
}
944
945
void InputEventMouseMotion::set_velocity(const Vector2 &p_velocity) {
946
velocity = p_velocity;
947
}
948
949
Vector2 InputEventMouseMotion::get_velocity() const {
950
return velocity;
951
}
952
953
void InputEventMouseMotion::set_screen_velocity(const Vector2 &p_velocity) {
954
screen_velocity = p_velocity;
955
}
956
957
Vector2 InputEventMouseMotion::get_screen_velocity() const {
958
return screen_velocity;
959
}
960
961
Ref<InputEvent> InputEventMouseMotion::xformed_by(const Transform2D &p_xform, const Vector2 &p_local_ofs) const {
962
Ref<InputEventMouseMotion> mm;
963
mm.instantiate();
964
965
mm->set_device(get_device());
966
mm->set_window_id(get_window_id());
967
968
mm->set_modifiers_from_event(this);
969
970
mm->set_position(p_xform.xform(get_position() + p_local_ofs));
971
mm->set_pressure(get_pressure());
972
mm->set_pen_inverted(get_pen_inverted());
973
mm->set_tilt(get_tilt());
974
mm->set_global_position(get_global_position());
975
976
mm->set_button_mask(get_button_mask());
977
mm->set_relative(p_xform.basis_xform(get_relative()));
978
mm->set_relative_screen_position(get_relative_screen_position());
979
mm->set_velocity(p_xform.basis_xform(get_velocity()));
980
mm->set_screen_velocity(get_screen_velocity());
981
982
mm->merge_meta_from(this);
983
984
return mm;
985
}
986
987
String InputEventMouseMotion::as_text() const {
988
return vformat(RTR("Mouse motion at position (%s) with velocity (%s)"), String(get_position()), String(get_velocity()));
989
}
990
991
String InputEventMouseMotion::to_string() {
992
BitField<MouseButtonMask> mouse_button_mask = get_button_mask();
993
String button_mask_string = itos((int64_t)mouse_button_mask);
994
995
if (mouse_button_mask.has_flag(MouseButtonMask::LEFT)) {
996
button_mask_string += vformat(" (%s)", TTRGET(_mouse_button_descriptions[(size_t)MouseButton::LEFT - 1]));
997
}
998
if (mouse_button_mask.has_flag(MouseButtonMask::MIDDLE)) {
999
button_mask_string += vformat(" (%s)", TTRGET(_mouse_button_descriptions[(size_t)MouseButton::MIDDLE - 1]));
1000
}
1001
if (mouse_button_mask.has_flag(MouseButtonMask::RIGHT)) {
1002
button_mask_string += vformat(" (%s)", TTRGET(_mouse_button_descriptions[(size_t)MouseButton::RIGHT - 1]));
1003
}
1004
if (mouse_button_mask.has_flag(MouseButtonMask::MB_XBUTTON1)) {
1005
button_mask_string += vformat(" (%s)", TTRGET(_mouse_button_descriptions[(size_t)MouseButton::MB_XBUTTON1 - 1]));
1006
}
1007
if (mouse_button_mask.has_flag(MouseButtonMask::MB_XBUTTON2)) {
1008
button_mask_string += vformat(" (%s)", TTRGET(_mouse_button_descriptions[(size_t)MouseButton::MB_XBUTTON2 - 1]));
1009
}
1010
1011
// Work around the fact vformat can only take 5 substitutions but 7 need to be passed.
1012
String mask_and_position_and_relative = vformat("button_mask=%s, position=(%s), relative=(%s)", button_mask_string, String(get_position()), String(get_relative()));
1013
return vformat("InputEventMouseMotion: %s, velocity=(%s), pressure=%.2f, tilt=(%s), pen_inverted=(%s)", mask_and_position_and_relative, String(get_velocity()), get_pressure(), String(get_tilt()), get_pen_inverted());
1014
}
1015
1016
bool InputEventMouseMotion::accumulate(const Ref<InputEvent> &p_event) {
1017
Ref<InputEventMouseMotion> motion = p_event;
1018
if (motion.is_null()) {
1019
return false;
1020
}
1021
1022
if (get_window_id() != motion->get_window_id()) {
1023
return false;
1024
}
1025
1026
if (is_canceled() != motion->is_canceled()) {
1027
return false;
1028
}
1029
1030
if (is_pressed() != motion->is_pressed()) {
1031
return false;
1032
}
1033
1034
if (get_button_mask() != motion->get_button_mask()) {
1035
return false;
1036
}
1037
1038
if (is_shift_pressed() != motion->is_shift_pressed()) {
1039
return false;
1040
}
1041
1042
if (is_ctrl_pressed() != motion->is_ctrl_pressed()) {
1043
return false;
1044
}
1045
1046
if (is_alt_pressed() != motion->is_alt_pressed()) {
1047
return false;
1048
}
1049
1050
if (is_meta_pressed() != motion->is_meta_pressed()) {
1051
return false;
1052
}
1053
1054
set_position(motion->get_position());
1055
set_global_position(motion->get_global_position());
1056
set_velocity(motion->get_velocity());
1057
set_screen_velocity(motion->get_screen_velocity());
1058
relative += motion->get_relative();
1059
screen_relative += motion->get_relative_screen_position();
1060
1061
return true;
1062
}
1063
1064
void InputEventMouseMotion::_bind_methods() {
1065
ClassDB::bind_method(D_METHOD("set_tilt", "tilt"), &InputEventMouseMotion::set_tilt);
1066
ClassDB::bind_method(D_METHOD("get_tilt"), &InputEventMouseMotion::get_tilt);
1067
1068
ClassDB::bind_method(D_METHOD("set_pressure", "pressure"), &InputEventMouseMotion::set_pressure);
1069
ClassDB::bind_method(D_METHOD("get_pressure"), &InputEventMouseMotion::get_pressure);
1070
1071
ClassDB::bind_method(D_METHOD("set_pen_inverted", "pen_inverted"), &InputEventMouseMotion::set_pen_inverted);
1072
ClassDB::bind_method(D_METHOD("get_pen_inverted"), &InputEventMouseMotion::get_pen_inverted);
1073
1074
ClassDB::bind_method(D_METHOD("set_relative", "relative"), &InputEventMouseMotion::set_relative);
1075
ClassDB::bind_method(D_METHOD("get_relative"), &InputEventMouseMotion::get_relative);
1076
1077
ClassDB::bind_method(D_METHOD("set_screen_relative", "relative"), &InputEventMouseMotion::set_relative_screen_position);
1078
ClassDB::bind_method(D_METHOD("get_screen_relative"), &InputEventMouseMotion::get_relative_screen_position);
1079
1080
ClassDB::bind_method(D_METHOD("set_velocity", "velocity"), &InputEventMouseMotion::set_velocity);
1081
ClassDB::bind_method(D_METHOD("get_velocity"), &InputEventMouseMotion::get_velocity);
1082
1083
ClassDB::bind_method(D_METHOD("set_screen_velocity", "velocity"), &InputEventMouseMotion::set_screen_velocity);
1084
ClassDB::bind_method(D_METHOD("get_screen_velocity"), &InputEventMouseMotion::get_screen_velocity);
1085
1086
ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "tilt"), "set_tilt", "get_tilt");
1087
ADD_PROPERTY(PropertyInfo(Variant::FLOAT, "pressure"), "set_pressure", "get_pressure");
1088
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "pen_inverted"), "set_pen_inverted", "get_pen_inverted");
1089
ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "relative", PROPERTY_HINT_NONE, "suffix:px"), "set_relative", "get_relative");
1090
ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "screen_relative", PROPERTY_HINT_NONE, "suffix:px"), "set_screen_relative", "get_screen_relative");
1091
ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "velocity", PROPERTY_HINT_NONE, "suffix:px/s"), "set_velocity", "get_velocity");
1092
ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "screen_velocity", PROPERTY_HINT_NONE, "suffix:px/s"), "set_screen_velocity", "get_screen_velocity");
1093
}
1094
1095
///////////////////////////////////
1096
1097
void InputEventJoypadMotion::set_axis(JoyAxis p_axis) {
1098
ERR_FAIL_COND(p_axis < JoyAxis::INVALID || p_axis > JoyAxis::MAX);
1099
1100
axis = p_axis;
1101
emit_changed();
1102
}
1103
1104
JoyAxis InputEventJoypadMotion::get_axis() const {
1105
return axis;
1106
}
1107
1108
void InputEventJoypadMotion::set_axis_value(float p_value) {
1109
axis_value = p_value;
1110
pressed = Math::abs(axis_value) >= InputMap::DEFAULT_TOGGLE_DEADZONE;
1111
emit_changed();
1112
}
1113
1114
float InputEventJoypadMotion::get_axis_value() const {
1115
return axis_value;
1116
}
1117
1118
bool InputEventJoypadMotion::action_match(const Ref<InputEvent> &p_event, bool p_exact_match, float p_deadzone, bool *r_pressed, float *r_strength, float *r_raw_strength) const {
1119
Ref<InputEventJoypadMotion> jm = p_event;
1120
if (jm.is_null()) {
1121
return false;
1122
}
1123
1124
// Matches even if not in the same direction, but returns a "not pressed" event.
1125
bool match = axis == jm->axis;
1126
if (p_exact_match) {
1127
match &= (axis_value < 0) == (jm->axis_value < 0);
1128
}
1129
if (match) {
1130
float jm_abs_axis_value = Math::abs(jm->get_axis_value());
1131
bool same_direction = (((axis_value < 0) == (jm->axis_value < 0)) || jm->axis_value == 0);
1132
bool pressed_state = same_direction && jm_abs_axis_value >= p_deadzone;
1133
if (r_pressed != nullptr) {
1134
*r_pressed = pressed_state;
1135
}
1136
if (r_strength != nullptr) {
1137
if (pressed_state) {
1138
if (p_deadzone == 1.0f) {
1139
*r_strength = 1.0f;
1140
} else {
1141
*r_strength = CLAMP(Math::inverse_lerp(p_deadzone, 1.0f, jm_abs_axis_value), 0.0f, 1.0f);
1142
}
1143
} else {
1144
*r_strength = 0.0f;
1145
}
1146
}
1147
if (r_raw_strength != nullptr) {
1148
if (same_direction) { // NOT pressed, because we want to ignore the deadzone.
1149
*r_raw_strength = jm_abs_axis_value;
1150
} else {
1151
*r_raw_strength = 0.0f;
1152
}
1153
}
1154
}
1155
return match;
1156
}
1157
1158
bool InputEventJoypadMotion::is_match(const Ref<InputEvent> &p_event, bool p_exact_match) const {
1159
Ref<InputEventJoypadMotion> jm = p_event;
1160
if (jm.is_null()) {
1161
return false;
1162
}
1163
1164
return axis == jm->axis &&
1165
(!p_exact_match || ((axis_value < 0) == (jm->axis_value < 0)));
1166
}
1167
1168
static const char *_joy_axis_descriptions[(size_t)JoyAxis::MAX] = {
1169
TTRC("Left Stick X-Axis, Joystick 0 X-Axis"),
1170
TTRC("Left Stick Y-Axis, Joystick 0 Y-Axis"),
1171
TTRC("Right Stick X-Axis, Joystick 1 X-Axis"),
1172
TTRC("Right Stick Y-Axis, Joystick 1 Y-Axis"),
1173
TTRC("Joystick 2 X-Axis, Left Trigger, Sony L2, Xbox LT"),
1174
TTRC("Joystick 2 Y-Axis, Right Trigger, Sony R2, Xbox RT"),
1175
TTRC("Joystick 3 X-Axis"),
1176
TTRC("Joystick 3 Y-Axis"),
1177
TTRC("Joystick 4 X-Axis"),
1178
TTRC("Joystick 4 Y-Axis"),
1179
};
1180
1181
String InputEventJoypadMotion::as_text() const {
1182
String desc = axis < JoyAxis::MAX ? TTRGET(_joy_axis_descriptions[(size_t)axis]) : RTR("Unknown Joypad Axis");
1183
1184
return vformat(RTR("Joypad Motion on Axis %d (%s) with Value %.2f"), axis, desc, axis_value);
1185
}
1186
1187
String InputEventJoypadMotion::to_string() {
1188
return vformat("InputEventJoypadMotion: axis=%d, axis_value=%.2f", axis, axis_value);
1189
}
1190
1191
Ref<InputEventJoypadMotion> InputEventJoypadMotion::create_reference(JoyAxis p_axis, float p_value) {
1192
Ref<InputEventJoypadMotion> ie;
1193
ie.instantiate();
1194
ie->set_axis(p_axis);
1195
ie->set_axis_value(p_value);
1196
1197
return ie;
1198
}
1199
1200
void InputEventJoypadMotion::_bind_methods() {
1201
ClassDB::bind_method(D_METHOD("set_axis", "axis"), &InputEventJoypadMotion::set_axis);
1202
ClassDB::bind_method(D_METHOD("get_axis"), &InputEventJoypadMotion::get_axis);
1203
1204
ClassDB::bind_method(D_METHOD("set_axis_value", "axis_value"), &InputEventJoypadMotion::set_axis_value);
1205
ClassDB::bind_method(D_METHOD("get_axis_value"), &InputEventJoypadMotion::get_axis_value);
1206
1207
ADD_PROPERTY(PropertyInfo(Variant::INT, "axis"), "set_axis", "get_axis");
1208
ADD_PROPERTY(PropertyInfo(Variant::FLOAT, "axis_value"), "set_axis_value", "get_axis_value");
1209
}
1210
1211
///////////////////////////////////
1212
1213
void InputEventJoypadButton::set_button_index(JoyButton p_index) {
1214
button_index = p_index;
1215
emit_changed();
1216
}
1217
1218
JoyButton InputEventJoypadButton::get_button_index() const {
1219
return button_index;
1220
}
1221
1222
void InputEventJoypadButton::set_pressed(bool p_pressed) {
1223
pressed = p_pressed;
1224
}
1225
1226
void InputEventJoypadButton::set_pressure(float p_pressure) {
1227
pressure = p_pressure;
1228
}
1229
1230
float InputEventJoypadButton::get_pressure() const {
1231
return pressure;
1232
}
1233
1234
bool InputEventJoypadButton::action_match(const Ref<InputEvent> &p_event, bool p_exact_match, float p_deadzone, bool *r_pressed, float *r_strength, float *r_raw_strength) const {
1235
Ref<InputEventJoypadButton> jb = p_event;
1236
if (jb.is_null()) {
1237
return false;
1238
}
1239
1240
bool match = button_index == jb->button_index;
1241
if (match) {
1242
bool jb_pressed = jb->is_pressed();
1243
if (r_pressed != nullptr) {
1244
*r_pressed = jb_pressed;
1245
}
1246
float strength = jb_pressed ? 1.0f : 0.0f;
1247
if (r_strength != nullptr) {
1248
*r_strength = strength;
1249
}
1250
if (r_raw_strength != nullptr) {
1251
*r_raw_strength = strength;
1252
}
1253
}
1254
1255
return match;
1256
}
1257
1258
bool InputEventJoypadButton::is_match(const Ref<InputEvent> &p_event, bool p_exact_match) const {
1259
Ref<InputEventJoypadButton> button = p_event;
1260
if (button.is_null()) {
1261
return false;
1262
}
1263
1264
return button_index == button->button_index;
1265
}
1266
1267
static const char *_joy_button_descriptions[(size_t)JoyButton::SDL_MAX] = {
1268
TTRC("Bottom Action, Sony Cross, Xbox A, Nintendo B"),
1269
TTRC("Right Action, Sony Circle, Xbox B, Nintendo A"),
1270
TTRC("Left Action, Sony Square, Xbox X, Nintendo Y"),
1271
TTRC("Top Action, Sony Triangle, Xbox Y, Nintendo X"),
1272
TTRC("Back, Sony Select, Xbox Back, Nintendo -"),
1273
TTRC("Guide, Sony PS, Xbox Home"),
1274
TTRC("Start, Xbox Menu, Nintendo +"),
1275
TTRC("Left Stick, Sony L3, Xbox L/LS"),
1276
TTRC("Right Stick, Sony R3, Xbox R/RS"),
1277
TTRC("Left Shoulder, Sony L1, Xbox LB"),
1278
TTRC("Right Shoulder, Sony R1, Xbox RB"),
1279
TTRC("D-pad Up"),
1280
TTRC("D-pad Down"),
1281
TTRC("D-pad Left"),
1282
TTRC("D-pad Right"),
1283
TTRC("Xbox Share, PS5 Microphone, Nintendo Capture"),
1284
TTRC("Xbox Paddle 1"),
1285
TTRC("Xbox Paddle 2"),
1286
TTRC("Xbox Paddle 3"),
1287
TTRC("Xbox Paddle 4"),
1288
TTRC("PS4/5 Touchpad"),
1289
};
1290
1291
String InputEventJoypadButton::as_text() const {
1292
String text = vformat(RTR("Joypad Button %d"), (int64_t)button_index);
1293
1294
if (button_index > JoyButton::INVALID && button_index < JoyButton::SDL_MAX) {
1295
text += vformat(" (%s)", TTRGET(_joy_button_descriptions[(size_t)button_index]));
1296
}
1297
1298
if (pressure != 0) {
1299
text += ", " + RTR("Pressure:") + " " + String(Variant(pressure));
1300
}
1301
1302
return text;
1303
}
1304
1305
String InputEventJoypadButton::to_string() {
1306
String p = is_pressed() ? "true" : "false";
1307
return vformat("InputEventJoypadButton: button_index=%d, pressed=%s, pressure=%.2f", button_index, p, pressure);
1308
}
1309
1310
Ref<InputEventJoypadButton> InputEventJoypadButton::create_reference(JoyButton p_btn_index) {
1311
Ref<InputEventJoypadButton> ie;
1312
ie.instantiate();
1313
ie->set_button_index(p_btn_index);
1314
1315
return ie;
1316
}
1317
1318
void InputEventJoypadButton::_bind_methods() {
1319
ClassDB::bind_method(D_METHOD("set_button_index", "button_index"), &InputEventJoypadButton::set_button_index);
1320
ClassDB::bind_method(D_METHOD("get_button_index"), &InputEventJoypadButton::get_button_index);
1321
1322
ClassDB::bind_method(D_METHOD("set_pressure", "pressure"), &InputEventJoypadButton::set_pressure);
1323
ClassDB::bind_method(D_METHOD("get_pressure"), &InputEventJoypadButton::get_pressure);
1324
1325
ClassDB::bind_method(D_METHOD("set_pressed", "pressed"), &InputEventJoypadButton::set_pressed);
1326
1327
ADD_PROPERTY(PropertyInfo(Variant::INT, "button_index"), "set_button_index", "get_button_index");
1328
ADD_PROPERTY(PropertyInfo(Variant::FLOAT, "pressure"), "set_pressure", "get_pressure");
1329
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "pressed"), "set_pressed", "is_pressed");
1330
}
1331
1332
///////////////////////////////////
1333
1334
void InputEventScreenTouch::set_index(int p_index) {
1335
index = p_index;
1336
}
1337
1338
int InputEventScreenTouch::get_index() const {
1339
return index;
1340
}
1341
1342
void InputEventScreenTouch::set_position(const Vector2 &p_pos) {
1343
pos = p_pos;
1344
}
1345
1346
Vector2 InputEventScreenTouch::get_position() const {
1347
return pos;
1348
}
1349
1350
void InputEventScreenTouch::set_pressed(bool p_pressed) {
1351
pressed = p_pressed;
1352
}
1353
1354
void InputEventScreenTouch::set_canceled(bool p_canceled) {
1355
canceled = p_canceled;
1356
}
1357
1358
void InputEventScreenTouch::set_double_tap(bool p_double_tap) {
1359
double_tap = p_double_tap;
1360
}
1361
bool InputEventScreenTouch::is_double_tap() const {
1362
return double_tap;
1363
}
1364
1365
Ref<InputEvent> InputEventScreenTouch::xformed_by(const Transform2D &p_xform, const Vector2 &p_local_ofs) const {
1366
Ref<InputEventScreenTouch> st;
1367
st.instantiate();
1368
st->set_device(get_device());
1369
st->set_window_id(get_window_id());
1370
st->set_index(index);
1371
st->set_position(p_xform.xform(pos + p_local_ofs));
1372
st->set_pressed(pressed);
1373
st->set_canceled(canceled);
1374
st->set_double_tap(double_tap);
1375
1376
st->merge_meta_from(this);
1377
1378
return st;
1379
}
1380
1381
String InputEventScreenTouch::as_text() const {
1382
String status = canceled ? RTR("canceled") : (pressed ? RTR("touched") : RTR("released"));
1383
1384
return vformat(RTR("Screen %s at (%s) with %s touch points"), status, String(get_position()), itos(index));
1385
}
1386
1387
String InputEventScreenTouch::to_string() {
1388
String p = pressed ? "true" : "false";
1389
String canceled_state = canceled ? "true" : "false";
1390
String double_tap_string = double_tap ? "true" : "false";
1391
return vformat("InputEventScreenTouch: index=%d, pressed=%s, canceled=%s, position=(%s), double_tap=%s", index, p, canceled_state, String(get_position()), double_tap_string);
1392
}
1393
1394
void InputEventScreenTouch::_bind_methods() {
1395
ClassDB::bind_method(D_METHOD("set_index", "index"), &InputEventScreenTouch::set_index);
1396
ClassDB::bind_method(D_METHOD("get_index"), &InputEventScreenTouch::get_index);
1397
1398
ClassDB::bind_method(D_METHOD("set_position", "position"), &InputEventScreenTouch::set_position);
1399
ClassDB::bind_method(D_METHOD("get_position"), &InputEventScreenTouch::get_position);
1400
1401
ClassDB::bind_method(D_METHOD("set_pressed", "pressed"), &InputEventScreenTouch::set_pressed);
1402
ClassDB::bind_method(D_METHOD("set_canceled", "canceled"), &InputEventScreenTouch::set_canceled);
1403
1404
ClassDB::bind_method(D_METHOD("set_double_tap", "double_tap"), &InputEventScreenTouch::set_double_tap);
1405
ClassDB::bind_method(D_METHOD("is_double_tap"), &InputEventScreenTouch::is_double_tap);
1406
1407
ADD_PROPERTY(PropertyInfo(Variant::INT, "index"), "set_index", "get_index");
1408
ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "position", PROPERTY_HINT_NONE, "suffix:px"), "set_position", "get_position");
1409
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "canceled"), "set_canceled", "is_canceled");
1410
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "pressed"), "set_pressed", "is_pressed");
1411
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "double_tap"), "set_double_tap", "is_double_tap");
1412
}
1413
1414
///////////////////////////////////
1415
1416
void InputEventScreenDrag::set_index(int p_index) {
1417
index = p_index;
1418
}
1419
1420
int InputEventScreenDrag::get_index() const {
1421
return index;
1422
}
1423
1424
void InputEventScreenDrag::set_tilt(const Vector2 &p_tilt) {
1425
tilt = p_tilt;
1426
}
1427
1428
Vector2 InputEventScreenDrag::get_tilt() const {
1429
return tilt;
1430
}
1431
1432
void InputEventScreenDrag::set_pressure(float p_pressure) {
1433
pressure = p_pressure;
1434
}
1435
1436
float InputEventScreenDrag::get_pressure() const {
1437
return pressure;
1438
}
1439
1440
void InputEventScreenDrag::set_pen_inverted(bool p_inverted) {
1441
pen_inverted = p_inverted;
1442
}
1443
1444
bool InputEventScreenDrag::get_pen_inverted() const {
1445
return pen_inverted;
1446
}
1447
1448
void InputEventScreenDrag::set_position(const Vector2 &p_pos) {
1449
pos = p_pos;
1450
}
1451
1452
Vector2 InputEventScreenDrag::get_position() const {
1453
return pos;
1454
}
1455
1456
void InputEventScreenDrag::set_relative(const Vector2 &p_relative) {
1457
relative = p_relative;
1458
}
1459
1460
Vector2 InputEventScreenDrag::get_relative() const {
1461
return relative;
1462
}
1463
1464
void InputEventScreenDrag::set_relative_screen_position(const Vector2 &p_relative) {
1465
screen_relative = p_relative;
1466
}
1467
1468
Vector2 InputEventScreenDrag::get_relative_screen_position() const {
1469
return screen_relative;
1470
}
1471
1472
void InputEventScreenDrag::set_velocity(const Vector2 &p_velocity) {
1473
velocity = p_velocity;
1474
}
1475
1476
Vector2 InputEventScreenDrag::get_velocity() const {
1477
return velocity;
1478
}
1479
1480
void InputEventScreenDrag::set_screen_velocity(const Vector2 &p_velocity) {
1481
screen_velocity = p_velocity;
1482
}
1483
1484
Vector2 InputEventScreenDrag::get_screen_velocity() const {
1485
return screen_velocity;
1486
}
1487
1488
Ref<InputEvent> InputEventScreenDrag::xformed_by(const Transform2D &p_xform, const Vector2 &p_local_ofs) const {
1489
Ref<InputEventScreenDrag> sd;
1490
1491
sd.instantiate();
1492
1493
sd->set_device(get_device());
1494
sd->set_window_id(get_window_id());
1495
1496
sd->set_index(index);
1497
sd->set_pressure(get_pressure());
1498
sd->set_pen_inverted(get_pen_inverted());
1499
sd->set_tilt(get_tilt());
1500
sd->set_position(p_xform.xform(pos + p_local_ofs));
1501
sd->set_relative(p_xform.basis_xform(relative));
1502
sd->set_relative_screen_position(get_relative_screen_position());
1503
sd->set_velocity(p_xform.basis_xform(velocity));
1504
sd->set_screen_velocity(get_screen_velocity());
1505
1506
sd->merge_meta_from(this);
1507
1508
return sd;
1509
}
1510
1511
String InputEventScreenDrag::as_text() const {
1512
return vformat(RTR("Screen dragged with %s touch points at position (%s) with velocity of (%s)"), itos(index), String(get_position()), String(get_velocity()));
1513
}
1514
1515
String InputEventScreenDrag::to_string() {
1516
return vformat("InputEventScreenDrag: index=%d, position=(%s), relative=(%s), velocity=(%s), pressure=%.2f, tilt=(%s), pen_inverted=(%s)", index, String(get_position()), String(get_relative()), String(get_velocity()), get_pressure(), String(get_tilt()), get_pen_inverted());
1517
}
1518
1519
bool InputEventScreenDrag::accumulate(const Ref<InputEvent> &p_event) {
1520
Ref<InputEventScreenDrag> drag = p_event;
1521
if (drag.is_null()) {
1522
return false;
1523
}
1524
1525
if (get_index() != drag->get_index()) {
1526
return false;
1527
}
1528
1529
set_position(drag->get_position());
1530
set_velocity(drag->get_velocity());
1531
set_screen_velocity(drag->get_screen_velocity());
1532
relative += drag->get_relative();
1533
screen_relative += drag->get_relative_screen_position();
1534
1535
return true;
1536
}
1537
1538
void InputEventScreenDrag::_bind_methods() {
1539
ClassDB::bind_method(D_METHOD("set_index", "index"), &InputEventScreenDrag::set_index);
1540
ClassDB::bind_method(D_METHOD("get_index"), &InputEventScreenDrag::get_index);
1541
1542
ClassDB::bind_method(D_METHOD("set_tilt", "tilt"), &InputEventScreenDrag::set_tilt);
1543
ClassDB::bind_method(D_METHOD("get_tilt"), &InputEventScreenDrag::get_tilt);
1544
1545
ClassDB::bind_method(D_METHOD("set_pressure", "pressure"), &InputEventScreenDrag::set_pressure);
1546
ClassDB::bind_method(D_METHOD("get_pressure"), &InputEventScreenDrag::get_pressure);
1547
1548
ClassDB::bind_method(D_METHOD("set_pen_inverted", "pen_inverted"), &InputEventScreenDrag::set_pen_inverted);
1549
ClassDB::bind_method(D_METHOD("get_pen_inverted"), &InputEventScreenDrag::get_pen_inverted);
1550
1551
ClassDB::bind_method(D_METHOD("set_position", "position"), &InputEventScreenDrag::set_position);
1552
ClassDB::bind_method(D_METHOD("get_position"), &InputEventScreenDrag::get_position);
1553
1554
ClassDB::bind_method(D_METHOD("set_relative", "relative"), &InputEventScreenDrag::set_relative);
1555
ClassDB::bind_method(D_METHOD("get_relative"), &InputEventScreenDrag::get_relative);
1556
1557
ClassDB::bind_method(D_METHOD("set_screen_relative", "relative"), &InputEventScreenDrag::set_relative_screen_position);
1558
ClassDB::bind_method(D_METHOD("get_screen_relative"), &InputEventScreenDrag::get_relative_screen_position);
1559
1560
ClassDB::bind_method(D_METHOD("set_velocity", "velocity"), &InputEventScreenDrag::set_velocity);
1561
ClassDB::bind_method(D_METHOD("get_velocity"), &InputEventScreenDrag::get_velocity);
1562
1563
ClassDB::bind_method(D_METHOD("set_screen_velocity", "velocity"), &InputEventScreenDrag::set_screen_velocity);
1564
ClassDB::bind_method(D_METHOD("get_screen_velocity"), &InputEventScreenDrag::get_screen_velocity);
1565
1566
ADD_PROPERTY(PropertyInfo(Variant::INT, "index"), "set_index", "get_index");
1567
ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "tilt"), "set_tilt", "get_tilt");
1568
ADD_PROPERTY(PropertyInfo(Variant::FLOAT, "pressure"), "set_pressure", "get_pressure");
1569
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "pen_inverted"), "set_pen_inverted", "get_pen_inverted");
1570
ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "position", PROPERTY_HINT_NONE, "suffix:px"), "set_position", "get_position");
1571
ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "relative", PROPERTY_HINT_NONE, "suffix:px"), "set_relative", "get_relative");
1572
ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "screen_relative", PROPERTY_HINT_NONE, "suffix:px"), "set_screen_relative", "get_screen_relative");
1573
ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "velocity", PROPERTY_HINT_NONE, "suffix:px/s"), "set_velocity", "get_velocity");
1574
ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "screen_velocity", PROPERTY_HINT_NONE, "suffix:px/s"), "set_screen_velocity", "get_screen_velocity");
1575
}
1576
1577
///////////////////////////////////
1578
1579
void InputEventAction::set_action(const StringName &p_action) {
1580
action = p_action;
1581
}
1582
1583
StringName InputEventAction::get_action() const {
1584
return action;
1585
}
1586
1587
void InputEventAction::set_pressed(bool p_pressed) {
1588
pressed = p_pressed;
1589
}
1590
1591
void InputEventAction::set_strength(float p_strength) {
1592
strength = CLAMP(p_strength, 0.0f, 1.0f);
1593
}
1594
1595
float InputEventAction::get_strength() const {
1596
return strength;
1597
}
1598
1599
void InputEventAction::set_event_index(int p_index) {
1600
event_index = p_index;
1601
}
1602
1603
int InputEventAction::get_event_index() const {
1604
return event_index;
1605
}
1606
1607
bool InputEventAction::is_match(const Ref<InputEvent> &p_event, bool p_exact_match) const {
1608
if (p_event.is_null()) {
1609
return false;
1610
}
1611
1612
return p_event->is_action(action, p_exact_match);
1613
}
1614
1615
bool InputEventAction::is_action(const StringName &p_action) const {
1616
return action == p_action;
1617
}
1618
1619
bool InputEventAction::action_match(const Ref<InputEvent> &p_event, bool p_exact_match, float p_deadzone, bool *r_pressed, float *r_strength, float *r_raw_strength) const {
1620
Ref<InputEventAction> act = p_event;
1621
if (act.is_null()) {
1622
return false;
1623
}
1624
1625
bool match = action == act->action;
1626
if (match) {
1627
bool act_pressed = act->is_pressed();
1628
if (r_pressed != nullptr) {
1629
*r_pressed = act_pressed;
1630
}
1631
float act_strength = act_pressed ? 1.0f : 0.0f;
1632
if (r_strength != nullptr) {
1633
*r_strength = act_strength;
1634
}
1635
if (r_raw_strength != nullptr) {
1636
*r_raw_strength = act_strength;
1637
}
1638
}
1639
return match;
1640
}
1641
1642
String InputEventAction::as_text() const {
1643
const List<Ref<InputEvent>> *events = InputMap::get_singleton()->action_get_events(action);
1644
if (!events) {
1645
return String();
1646
}
1647
1648
for (const Ref<InputEvent> &E : *events) {
1649
if (E.is_valid()) {
1650
return E->as_text();
1651
}
1652
}
1653
1654
return String();
1655
}
1656
1657
String InputEventAction::to_string() {
1658
String p = is_pressed() ? "true" : "false";
1659
return vformat("InputEventAction: action=\"%s\", pressed=%s", action, p);
1660
}
1661
1662
void InputEventAction::_bind_methods() {
1663
ClassDB::bind_method(D_METHOD("set_action", "action"), &InputEventAction::set_action);
1664
ClassDB::bind_method(D_METHOD("get_action"), &InputEventAction::get_action);
1665
1666
ClassDB::bind_method(D_METHOD("set_pressed", "pressed"), &InputEventAction::set_pressed);
1667
1668
ClassDB::bind_method(D_METHOD("set_strength", "strength"), &InputEventAction::set_strength);
1669
ClassDB::bind_method(D_METHOD("get_strength"), &InputEventAction::get_strength);
1670
1671
ClassDB::bind_method(D_METHOD("set_event_index", "index"), &InputEventAction::set_event_index);
1672
ClassDB::bind_method(D_METHOD("get_event_index"), &InputEventAction::get_event_index);
1673
1674
ADD_PROPERTY(PropertyInfo(Variant::STRING_NAME, "action", PROPERTY_HINT_INPUT_NAME, "show_builtin,loose_mode"), "set_action", "get_action");
1675
ADD_PROPERTY(PropertyInfo(Variant::BOOL, "pressed"), "set_pressed", "is_pressed");
1676
ADD_PROPERTY(PropertyInfo(Variant::FLOAT, "strength", PROPERTY_HINT_RANGE, "0,1,0.01"), "set_strength", "get_strength");
1677
ADD_PROPERTY(PropertyInfo(Variant::INT, "event_index", PROPERTY_HINT_RANGE, "-1,31,1"), "set_event_index", "get_event_index"); // The max value equals to Input::MAX_EVENT - 1.
1678
}
1679
1680
///////////////////////////////////
1681
1682
void InputEventGesture::set_position(const Vector2 &p_pos) {
1683
pos = p_pos;
1684
}
1685
1686
void InputEventGesture::_bind_methods() {
1687
ClassDB::bind_method(D_METHOD("set_position", "position"), &InputEventGesture::set_position);
1688
ClassDB::bind_method(D_METHOD("get_position"), &InputEventGesture::get_position);
1689
1690
ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "position", PROPERTY_HINT_NONE, "suffix:px"), "set_position", "get_position");
1691
}
1692
1693
Vector2 InputEventGesture::get_position() const {
1694
return pos;
1695
}
1696
1697
///////////////////////////////////
1698
1699
void InputEventMagnifyGesture::set_factor(real_t p_factor) {
1700
factor = p_factor;
1701
}
1702
1703
real_t InputEventMagnifyGesture::get_factor() const {
1704
return factor;
1705
}
1706
1707
Ref<InputEvent> InputEventMagnifyGesture::xformed_by(const Transform2D &p_xform, const Vector2 &p_local_ofs) const {
1708
Ref<InputEventMagnifyGesture> ev;
1709
ev.instantiate();
1710
1711
ev->set_device(get_device());
1712
ev->set_window_id(get_window_id());
1713
1714
ev->set_modifiers_from_event(this);
1715
1716
ev->set_position(p_xform.xform(get_position() + p_local_ofs));
1717
ev->set_factor(get_factor());
1718
1719
ev->merge_meta_from(this);
1720
1721
return ev;
1722
}
1723
1724
String InputEventMagnifyGesture::as_text() const {
1725
return vformat(RTR("Magnify Gesture at (%s) with factor %s"), String(get_position()), rtos(get_factor()));
1726
}
1727
1728
String InputEventMagnifyGesture::to_string() {
1729
return vformat("InputEventMagnifyGesture: factor=%.2f, position=(%s)", factor, String(get_position()));
1730
}
1731
1732
void InputEventMagnifyGesture::_bind_methods() {
1733
ClassDB::bind_method(D_METHOD("set_factor", "factor"), &InputEventMagnifyGesture::set_factor);
1734
ClassDB::bind_method(D_METHOD("get_factor"), &InputEventMagnifyGesture::get_factor);
1735
1736
ADD_PROPERTY(PropertyInfo(Variant::FLOAT, "factor"), "set_factor", "get_factor");
1737
}
1738
1739
///////////////////////////////////
1740
1741
void InputEventPanGesture::set_delta(const Vector2 &p_delta) {
1742
delta = p_delta;
1743
}
1744
1745
Vector2 InputEventPanGesture::get_delta() const {
1746
return delta;
1747
}
1748
1749
Ref<InputEvent> InputEventPanGesture::xformed_by(const Transform2D &p_xform, const Vector2 &p_local_ofs) const {
1750
Ref<InputEventPanGesture> ev;
1751
ev.instantiate();
1752
1753
ev->set_device(get_device());
1754
ev->set_window_id(get_window_id());
1755
1756
ev->set_modifiers_from_event(this);
1757
1758
ev->set_position(p_xform.xform(get_position() + p_local_ofs));
1759
ev->set_delta(get_delta());
1760
1761
ev->merge_meta_from(this);
1762
1763
return ev;
1764
}
1765
1766
String InputEventPanGesture::as_text() const {
1767
return vformat(RTR("Pan Gesture at (%s) with delta (%s)"), String(get_position()), String(get_delta()));
1768
}
1769
1770
String InputEventPanGesture::to_string() {
1771
return vformat("InputEventPanGesture: delta=(%s), position=(%s)", String(get_delta()), String(get_position()));
1772
}
1773
1774
void InputEventPanGesture::_bind_methods() {
1775
ClassDB::bind_method(D_METHOD("set_delta", "delta"), &InputEventPanGesture::set_delta);
1776
ClassDB::bind_method(D_METHOD("get_delta"), &InputEventPanGesture::get_delta);
1777
1778
ADD_PROPERTY(PropertyInfo(Variant::VECTOR2, "delta"), "set_delta", "get_delta");
1779
}
1780
1781
///////////////////////////////////
1782
1783
void InputEventMIDI::set_channel(const int p_channel) {
1784
channel = p_channel;
1785
}
1786
1787
int InputEventMIDI::get_channel() const {
1788
return channel;
1789
}
1790
1791
void InputEventMIDI::set_message(const MIDIMessage p_message) {
1792
message = p_message;
1793
}
1794
1795
MIDIMessage InputEventMIDI::get_message() const {
1796
return message;
1797
}
1798
1799
void InputEventMIDI::set_pitch(const int p_pitch) {
1800
pitch = p_pitch;
1801
}
1802
1803
int InputEventMIDI::get_pitch() const {
1804
return pitch;
1805
}
1806
1807
void InputEventMIDI::set_velocity(const int p_velocity) {
1808
velocity = p_velocity;
1809
}
1810
1811
int InputEventMIDI::get_velocity() const {
1812
return velocity;
1813
}
1814
1815
void InputEventMIDI::set_instrument(const int p_instrument) {
1816
instrument = p_instrument;
1817
}
1818
1819
int InputEventMIDI::get_instrument() const {
1820
return instrument;
1821
}
1822
1823
void InputEventMIDI::set_pressure(const int p_pressure) {
1824
pressure = p_pressure;
1825
}
1826
1827
int InputEventMIDI::get_pressure() const {
1828
return pressure;
1829
}
1830
1831
void InputEventMIDI::set_controller_number(const int p_controller_number) {
1832
controller_number = p_controller_number;
1833
}
1834
1835
int InputEventMIDI::get_controller_number() const {
1836
return controller_number;
1837
}
1838
1839
void InputEventMIDI::set_controller_value(const int p_controller_value) {
1840
controller_value = p_controller_value;
1841
}
1842
1843
int InputEventMIDI::get_controller_value() const {
1844
return controller_value;
1845
}
1846
1847
String InputEventMIDI::as_text() const {
1848
return vformat(RTR("MIDI Input on Channel=%s Message=%s"), itos(channel), itos((int64_t)message));
1849
}
1850
1851
String InputEventMIDI::to_string() {
1852
String ret;
1853
switch (message) {
1854
case MIDIMessage::NOTE_ON:
1855
ret = vformat("Note On: channel=%d, pitch=%d, velocity=%d", channel, pitch, velocity);
1856
break;
1857
case MIDIMessage::NOTE_OFF:
1858
ret = vformat("Note Off: channel=%d, pitch=%d, velocity=%d", channel, pitch, velocity);
1859
break;
1860
case MIDIMessage::PITCH_BEND:
1861
ret = vformat("Pitch Bend: channel=%d, pitch=%d", channel, pitch);
1862
break;
1863
case MIDIMessage::CHANNEL_PRESSURE:
1864
ret = vformat("Channel Pressure: channel=%d, pressure=%d", channel, pressure);
1865
break;
1866
case MIDIMessage::CONTROL_CHANGE:
1867
ret = vformat("Control Change: channel=%d, controller_number=%d, controller_value=%d", channel, controller_number, controller_value);
1868
break;
1869
default:
1870
ret = vformat("channel=%d, message=%d, pitch=%d, velocity=%d, pressure=%d, controller_number=%d, controller_value=%d, instrument=%d", channel, message, pitch, velocity, pressure, controller_number, controller_value, instrument);
1871
}
1872
return "InputEventMIDI: " + ret;
1873
}
1874
1875
void InputEventMIDI::_bind_methods() {
1876
ClassDB::bind_method(D_METHOD("set_channel", "channel"), &InputEventMIDI::set_channel);
1877
ClassDB::bind_method(D_METHOD("get_channel"), &InputEventMIDI::get_channel);
1878
ClassDB::bind_method(D_METHOD("set_message", "message"), &InputEventMIDI::set_message);
1879
ClassDB::bind_method(D_METHOD("get_message"), &InputEventMIDI::get_message);
1880
ClassDB::bind_method(D_METHOD("set_pitch", "pitch"), &InputEventMIDI::set_pitch);
1881
ClassDB::bind_method(D_METHOD("get_pitch"), &InputEventMIDI::get_pitch);
1882
ClassDB::bind_method(D_METHOD("set_velocity", "velocity"), &InputEventMIDI::set_velocity);
1883
ClassDB::bind_method(D_METHOD("get_velocity"), &InputEventMIDI::get_velocity);
1884
ClassDB::bind_method(D_METHOD("set_instrument", "instrument"), &InputEventMIDI::set_instrument);
1885
ClassDB::bind_method(D_METHOD("get_instrument"), &InputEventMIDI::get_instrument);
1886
ClassDB::bind_method(D_METHOD("set_pressure", "pressure"), &InputEventMIDI::set_pressure);
1887
ClassDB::bind_method(D_METHOD("get_pressure"), &InputEventMIDI::get_pressure);
1888
ClassDB::bind_method(D_METHOD("set_controller_number", "controller_number"), &InputEventMIDI::set_controller_number);
1889
ClassDB::bind_method(D_METHOD("get_controller_number"), &InputEventMIDI::get_controller_number);
1890
ClassDB::bind_method(D_METHOD("set_controller_value", "controller_value"), &InputEventMIDI::set_controller_value);
1891
ClassDB::bind_method(D_METHOD("get_controller_value"), &InputEventMIDI::get_controller_value);
1892
1893
ADD_PROPERTY(PropertyInfo(Variant::INT, "channel"), "set_channel", "get_channel");
1894
ADD_PROPERTY(PropertyInfo(Variant::INT, "message"), "set_message", "get_message");
1895
ADD_PROPERTY(PropertyInfo(Variant::INT, "pitch"), "set_pitch", "get_pitch");
1896
ADD_PROPERTY(PropertyInfo(Variant::INT, "velocity"), "set_velocity", "get_velocity");
1897
ADD_PROPERTY(PropertyInfo(Variant::INT, "instrument"), "set_instrument", "get_instrument");
1898
ADD_PROPERTY(PropertyInfo(Variant::INT, "pressure"), "set_pressure", "get_pressure");
1899
ADD_PROPERTY(PropertyInfo(Variant::INT, "controller_number"), "set_controller_number", "get_controller_number");
1900
ADD_PROPERTY(PropertyInfo(Variant::INT, "controller_value"), "set_controller_value", "get_controller_value");
1901
}
1902
1903
///////////////////////////////////
1904
1905
void InputEventShortcut::set_shortcut(Ref<Shortcut> p_shortcut) {
1906
shortcut = p_shortcut;
1907
emit_changed();
1908
}
1909
1910
Ref<Shortcut> InputEventShortcut::get_shortcut() {
1911
return shortcut;
1912
}
1913
1914
void InputEventShortcut::_bind_methods() {
1915
ClassDB::bind_method(D_METHOD("set_shortcut", "shortcut"), &InputEventShortcut::set_shortcut);
1916
ClassDB::bind_method(D_METHOD("get_shortcut"), &InputEventShortcut::get_shortcut);
1917
1918
ADD_PROPERTY(PropertyInfo(Variant::OBJECT, "shortcut", PROPERTY_HINT_RESOURCE_TYPE, "Shortcut"), "set_shortcut", "get_shortcut");
1919
}
1920
1921
String InputEventShortcut::as_text() const {
1922
ERR_FAIL_COND_V(shortcut.is_null(), "None");
1923
1924
return vformat(RTR("Input Event with Shortcut=%s"), shortcut->get_as_text());
1925
}
1926
1927
String InputEventShortcut::to_string() {
1928
ERR_FAIL_COND_V(shortcut.is_null(), "None");
1929
1930
return vformat("InputEventShortcut: shortcut=%s", shortcut->get_as_text());
1931
}
1932
1933
InputEventShortcut::InputEventShortcut() {
1934
pressed = true;
1935
}
1936
1937