10 #include "flutter/shell/platform/embedder/embedder.h"
11 #include "flutter/shell/platform/embedder/test_utils/key_codes.g.h"
12 #include "flutter/shell/platform/embedder/test_utils/proc_table_replacement.h"
14 #include "flutter/shell/platform/windows/testing/engine_modifier.h"
15 #include "gtest/gtest.h"
22 constexpr SHORT kStateMaskToggled = 0x01;
23 constexpr SHORT kStateMaskPressed = 0x80;
25 class TestFlutterKeyEvent :
public FlutterKeyEvent {
27 TestFlutterKeyEvent(
const FlutterKeyEvent& src,
31 struct_size = src.struct_size;
32 timestamp = src.timestamp;
34 physical = src.physical;
35 logical = src.logical;
37 synthesized = src.synthesized;
40 TestFlutterKeyEvent(TestFlutterKeyEvent&& source)
41 : FlutterKeyEvent(source),
51 const std::string character_str;
57 state_[virtual_key] = (
pressed ? kStateMaskPressed : 0) |
61 SHORT Get(
int virtual_key) {
return state_[virtual_key]; }
64 return [
this](
int virtual_key) {
return Get(virtual_key); };
68 std::map<int, SHORT> state_;
71 UINT DefaultMapVkToScan(UINT virtual_key,
bool extended) {
72 return MapVirtualKey(virtual_key,
73 extended ? MAPVK_VK_TO_VSC_EX : MAPVK_VK_TO_VSC);
77 constexpr uint64_t kScanCodeAltLeft = 0x38;
78 constexpr uint64_t kScanCodeNumpad1 = 0x4f;
79 constexpr uint64_t kScanCodeNumLock = 0x45;
80 constexpr uint64_t kScanCodeControl = 0x1d;
88 using namespace ::flutter::testing::keycodes;
94 EXPECT_EQ(result.length(), 1);
95 EXPECT_EQ(result[0],
'\x24');
98 EXPECT_EQ(result.length(), 2);
99 EXPECT_EQ(result[0],
'\xC2');
100 EXPECT_EQ(result[1],
'\xA2');
103 EXPECT_EQ(result.length(), 3);
104 EXPECT_EQ(result[0],
'\xE0');
105 EXPECT_EQ(result[1],
'\xA4');
106 EXPECT_EQ(result[2],
'\xB9');
109 EXPECT_EQ(result.length(), 4);
110 EXPECT_EQ(result[0],
'\xF0');
111 EXPECT_EQ(result[1],
'\x90');
112 EXPECT_EQ(result[2],
'\x8D');
113 EXPECT_EQ(result[3],
'\x88');
119 TEST(KeyboardKeyEmbedderHandlerTest, BasicKeyPressingAndHolding) {
120 TestKeystate key_state;
121 std::vector<TestFlutterKeyEvent> results;
122 TestFlutterKeyEvent* event;
123 bool last_handled =
false;
125 std::unique_ptr<KeyboardKeyEmbedderHandler> handler =
126 std::make_unique<KeyboardKeyEmbedderHandler>(
127 [&results](
const FlutterKeyEvent& event,
131 key_state.Getter(), DefaultMapVkToScan);
134 handler->KeyboardHook(
136 [&last_handled](
bool handled) { last_handled = handled; });
137 EXPECT_EQ(last_handled,
false);
138 EXPECT_EQ(results.size(), 1);
140 EXPECT_EQ(event->type, kFlutterKeyEventTypeDown);
141 EXPECT_EQ(event->physical, kPhysicalKeyA);
142 EXPECT_EQ(event->logical, kLogicalKeyA);
143 EXPECT_STREQ(event->character,
"a");
144 EXPECT_EQ(event->synthesized,
false);
146 event->callback(
true, event->user_data);
147 EXPECT_EQ(last_handled,
true);
152 handler->KeyboardHook(
154 [&last_handled](
bool handled) { last_handled = handled; });
155 EXPECT_EQ(last_handled,
true);
156 EXPECT_EQ(results.size(), 1);
158 EXPECT_EQ(event->type, kFlutterKeyEventTypeRepeat);
159 EXPECT_EQ(event->physical, kPhysicalKeyA);
160 EXPECT_EQ(event->logical, kLogicalKeyA);
161 EXPECT_STREQ(event->character,
"a");
162 EXPECT_EQ(event->synthesized,
false);
164 event->callback(
false, event->user_data);
165 EXPECT_EQ(last_handled,
false);
169 handler->KeyboardHook(
171 [&last_handled](
bool handled) { last_handled = handled; });
172 EXPECT_EQ(results.size(), 1);
174 EXPECT_EQ(event->type, kFlutterKeyEventTypeUp);
175 EXPECT_EQ(event->physical, kPhysicalKeyA);
176 EXPECT_EQ(event->logical, kLogicalKeyA);
177 EXPECT_STREQ(event->character,
"");
178 EXPECT_EQ(event->synthesized,
false);
179 event->callback(
false, event->user_data);
187 TEST(KeyboardKeyEmbedderHandlerTest, ToggleNumLockDuringNumpadPress) {
188 TestKeystate key_state;
189 std::vector<TestFlutterKeyEvent> results;
190 TestFlutterKeyEvent* event;
191 bool last_handled =
false;
193 std::unique_ptr<KeyboardKeyEmbedderHandler> handler =
194 std::make_unique<KeyboardKeyEmbedderHandler>(
195 [&results](
const FlutterKeyEvent& event,
199 key_state.Getter(), DefaultMapVkToScan);
202 key_state.Set(VK_NUMPAD1,
true);
203 handler->KeyboardHook(
204 VK_NUMPAD1, kScanCodeNumpad1, WM_KEYDOWN, 0,
false,
false,
205 [&last_handled](
bool handled) { last_handled = handled; });
206 EXPECT_EQ(results.size(), 1);
208 EXPECT_EQ(event->type, kFlutterKeyEventTypeDown);
209 EXPECT_EQ(event->physical, kPhysicalNumpad1);
210 EXPECT_EQ(event->logical, kLogicalNumpad1);
212 EXPECT_EQ(event->synthesized,
false);
216 key_state.Set(VK_NUMLOCK,
true,
true);
217 handler->KeyboardHook(
218 VK_NUMLOCK, kScanCodeNumLock, WM_KEYDOWN, 0,
true,
false,
219 [&last_handled](
bool handled) { last_handled = handled; });
220 EXPECT_EQ(results.size(), 1);
222 EXPECT_EQ(event->type, kFlutterKeyEventTypeDown);
223 EXPECT_EQ(event->physical, kPhysicalNumLock);
224 EXPECT_EQ(event->logical, kLogicalNumLock);
225 EXPECT_STREQ(event->character,
"");
226 EXPECT_EQ(event->synthesized,
false);
230 key_state.Set(VK_NUMLOCK,
false,
true);
231 handler->KeyboardHook(
232 VK_NUMLOCK, kScanCodeNumLock, WM_KEYUP, 0,
true,
true,
233 [&last_handled](
bool handled) { last_handled = handled; });
234 EXPECT_EQ(results.size(), 1);
236 EXPECT_EQ(event->type, kFlutterKeyEventTypeUp);
237 EXPECT_EQ(event->physical, kPhysicalNumLock);
238 EXPECT_EQ(event->logical, kLogicalNumLock);
239 EXPECT_STREQ(event->character,
"");
240 EXPECT_EQ(event->synthesized,
false);
244 handler->KeyboardHook(
245 VK_END, kScanCodeNumpad1, WM_KEYUP, 0,
false,
true,
246 [&last_handled](
bool handled) { last_handled = handled; });
247 EXPECT_EQ(results.size(), 1);
249 EXPECT_EQ(event->type, kFlutterKeyEventTypeUp);
250 EXPECT_EQ(event->physical, kPhysicalNumpad1);
251 EXPECT_EQ(event->logical, kLogicalNumpad1);
252 EXPECT_STREQ(event->character,
"");
253 EXPECT_EQ(event->synthesized,
false);
259 TEST(KeyboardKeyEmbedderHandlerTest, ImeEventsAreIgnored) {
260 TestKeystate key_state;
261 std::vector<TestFlutterKeyEvent> results;
262 TestFlutterKeyEvent* event;
263 bool last_handled =
false;
265 std::unique_ptr<KeyboardKeyEmbedderHandler> handler =
266 std::make_unique<KeyboardKeyEmbedderHandler>(
267 [&results](
const FlutterKeyEvent& event,
271 key_state.Getter(), DefaultMapVkToScan);
274 last_handled =
false;
275 handler->KeyboardHook(
277 [&last_handled](
bool handled) { last_handled = handled; });
278 EXPECT_EQ(last_handled,
true);
281 EXPECT_EQ(results.size(), 1);
283 EXPECT_EQ(event->physical, 0);
284 EXPECT_EQ(event->logical, 0);
285 EXPECT_EQ(event->callback,
nullptr);
289 last_handled =
false;
290 handler->KeyboardHook(
293 [&last_handled](
bool handled) { last_handled = handled; });
294 EXPECT_EQ(last_handled,
true);
297 EXPECT_EQ(results.size(), 1);
299 EXPECT_EQ(event->physical, 0);
300 EXPECT_EQ(event->logical, 0);
301 EXPECT_EQ(event->callback,
nullptr);
306 last_handled =
false;
307 handler->KeyboardHook(
309 [&last_handled](
bool handled) { last_handled = handled; });
311 EXPECT_EQ(last_handled,
false);
312 EXPECT_EQ(results.size(), 1);
314 event->callback(
true, event->user_data);
315 EXPECT_EQ(last_handled,
true);
318 last_handled =
false;
320 handler->KeyboardHook(
322 [&last_handled](
bool handled) { last_handled = handled; });
323 EXPECT_EQ(last_handled,
false);
324 EXPECT_EQ(results.size(), 1);
326 event->callback(
true, event->user_data);
327 EXPECT_EQ(last_handled,
true);
333 TEST(KeyboardKeyEmbedderHandlerTest, ModifierKeysByExtendedBit) {
334 TestKeystate key_state;
335 std::vector<TestFlutterKeyEvent> results;
336 TestFlutterKeyEvent* event;
337 bool last_handled =
false;
339 std::unique_ptr<KeyboardKeyEmbedderHandler> handler =
340 std::make_unique<KeyboardKeyEmbedderHandler>(
341 [&results](
const FlutterKeyEvent& event,
345 key_state.Getter(), DefaultMapVkToScan);
348 last_handled =
false;
349 key_state.Set(VK_LCONTROL,
true);
350 handler->KeyboardHook(
351 VK_LCONTROL, kScanCodeControl, WM_KEYDOWN, 0,
false,
false,
352 [&last_handled](
bool handled) { last_handled = handled; });
353 EXPECT_EQ(last_handled,
false);
354 EXPECT_EQ(results.size(), 1);
356 EXPECT_EQ(event->type, kFlutterKeyEventTypeDown);
357 EXPECT_EQ(event->physical, kPhysicalControlLeft);
358 EXPECT_EQ(event->logical, kLogicalControlLeft);
359 EXPECT_STREQ(event->character,
"");
360 EXPECT_EQ(event->synthesized,
false);
362 event->callback(
true, event->user_data);
363 EXPECT_EQ(last_handled,
true);
367 last_handled =
false;
368 key_state.Set(VK_RCONTROL,
true);
369 handler->KeyboardHook(
370 VK_RCONTROL, kScanCodeControl, WM_KEYDOWN, 0,
true,
true,
371 [&last_handled](
bool handled) { last_handled = handled; });
372 EXPECT_EQ(last_handled,
false);
373 EXPECT_EQ(results.size(), 1);
375 EXPECT_EQ(event->type, kFlutterKeyEventTypeDown);
376 EXPECT_EQ(event->physical, kPhysicalControlRight);
377 EXPECT_EQ(event->logical, kLogicalControlRight);
378 EXPECT_STREQ(event->character,
"");
379 EXPECT_EQ(event->synthesized,
false);
381 event->callback(
true, event->user_data);
382 EXPECT_EQ(last_handled,
true);
386 last_handled =
false;
387 key_state.Set(VK_LCONTROL,
false);
388 handler->KeyboardHook(
389 VK_LCONTROL, kScanCodeControl, WM_KEYUP, 0,
false,
true,
390 [&last_handled](
bool handled) { last_handled = handled; });
391 EXPECT_EQ(last_handled,
false);
392 EXPECT_EQ(results.size(), 1);
394 EXPECT_EQ(event->type, kFlutterKeyEventTypeUp);
395 EXPECT_EQ(event->physical, kPhysicalControlLeft);
396 EXPECT_EQ(event->logical, kLogicalControlLeft);
397 EXPECT_STREQ(event->character,
"");
398 EXPECT_EQ(event->synthesized,
false);
400 event->callback(
true, event->user_data);
401 EXPECT_EQ(last_handled,
true);
405 last_handled =
false;
406 key_state.Set(VK_RCONTROL,
false);
407 handler->KeyboardHook(
408 VK_RCONTROL, kScanCodeControl, WM_KEYUP, 0,
true,
true,
409 [&last_handled](
bool handled) { last_handled = handled; });
410 EXPECT_EQ(last_handled,
false);
411 EXPECT_EQ(results.size(), 1);
413 EXPECT_EQ(event->type, kFlutterKeyEventTypeUp);
414 EXPECT_EQ(event->physical, kPhysicalControlRight);
415 EXPECT_EQ(event->logical, kLogicalControlRight);
416 EXPECT_STREQ(event->character,
"");
417 EXPECT_EQ(event->synthesized,
false);
419 event->callback(
true, event->user_data);
420 EXPECT_EQ(last_handled,
true);
426 TEST(KeyboardKeyEmbedderHandlerTest, ModifierKeysByVirtualKey) {
427 TestKeystate key_state;
428 std::vector<TestFlutterKeyEvent> results;
429 TestFlutterKeyEvent* event;
430 bool last_handled =
false;
432 std::unique_ptr<KeyboardKeyEmbedderHandler> handler =
433 std::make_unique<KeyboardKeyEmbedderHandler>(
434 [&results](
const FlutterKeyEvent& event,
438 key_state.Getter(), DefaultMapVkToScan);
441 last_handled =
false;
442 key_state.Set(VK_LSHIFT,
true);
443 handler->KeyboardHook(
445 [&last_handled](
bool handled) { last_handled = handled; });
446 EXPECT_EQ(last_handled,
false);
447 EXPECT_EQ(results.size(), 1);
449 EXPECT_EQ(event->type, kFlutterKeyEventTypeDown);
450 EXPECT_EQ(event->physical, kPhysicalShiftLeft);
451 EXPECT_EQ(event->logical, kLogicalShiftLeft);
452 EXPECT_STREQ(event->character,
"");
453 EXPECT_EQ(event->synthesized,
false);
455 event->callback(
true, event->user_data);
456 EXPECT_EQ(last_handled,
true);
460 last_handled =
false;
461 key_state.Set(VK_RSHIFT,
true);
462 handler->KeyboardHook(
464 [&last_handled](
bool handled) { last_handled = handled; });
465 EXPECT_EQ(last_handled,
false);
466 EXPECT_EQ(results.size(), 1);
468 EXPECT_EQ(event->type, kFlutterKeyEventTypeDown);
469 EXPECT_EQ(event->physical, kPhysicalShiftRight);
470 EXPECT_EQ(event->logical, kLogicalShiftRight);
471 EXPECT_STREQ(event->character,
"");
472 EXPECT_EQ(event->synthesized,
false);
474 event->callback(
true, event->user_data);
475 EXPECT_EQ(last_handled,
true);
479 last_handled =
false;
480 key_state.Set(VK_LSHIFT,
false);
481 handler->KeyboardHook(
483 [&last_handled](
bool handled) { last_handled = handled; });
484 EXPECT_EQ(last_handled,
false);
485 EXPECT_EQ(results.size(), 1);
487 EXPECT_EQ(event->type, kFlutterKeyEventTypeUp);
488 EXPECT_EQ(event->physical, kPhysicalShiftLeft);
489 EXPECT_EQ(event->logical, kLogicalShiftLeft);
490 EXPECT_STREQ(event->character,
"");
491 EXPECT_EQ(event->synthesized,
false);
493 event->callback(
true, event->user_data);
494 EXPECT_EQ(last_handled,
true);
498 last_handled =
false;
499 key_state.Set(VK_RSHIFT,
false);
500 handler->KeyboardHook(
502 [&last_handled](
bool handled) { last_handled = handled; });
503 EXPECT_EQ(last_handled,
false);
504 EXPECT_EQ(results.size(), 1);
506 EXPECT_EQ(event->type, kFlutterKeyEventTypeUp);
507 EXPECT_EQ(event->physical, kPhysicalShiftRight);
508 EXPECT_EQ(event->logical, kLogicalShiftRight);
509 EXPECT_STREQ(event->character,
"");
510 EXPECT_EQ(event->synthesized,
false);
512 event->callback(
true, event->user_data);
513 EXPECT_EQ(last_handled,
true);
519 TEST(KeyboardKeyEmbedderHandlerTest,
520 SynthesizeModifierLeftKeyDownWhenNotPressed) {
521 TestKeystate key_state;
522 std::vector<TestFlutterKeyEvent> results;
523 TestFlutterKeyEvent* event;
524 bool last_handled =
false;
526 std::unique_ptr<KeyboardKeyEmbedderHandler> handler =
527 std::make_unique<KeyboardKeyEmbedderHandler>(
528 [&results](
const FlutterKeyEvent& event,
532 key_state.Getter(), DefaultMapVkToScan);
535 handler->SyncModifiersIfNeeded(
kShift);
536 EXPECT_EQ(results.size(), 1);
538 EXPECT_EQ(event->type, kFlutterKeyEventTypeDown);
539 EXPECT_EQ(event->physical, kPhysicalShiftLeft);
540 EXPECT_EQ(event->logical, kLogicalShiftLeft);
541 EXPECT_STREQ(event->character,
"");
542 EXPECT_EQ(event->synthesized,
true);
546 handler->SyncModifiersIfNeeded(0);
550 handler->SyncModifiersIfNeeded(
kControl);
551 EXPECT_EQ(results.size(), 1);
553 EXPECT_EQ(event->type, kFlutterKeyEventTypeDown);
554 EXPECT_EQ(event->physical, kPhysicalControlLeft);
555 EXPECT_EQ(event->logical, kLogicalControlLeft);
556 EXPECT_STREQ(event->character,
"");
557 EXPECT_EQ(event->synthesized,
true);
562 TEST(KeyboardKeyEmbedderHandlerTest, DoNotSynthesizeModifierDownWhenPressed) {
563 TestKeystate key_state;
564 std::vector<TestFlutterKeyEvent> results;
565 TestFlutterKeyEvent* event;
566 bool last_handled =
false;
568 std::unique_ptr<KeyboardKeyEmbedderHandler> handler =
569 std::make_unique<KeyboardKeyEmbedderHandler>(
570 [&results](
const FlutterKeyEvent& event,
574 key_state.Getter(), DefaultMapVkToScan);
578 handler->KeyboardHook(
580 [&last_handled](
bool handled) { last_handled = handled; });
582 handler->SyncModifiersIfNeeded(
kShift);
583 EXPECT_EQ(results.size(), 0);
587 handler->KeyboardHook(
589 [&last_handled](
bool handled) { last_handled = handled; });
591 handler->SyncModifiersIfNeeded(
kShift);
592 EXPECT_EQ(results.size(), 0);
596 handler->KeyboardHook(
598 [&last_handled](
bool handled) { last_handled = handled; });
600 handler->SyncModifiersIfNeeded(
kControl);
601 EXPECT_EQ(results.size(), 0);
605 handler->KeyboardHook(
607 [&last_handled](
bool handled) { last_handled = handled; });
609 handler->SyncModifiersIfNeeded(
kControl);
610 EXPECT_EQ(results.size(), 0);
615 TEST(KeyboardKeyEmbedderHandlerTest, SynthesizeModifierUpWhenPressed) {
616 TestKeystate key_state;
617 std::vector<TestFlutterKeyEvent> results;
618 TestFlutterKeyEvent* event;
619 bool last_handled =
false;
621 std::unique_ptr<KeyboardKeyEmbedderHandler> handler =
622 std::make_unique<KeyboardKeyEmbedderHandler>(
623 [&results](
const FlutterKeyEvent& event,
627 key_state.Getter(), DefaultMapVkToScan);
631 handler->KeyboardHook(
633 [&last_handled](
bool handled) { last_handled = handled; });
635 handler->SyncModifiersIfNeeded(0);
636 EXPECT_EQ(results.size(), 1);
638 EXPECT_EQ(event->type, kFlutterKeyEventTypeUp);
639 EXPECT_EQ(event->physical, kPhysicalShiftLeft);
640 EXPECT_EQ(event->logical, kLogicalShiftLeft);
641 EXPECT_STREQ(event->character,
"");
642 EXPECT_EQ(event->synthesized,
true);
647 handler->KeyboardHook(
649 [&last_handled](
bool handled) { last_handled = handled; });
651 handler->SyncModifiersIfNeeded(0);
652 EXPECT_EQ(results.size(), 1);
654 EXPECT_EQ(event->type, kFlutterKeyEventTypeUp);
655 EXPECT_EQ(event->physical, kPhysicalShiftRight);
656 EXPECT_EQ(event->logical, kLogicalShiftRight);
657 EXPECT_STREQ(event->character,
"");
658 EXPECT_EQ(event->synthesized,
true);
663 handler->KeyboardHook(
665 [&last_handled](
bool handled) { last_handled = handled; });
667 handler->SyncModifiersIfNeeded(0);
668 EXPECT_EQ(results.size(), 1);
670 EXPECT_EQ(event->type, kFlutterKeyEventTypeUp);
671 EXPECT_EQ(event->physical, kPhysicalControlLeft);
672 EXPECT_EQ(event->logical, kLogicalControlLeft);
673 EXPECT_STREQ(event->character,
"");
674 EXPECT_EQ(event->synthesized,
true);
679 handler->KeyboardHook(
681 [&last_handled](
bool handled) { last_handled = handled; });
683 handler->SyncModifiersIfNeeded(0);
684 EXPECT_EQ(results.size(), 1);
686 EXPECT_EQ(event->type, kFlutterKeyEventTypeUp);
687 EXPECT_EQ(event->physical, kPhysicalControlRight);
688 EXPECT_EQ(event->logical, kLogicalControlRight);
689 EXPECT_STREQ(event->character,
"");
690 EXPECT_EQ(event->synthesized,
true);
696 TEST(KeyboardKeyEmbedderHandlerTest, DoNotSynthesizeModifierUpWhenNotPressed) {
697 TestKeystate key_state;
698 std::vector<TestFlutterKeyEvent> results;
699 TestFlutterKeyEvent* event;
700 bool last_handled =
false;
702 std::unique_ptr<KeyboardKeyEmbedderHandler> handler =
703 std::make_unique<KeyboardKeyEmbedderHandler>(
704 [&results](
const FlutterKeyEvent& event,
708 key_state.Getter(), DefaultMapVkToScan);
712 handler->SyncModifiersIfNeeded(0);
713 EXPECT_EQ(results.size(), 0);
716 TEST(KeyboardKeyEmbedderHandlerTest, RepeatedDownIsIgnored) {
717 TestKeystate key_state;
718 std::vector<TestFlutterKeyEvent> results;
719 TestFlutterKeyEvent* event;
720 bool last_handled =
false;
722 std::unique_ptr<KeyboardKeyEmbedderHandler> handler =
723 std::make_unique<KeyboardKeyEmbedderHandler>(
724 [&results](
const FlutterKeyEvent& event,
728 key_state.Getter(), DefaultMapVkToScan);
729 last_handled =
false;
732 handler->KeyboardHook(
734 [&last_handled](
bool handled) { last_handled = handled; });
735 EXPECT_EQ(last_handled,
false);
736 EXPECT_EQ(results.size(), 1);
738 EXPECT_EQ(event->type, kFlutterKeyEventTypeDown);
739 EXPECT_EQ(event->physical, kPhysicalKeyA);
740 EXPECT_EQ(event->logical, kLogicalKeyA);
741 EXPECT_STREQ(event->character,
"a");
742 EXPECT_EQ(event->synthesized,
false);
744 event->callback(
true, event->user_data);
745 EXPECT_EQ(last_handled,
true);
751 last_handled =
false;
752 handler->KeyboardHook(
754 [&last_handled](
bool handled) { last_handled = handled; });
755 EXPECT_EQ(last_handled,
true);
756 EXPECT_EQ(results.size(), 1);
758 EXPECT_EQ(event->physical, 0);
759 EXPECT_EQ(event->logical, 0);
760 EXPECT_EQ(event->callback,
nullptr);
764 TEST(KeyboardKeyEmbedderHandlerTest, AbruptRepeatIsConvertedToDown) {
765 TestKeystate key_state;
766 std::vector<TestFlutterKeyEvent> results;
767 TestFlutterKeyEvent* event;
768 bool last_handled =
false;
770 std::unique_ptr<KeyboardKeyEmbedderHandler> handler =
771 std::make_unique<KeyboardKeyEmbedderHandler>(
772 [&results](
const FlutterKeyEvent& event,
776 key_state.Getter(), DefaultMapVkToScan);
777 last_handled =
false;
782 handler->KeyboardHook(
784 [&last_handled](
bool handled) { last_handled = handled; });
785 EXPECT_EQ(last_handled,
false);
786 EXPECT_EQ(results.size(), 1);
788 EXPECT_EQ(event->type, kFlutterKeyEventTypeDown);
789 EXPECT_EQ(event->physical, kPhysicalKeyA);
790 EXPECT_EQ(event->logical, kLogicalKeyA);
791 EXPECT_STREQ(event->character,
"a");
792 EXPECT_EQ(event->synthesized,
false);
794 event->callback(
true, event->user_data);
795 EXPECT_EQ(last_handled,
true);
799 last_handled =
false;
801 handler->KeyboardHook(
803 [&last_handled](
bool handled) { last_handled = handled; });
804 EXPECT_EQ(last_handled,
false);
805 EXPECT_EQ(results.size(), 1);
807 EXPECT_EQ(event->type, kFlutterKeyEventTypeUp);
808 EXPECT_EQ(event->physical, kPhysicalKeyA);
809 EXPECT_EQ(event->logical, kLogicalKeyA);
810 EXPECT_STREQ(event->character,
"");
811 EXPECT_EQ(event->synthesized,
false);
813 event->callback(
true, event->user_data);
814 EXPECT_EQ(last_handled,
true);
818 TEST(KeyboardKeyEmbedderHandlerTest, AbruptUpIsIgnored) {
819 TestKeystate key_state;
820 std::vector<TestFlutterKeyEvent> results;
821 TestFlutterKeyEvent* event;
822 bool last_handled =
false;
824 std::unique_ptr<KeyboardKeyEmbedderHandler> handler =
825 std::make_unique<KeyboardKeyEmbedderHandler>(
826 [&results](
const FlutterKeyEvent& event,
830 key_state.Getter(), DefaultMapVkToScan);
831 last_handled =
false;
838 last_handled =
false;
839 handler->KeyboardHook(
841 [&last_handled](
bool handled) { last_handled = handled; });
842 EXPECT_EQ(last_handled,
true);
843 EXPECT_EQ(results.size(), 1);
845 EXPECT_EQ(event->physical, 0);
846 EXPECT_EQ(event->logical, 0);
847 EXPECT_EQ(event->callback,
nullptr);
851 TEST(KeyboardKeyEmbedderHandlerTest, SynthesizeForDesyncPressingState) {
852 TestKeystate key_state;
853 std::vector<TestFlutterKeyEvent> results;
854 TestFlutterKeyEvent* event;
855 bool last_handled =
false;
857 std::unique_ptr<KeyboardKeyEmbedderHandler> handler =
858 std::make_unique<KeyboardKeyEmbedderHandler>(
859 [&results](
const FlutterKeyEvent& event,
863 key_state.Getter(), DefaultMapVkToScan);
866 key_state.Set(VK_LCONTROL,
true);
870 handler->KeyboardHook(
872 [&last_handled](
bool handled) { last_handled = handled; });
873 EXPECT_EQ(last_handled,
false);
874 EXPECT_EQ(results.size(), 2);
876 EXPECT_EQ(event->type, kFlutterKeyEventTypeDown);
877 EXPECT_EQ(event->physical, kPhysicalControlLeft);
878 EXPECT_EQ(event->logical, kLogicalControlLeft);
879 EXPECT_STREQ(event->character,
"");
880 EXPECT_EQ(event->synthesized,
true);
881 EXPECT_EQ(event->callback,
nullptr);
884 EXPECT_EQ(event->type, kFlutterKeyEventTypeDown);
885 EXPECT_EQ(event->physical, kPhysicalKeyA);
886 EXPECT_EQ(event->logical, kLogicalKeyA);
887 EXPECT_STREQ(event->character,
"a");
888 EXPECT_EQ(event->synthesized,
false);
891 event->callback(
false, event->user_data);
892 EXPECT_EQ(last_handled,
false);
896 key_state.Set(VK_LCONTROL,
false);
899 handler->KeyboardHook(
901 [&last_handled](
bool handled) { last_handled = handled; });
902 EXPECT_EQ(last_handled,
false);
903 EXPECT_EQ(results.size(), 2);
905 EXPECT_EQ(event->type, kFlutterKeyEventTypeUp);
906 EXPECT_EQ(event->physical, kPhysicalControlLeft);
907 EXPECT_EQ(event->logical, kLogicalControlLeft);
908 EXPECT_STREQ(event->character,
"");
909 EXPECT_EQ(event->synthesized,
true);
910 EXPECT_EQ(event->callback,
nullptr);
913 EXPECT_EQ(event->type, kFlutterKeyEventTypeRepeat);
914 EXPECT_EQ(event->physical, kPhysicalKeyA);
915 EXPECT_EQ(event->logical, kLogicalKeyA);
916 EXPECT_STREQ(event->character,
"a");
917 EXPECT_EQ(event->synthesized,
false);
920 event->callback(
false, event->user_data);
921 EXPECT_EQ(last_handled,
false);
926 handler->KeyboardHook(
928 [&last_handled](
bool handled) { last_handled = handled; });
929 EXPECT_EQ(results.size(), 1);
931 EXPECT_EQ(event->type, kFlutterKeyEventTypeUp);
932 EXPECT_EQ(event->physical, kPhysicalKeyA);
933 EXPECT_EQ(event->logical, kLogicalKeyA);
934 EXPECT_STREQ(event->character,
"");
935 EXPECT_EQ(event->synthesized,
false);
936 event->callback(
false, event->user_data);
939 TEST(KeyboardKeyEmbedderHandlerTest, SynthesizeForDesyncToggledState) {
940 TestKeystate key_state;
941 std::vector<TestFlutterKeyEvent> results;
942 TestFlutterKeyEvent* event;
943 bool last_handled =
false;
945 std::unique_ptr<KeyboardKeyEmbedderHandler> handler =
946 std::make_unique<KeyboardKeyEmbedderHandler>(
947 [&results](
const FlutterKeyEvent& event,
951 key_state.Getter(), DefaultMapVkToScan);
954 key_state.Set(VK_NUMLOCK,
false,
true);
958 handler->KeyboardHook(
960 [&last_handled](
bool handled) { last_handled = handled; });
961 EXPECT_EQ(last_handled,
false);
962 EXPECT_EQ(results.size(), 3);
964 EXPECT_EQ(event->type, kFlutterKeyEventTypeDown);
965 EXPECT_EQ(event->physical, kPhysicalNumLock);
966 EXPECT_EQ(event->logical, kLogicalNumLock);
967 EXPECT_STREQ(event->character,
"");
968 EXPECT_EQ(event->synthesized,
true);
971 EXPECT_EQ(event->type, kFlutterKeyEventTypeUp);
972 EXPECT_EQ(event->physical, kPhysicalNumLock);
973 EXPECT_EQ(event->logical, kLogicalNumLock);
974 EXPECT_STREQ(event->character,
"");
975 EXPECT_EQ(event->synthesized,
true);
978 EXPECT_EQ(event->type, kFlutterKeyEventTypeDown);
979 EXPECT_EQ(event->physical, kPhysicalKeyA);
980 EXPECT_EQ(event->logical, kLogicalKeyA);
981 EXPECT_STREQ(event->character,
"a");
982 EXPECT_EQ(event->synthesized,
false);
984 event->callback(
true, event->user_data);
985 EXPECT_EQ(last_handled,
true);
989 key_state.Set(VK_NUMLOCK,
true,
true);
992 handler->KeyboardHook(
994 [&last_handled](
bool handled) { last_handled = handled; });
995 EXPECT_EQ(last_handled,
true);
996 EXPECT_EQ(results.size(), 2);
998 EXPECT_EQ(event->type, kFlutterKeyEventTypeDown);
999 EXPECT_EQ(event->physical, kPhysicalNumLock);
1000 EXPECT_EQ(event->logical, kLogicalNumLock);
1001 EXPECT_STREQ(event->character,
"");
1002 EXPECT_EQ(event->synthesized,
true);
1004 event = &results[1];
1005 EXPECT_EQ(event->type, kFlutterKeyEventTypeRepeat);
1006 EXPECT_EQ(event->physical, kPhysicalKeyA);
1007 EXPECT_EQ(event->logical, kLogicalKeyA);
1008 EXPECT_STREQ(event->character,
"a");
1009 EXPECT_EQ(event->synthesized,
false);
1011 event->callback(
false, event->user_data);
1012 EXPECT_EQ(last_handled,
false);
1018 key_state.Set(VK_NUMLOCK,
false,
false);
1022 handler->KeyboardHook(
1024 [&last_handled](
bool handled) { last_handled = handled; });
1025 EXPECT_EQ(results.size(), 4);
1026 event = &results[0];
1027 EXPECT_EQ(event->type, kFlutterKeyEventTypeUp);
1028 EXPECT_EQ(event->physical, kPhysicalNumLock);
1029 EXPECT_EQ(event->logical, kLogicalNumLock);
1030 EXPECT_STREQ(event->character,
"");
1031 EXPECT_EQ(event->synthesized,
true);
1032 EXPECT_EQ(event->callback,
nullptr);
1034 event = &results[1];
1035 EXPECT_EQ(event->type, kFlutterKeyEventTypeDown);
1036 EXPECT_EQ(event->physical, kPhysicalNumLock);
1037 EXPECT_EQ(event->logical, kLogicalNumLock);
1038 EXPECT_STREQ(event->character,
"");
1039 EXPECT_EQ(event->synthesized,
true);
1040 EXPECT_EQ(event->callback,
nullptr);
1042 event = &results[2];
1043 EXPECT_EQ(event->type, kFlutterKeyEventTypeUp);
1044 EXPECT_EQ(event->physical, kPhysicalNumLock);
1045 EXPECT_EQ(event->logical, kLogicalNumLock);
1046 EXPECT_STREQ(event->character,
"");
1047 EXPECT_EQ(event->synthesized,
true);
1048 EXPECT_EQ(event->callback,
nullptr);
1050 event = &results[3];
1051 EXPECT_EQ(event->type, kFlutterKeyEventTypeUp);
1052 EXPECT_EQ(event->physical, kPhysicalKeyA);
1053 EXPECT_EQ(event->logical, kLogicalKeyA);
1054 EXPECT_STREQ(event->character,
"");
1055 EXPECT_EQ(event->synthesized,
false);
1056 event->callback(
false, event->user_data);
1059 TEST(KeyboardKeyEmbedderHandlerTest,
1060 SynthesizeForDesyncToggledStateByItselfsUp) {
1061 TestKeystate key_state;
1062 std::vector<TestFlutterKeyEvent> results;
1063 TestFlutterKeyEvent* event;
1064 bool last_handled =
false;
1066 std::unique_ptr<KeyboardKeyEmbedderHandler> handler =
1067 std::make_unique<KeyboardKeyEmbedderHandler>(
1068 [&results](
const FlutterKeyEvent& event,
1072 key_state.Getter(), DefaultMapVkToScan);
1075 key_state.Set(VK_NUMLOCK,
true,
true);
1076 handler->KeyboardHook(
1077 VK_NUMLOCK, kScanCodeNumLock, WM_KEYDOWN, 0,
true,
false,
1078 [&last_handled](
bool handled) { last_handled = handled; });
1079 event = &results.back();
1080 event->callback(
false, event->user_data);
1084 key_state.Set(VK_NUMLOCK,
false,
false);
1086 handler->KeyboardHook(
1087 VK_NUMLOCK, kScanCodeNumLock, WM_KEYUP, 0,
true,
true,
1088 [&last_handled](
bool handled) { last_handled = handled; });
1089 EXPECT_EQ(last_handled,
false);
1090 EXPECT_EQ(results.size(), 3);
1091 event = &results[0];
1092 EXPECT_EQ(event->type, kFlutterKeyEventTypeUp);
1093 EXPECT_EQ(event->physical, kPhysicalNumLock);
1094 EXPECT_EQ(event->logical, kLogicalNumLock);
1095 EXPECT_STREQ(event->character,
"");
1096 EXPECT_EQ(event->synthesized,
true);
1097 EXPECT_EQ(event->callback,
nullptr);
1099 event = &results[1];
1100 EXPECT_EQ(event->type, kFlutterKeyEventTypeDown);
1101 EXPECT_EQ(event->physical, kPhysicalNumLock);
1102 EXPECT_EQ(event->logical, kLogicalNumLock);
1103 EXPECT_STREQ(event->character,
"");
1104 EXPECT_EQ(event->synthesized,
true);
1105 EXPECT_EQ(event->callback,
nullptr);
1107 event = &results[2];
1108 EXPECT_EQ(event->type, kFlutterKeyEventTypeUp);
1109 EXPECT_EQ(event->physical, kPhysicalNumLock);
1110 EXPECT_EQ(event->logical, kLogicalNumLock);
1111 EXPECT_STREQ(event->character,
"");
1112 EXPECT_EQ(event->synthesized,
false);
1114 last_handled =
false;
1115 event->callback(
true, event->user_data);
1116 EXPECT_EQ(last_handled,
true);
1119 TEST(KeyboardKeyEmbedderHandlerTest,
1120 SynthesizeForDesyncToggledStateByItselfsDown) {
1121 TestKeystate key_state;
1122 std::vector<TestFlutterKeyEvent> results;
1123 TestFlutterKeyEvent* event;
1124 bool last_handled =
false;
1127 key_state.Set(VK_NUMLOCK,
false,
false);
1128 std::unique_ptr<KeyboardKeyEmbedderHandler> handler =
1129 std::make_unique<KeyboardKeyEmbedderHandler>(
1130 [&results](
const FlutterKeyEvent& event,
1134 key_state.Getter(), DefaultMapVkToScan);
1140 key_state.Set(VK_NUMLOCK,
true,
false);
1141 handler->KeyboardHook(
1142 VK_NUMLOCK, kScanCodeNumLock, WM_KEYDOWN, 0,
true,
false,
1143 [&last_handled](
bool handled) { last_handled = handled; });
1144 EXPECT_EQ(last_handled,
false);
1148 EXPECT_EQ(results.size(), 4);
1149 event = &results[0];
1150 EXPECT_EQ(event->type, kFlutterKeyEventTypeDown);
1151 EXPECT_EQ(event->physical, kPhysicalNumLock);
1152 EXPECT_EQ(event->logical, kLogicalNumLock);
1153 EXPECT_STREQ(event->character,
"");
1154 EXPECT_EQ(event->synthesized,
true);
1155 EXPECT_EQ(event->callback,
nullptr);
1157 event = &results[1];
1158 EXPECT_EQ(event->type, kFlutterKeyEventTypeUp);
1159 EXPECT_EQ(event->physical, kPhysicalNumLock);
1160 EXPECT_EQ(event->logical, kLogicalNumLock);
1161 EXPECT_STREQ(event->character,
"");
1162 EXPECT_EQ(event->synthesized,
true);
1163 EXPECT_EQ(event->callback,
nullptr);
1165 event = &results[2];
1166 EXPECT_EQ(event->type, kFlutterKeyEventTypeDown);
1167 EXPECT_EQ(event->physical, kPhysicalNumLock);
1168 EXPECT_EQ(event->logical, kLogicalNumLock);
1169 EXPECT_STREQ(event->character,
"");
1170 EXPECT_EQ(event->synthesized,
false);
1172 last_handled =
false;
1173 event->callback(
true, event->user_data);
1174 EXPECT_EQ(last_handled,
true);
1177 TEST(KeyboardKeyEmbedderHandlerTest, SynthesizeWithInitialTogglingState) {
1178 TestKeystate key_state;
1179 std::vector<TestFlutterKeyEvent> results;
1180 TestFlutterKeyEvent* event;
1181 bool last_handled =
false;
1184 key_state.Set(VK_NUMLOCK,
false,
true);
1186 std::unique_ptr<KeyboardKeyEmbedderHandler> handler =
1187 std::make_unique<KeyboardKeyEmbedderHandler>(
1188 [&results](
const FlutterKeyEvent& event,
1192 key_state.Getter(), DefaultMapVkToScan);
1195 key_state.Set(VK_NUMLOCK,
true,
false);
1196 handler->KeyboardHook(
1197 VK_NUMLOCK, kScanCodeNumLock, WM_KEYDOWN, 0,
true,
false,
1198 [&last_handled](
bool handled) { last_handled = handled; });
1199 EXPECT_EQ(last_handled,
false);
1200 EXPECT_EQ(results.size(), 1);
1201 event = &results[0];
1202 EXPECT_EQ(event->type, kFlutterKeyEventTypeDown);
1203 EXPECT_EQ(event->physical, kPhysicalNumLock);
1204 EXPECT_EQ(event->logical, kLogicalNumLock);
1205 EXPECT_STREQ(event->character,
"");
1206 EXPECT_EQ(event->synthesized,
false);
1208 event->callback(
true, event->user_data);
1209 EXPECT_EQ(last_handled,
true);
1213 TEST(KeyboardKeyEmbedderHandlerTest, SysKeyPress) {
1214 TestKeystate key_state;
1215 std::vector<TestFlutterKeyEvent> results;
1216 TestFlutterKeyEvent* event;
1217 bool last_handled =
false;
1219 std::unique_ptr<KeyboardKeyEmbedderHandler> handler =
1220 std::make_unique<KeyboardKeyEmbedderHandler>(
1221 [&results](
const FlutterKeyEvent& event,
1225 key_state.Getter(), DefaultMapVkToScan);
1228 key_state.Set(VK_LMENU,
true);
1229 handler->KeyboardHook(
1230 VK_LMENU, kScanCodeAltLeft, WM_SYSKEYDOWN, 0,
false,
false,
1231 [&last_handled](
bool handled) { last_handled = handled; });
1232 EXPECT_EQ(last_handled,
false);
1233 EXPECT_EQ(results.size(), 1);
1234 event = results.data();
1235 EXPECT_EQ(event->type, kFlutterKeyEventTypeDown);
1236 EXPECT_EQ(event->physical, kPhysicalAltLeft);
1237 EXPECT_EQ(event->logical, kLogicalAltLeft);
1238 EXPECT_STREQ(event->character,
"");
1239 EXPECT_EQ(event->synthesized,
false);
1241 event->callback(
true, event->user_data);
1242 EXPECT_EQ(last_handled,
true);
1246 key_state.Set(VK_LMENU,
false);
1247 handler->KeyboardHook(
1248 VK_LMENU, kScanCodeAltLeft, WM_SYSKEYUP, 0,
false,
true,
1249 [&last_handled](
bool handled) { last_handled = handled; });
1250 EXPECT_EQ(results.size(), 1);
1251 event = results.data();
1252 EXPECT_EQ(event->type, kFlutterKeyEventTypeUp);
1253 EXPECT_EQ(event->physical, kPhysicalAltLeft);
1254 EXPECT_EQ(event->logical, kLogicalAltLeft);
1255 EXPECT_STREQ(event->character,
"");
1256 EXPECT_EQ(event->synthesized,
false);
1257 event->callback(
false, event->user_data);