| Flutter Linux Embedder |

Classes | Functions | Variables
fl_key_embedder_responder_test.cc File Reference
`#include "flutter/shell/platform/linux/fl_key_embedder_responder.h"`
`#include "gtest/gtest.h"`
`#include "flutter/shell/platform/embedder/test_utils/key_codes.g.h"`
`#include "flutter/shell/platform/embedder/test_utils/proc_table_replacement.h"`
`#include "flutter/shell/platform/linux/fl_binary_messenger_private.h"`
`#include "flutter/shell/platform/linux/fl_engine_private.h"`
`#include "flutter/shell/platform/linux/testing/fl_test.h"`

Go to the source code of this file.

## Classes
struct | _FlKeyEmbedderCallRecord

## Functions
static void | g_ptr_array_clear (GPtrArray *array)
| G_DECLARE_FINAL_TYPE (FlKeyEmbedderCallRecord, fl_key_embedder_call_record, FL, KEY_EMBEDDER_CALL_RECORD, GObject)
| G_DEFINE_TYPE (FlKeyEmbedderCallRecord, fl_key_embedder_call_record, G_TYPE_OBJECT) static void fl_key_embedder_call_record_init(FlKeyEmbedderCallRecord *self)
static void | fl_key_embedder_call_record_dispose (GObject *object)
static void | fl_key_embedder_call_record_class_init (FlKeyEmbedderCallRecordClass *klass)
static FlKeyEmbedderCallRecord * | fl_key_embedder_call_record_new (const FlutterKeyEvent *event, FlutterKeyEventCallback callback, gpointer user_data)
static FlKeyEvent * | fl_key_event_new_by_mock (guint32 time_in_milliseconds, bool is_press, guint keyval, guint16 keycode, GdkModifierType state, gboolean is_modifier)
static void | verify_response_handled (bool handled, gpointer user_data)
static void | invoke_record_callback_and_verify (FlKeyEmbedderCallRecord *record, bool expected_handled, void *expected_user_data)
static void | record_calls (const FlutterKeyEvent *event, FlutterKeyEventCallback callback, void *callback_user_data, void *send_key_event_user_data)
static void | clear_g_call_records ()
| TEST (FlKeyEmbedderResponderTest, SendKeyEvent)
| TEST (FlKeyEmbedderResponderTest, UsesSpecifiedLogicalKey)
| TEST (FlKeyEmbedderResponderTest, PressShiftDuringLetterKeyTap)
| TEST (FlKeyEmbedderResponderTest, TapNumPadKeysBetweenNumLockEvents)
| TEST (FlKeyEmbedderResponderTest, ReleaseShiftKeyBetweenDigitKeyEvents)
| TEST (FlKeyEmbedderResponderTest, TapLetterKeysBetweenCapsLockEvents)
| TEST (FlKeyEmbedderResponderTest, TapLetterKeysBetweenCapsLockEventsReversed)
| TEST (FlKeyEmbedderResponderTest, TurnDuplicateDownEventsToRepeats)
| TEST (FlKeyEmbedderResponderTest, IgnoreAbruptUpEvent)
| TEST (FlKeyEmbedderResponderTest, SynthesizeForDesyncPressingStateOnSelfEvents)
| TEST (FlKeyEmbedderResponderTest, SynthesizeForDesyncPressingStateOnNonSelfEvents)
| TEST (FlKeyEmbedderResponderTest, SynthesizeForDesyncPressingStateOnRemappedEvents)
| TEST (FlKeyEmbedderResponderTest, SynthesizeForDesyncLockModeOnNonSelfEvents)
| TEST (FlKeyEmbedderResponderTest, SynthesizeForDesyncLockModeOnSelfEvents)
| TEST (FlKeyEmbedderResponderTest, SynthesizationOccursOnIgnoredEvents)
| TEST (FlKeyEmbedderResponderTest, HandlesShiftAltVersusGroupNext)
| TEST (FlKeyEmbedderResponderTest, HandlesShiftAltLeftIsMetaLeft)

## Variables
static gboolean | g_expected_handled
static gpointer | g_expected_user_data

## Function Documentation

## ◆ clear_g_call_records()

static void clear_g_call_records | ( |  | ) |
| static

Definition at line 162 of file fl_key_embedder_responder_test.cc.

162 {
163 g_ptr_array_free(g_call_records, TRUE);
164 g_call_records = nullptr;
165 }

References TRUE.

Referenced by TEST().

## ◆ fl_key_embedder_call_record_class_init()

static void fl_key_embedder_call_record_class_init | ( | FlKeyEmbedderCallRecordClass * | klass | ) |
| static

Definition at line 74 of file fl_key_embedder_responder_test.cc.

75 {
76 G_OBJECT_CLASS(klass)->dispose = fl_key_embedder_call_record_dispose;
77 }

References fl_key_embedder_call_record_dispose().

## ◆ fl_key_embedder_call_record_dispose()

static void fl_key_embedder_call_record_dispose | ( | GObject * | object | ) |
| static

Definition at line 62 of file fl_key_embedder_responder_test.cc.

62 {
63 g_return_if_fail(FL_IS_KEY_EMBEDDER_CALL_RECORD(object));
64
65 FlKeyEmbedderCallRecord* self = FL_KEY_EMBEDDER_CALL_RECORD(object);
66 if (self->event != nullptr) {
67 g_free(const_cast<char*>(self->event->character));
68 g_free(self->event);
69 }
70 G_OBJECT_CLASS(fl_key_embedder_call_record_parent_class)->dispose(object);
71 }

Referenced by fl_key_embedder_call_record_class_init().

## ◆ fl_key_embedder_call_record_new()

static FlKeyEmbedderCallRecord* fl_key_embedder_call_record_new | ( | const FlutterKeyEvent * | event,
|  | FlutterKeyEventCallback | callback,
|  | gpointer | user_data
| ) |  |
| static

Definition at line 79 of file fl_key_embedder_responder_test.cc.

82 {
83 g_return_val_if_fail(event != nullptr, nullptr);
84
85 FlKeyEmbedderCallRecord* self = FL_KEY_EMBEDDER_CALL_RECORD(
86 g_object_new(fl_key_embedder_call_record_get_type(), nullptr));
87
88 FlutterKeyEvent* clone_event = g_new(FlutterKeyEvent, 1);
89 *clone_event = *event;
90 if (event->character != nullptr) {
91 size_t character_length = strlen(event->character);
92 char* clone_character = g_new(char, character_length + 1);
93 strncpy(clone_character, event->character, character_length + 1);
94 clone_event->character = clone_character;
95 }
96 self->event = clone_event;
97 self->callback = callback;
98 self->user_data = user_data;
99
100 return self;
101 }

References callback, event, and user_data.

Referenced by record_calls().

## ◆ fl_key_event_new_by_mock()

static FlKeyEvent* fl_key_event_new_by_mock | ( | guint32 | time_in_milliseconds,
|  | bool | is_press,
|  | guint | keyval,
|  | guint16 | keycode,
|  | GdkModifierType | state,
|  | gboolean | is_modifier
| ) |  |
| static

Definition at line 115 of file fl_key_embedder_responder_test.cc.

120 {
121 _g_key_event.is_press = is_press;
122 _g_key_event.time = time_in_milliseconds;
123 _g_key_event.state = state;
124 _g_key_event.keyval = keyval;
125 _g_key_event.keycode = keycode;
126 _g_key_event.origin = nullptr;
127 return &_g_key_event;
128 }

References _FlKeyEvent::is_press, and state.

Referenced by TEST().

## ◆ G_DECLARE_FINAL_TYPE()

G_DECLARE_FINAL_TYPE | ( | FlKeyEmbedderCallRecord | ,
|  | fl_key_embedder_call_record | ,
|  | FL | ,
|  | KEY_EMBEDDER_CALL_RECORD | ,
|  | GObject |
| ) |  |

## ◆ G_DEFINE_TYPE()

G_DEFINE_TYPE | ( | FlKeyEmbedderCallRecord | ,
|  | fl_key_embedder_call_record | ,
|  | G_TYPE_OBJECT |
| ) |  |

Definition at line 55 of file fl_key_embedder_responder_test.cc.

59 {}

## ◆ g_ptr_array_clear()

static void g_ptr_array_clear | ( | GPtrArray * | array | ) |
| static

Definition at line 37 of file fl_key_embedder_responder_test.cc.

37 {
38 g_ptr_array_remove_range(array, 0, array->len);
39 }

Referenced by TEST().

## ◆ invoke_record_callback_and_verify()

static void invoke_record_callback_and_verify | ( | FlKeyEmbedderCallRecord * | record,
|  | bool | expected_handled,
|  | void * | expected_user_data
| ) |  |
| static

Definition at line 137 of file fl_key_embedder_responder_test.cc.

139 {
140 g_return_if_fail(record->callback != nullptr);
141 g_expected_handled = expected_handled;
142 g_expected_user_data = expected_user_data;
143 record->callback(expected_handled, record->user_data);
144 }

References expected_handled, g_expected_handled, and g_expected_user_data.

Referenced by TEST().

## ◆ record_calls()

static void record_calls | ( | const FlutterKeyEvent * | event,
|  | FlutterKeyEventCallback | callback,
|  | void * | callback_user_data,
|  | void * | send_key_event_user_data
| ) |  |
| static

Definition at line 150 of file fl_key_embedder_responder_test.cc.

153 {
154 GPtrArray* records_array =
155 reinterpret_cast<GPtrArray*>(send_key_event_user_data);
156 if (records_array != nullptr) {
157 g_ptr_array_add(records_array, fl_key_embedder_call_record_new(
158 event, callback, callback_user_data));
159 }
160 }

References callback, event, and fl_key_embedder_call_record_new().

Referenced by TEST().

## ◆ TEST() [1/17]

TEST | ( | FlKeyEmbedderResponderTest | ,
|  | HandlesShiftAltLeftIsMetaLeft |
| ) |  |

Definition at line 1757 of file fl_key_embedder_responder_test.cc.

1757 {
1758 EXPECT_EQ(g_call_records, nullptr);
1759 g_call_records = g_ptr_array_new_with_free_func(g_object_unref);
1760 FlKeyResponder* responder = FL_KEY_RESPONDER(
1761 fl_key_embedder_responder_new(record_calls, g_call_records));
1762
1763 g_expected_handled = true;
1764 guint32 now_time = 1;
1765 // A convenient shorthand to simulate events.
1766 auto send_key_event = [responder, &now_time](bool is_press, guint keyval,
1767 guint16 keycode,
1768 GdkModifierType state) {
1769 now_time += 1;
1770 int user_data = 123; // Arbitrary user data
1771 fl_key_responder_handle_event(
1772 responder,
1773 fl_key_event_new_by_mock(now_time, is_press, keyval, keycode, state,
1774 kIsModifier),
1775 verify_response_handled, &user_data);
1776 };
1777
1778 FlKeyEmbedderCallRecord* record;
1779
1780 // ShiftLeft + AltLeft
1781 send_key_event(kPress, GDK_KEY_Shift_L, kKeyCodeShiftLeft,
1782 GDK_MODIFIER_RESERVED_25_MASK);
1783 EXPECT_EQ(g_call_records->len, 1u);
1784 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
1785 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1786 EXPECT_EQ(record->event->physical, kPhysicalShiftLeft);
1787 EXPECT_EQ(record->event->logical, kLogicalShiftLeft);
1788 EXPECT_EQ(record->event->synthesized, false);
1789
1790 send_key_event(kPress, GDK_KEY_Meta_L, kKeyCodeAltLeft,
1791 static_cast<GdkModifierType>(GDK_SHIFT_MASK |
1792 GDK_MODIFIER_RESERVED_25_MASK));
1793 EXPECT_EQ(g_call_records->len, 2u);
1794 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 1));
1795 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1796 EXPECT_EQ(record->event->physical, kPhysicalMetaLeft);
1797 EXPECT_EQ(record->event->logical, kLogicalMetaLeft);
1798 EXPECT_EQ(record->event->synthesized, false);
1799
1800 send_key_event(kRelease, GDK_KEY_Meta_L, kKeyCodeAltLeft,
1801 static_cast<GdkModifierType>(GDK_MODIFIER_RESERVED_13_MASK |
1802 GDK_MODIFIER_RESERVED_25_MASK));
1803 send_key_event(kRelease, GDK_KEY_Shift_L, kKeyCodeShiftLeft,
1804 GDK_MODIFIER_RESERVED_25_MASK);
1805 g_ptr_array_clear(g_call_records);
1806
1807 // ShiftRight + AltLeft
1808 send_key_event(kPress, GDK_KEY_Shift_R, kKeyCodeShiftRight,
1809 GDK_MODIFIER_RESERVED_25_MASK);
1810 EXPECT_EQ(g_call_records->len, 1u);
1811 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
1812 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1813 EXPECT_EQ(record->event->physical, kPhysicalShiftRight);
1814 EXPECT_EQ(record->event->logical, kLogicalShiftRight);
1815 EXPECT_EQ(record->event->synthesized, false);
1816
1817 send_key_event(kPress, GDK_KEY_Meta_L, kKeyCodeAltLeft,
1818 static_cast<GdkModifierType>(GDK_SHIFT_MASK |
1819 GDK_MODIFIER_RESERVED_25_MASK));
1820 EXPECT_EQ(g_call_records->len, 2u);
1821 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 1));
1822 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1823 EXPECT_EQ(record->event->physical, kPhysicalMetaLeft);
1824 EXPECT_EQ(record->event->logical, kLogicalMetaLeft);
1825 EXPECT_EQ(record->event->synthesized, false);
1826
1827 clear_g_call_records();
1828 g_object_unref(responder);
1829 }

References clear_g_call_records(), fl_key_embedder_responder_new(), fl_key_event_new_by_mock(), fl_key_responder_handle_event(), g_expected_handled, g_ptr_array_clear(), record_calls(), send_key_event(), state, user_data, and verify_response_handled().

## ◆ TEST() [2/17]

TEST | ( | FlKeyEmbedderResponderTest | ,
|  | HandlesShiftAltVersusGroupNext |
| ) |  |

Definition at line 1648 of file fl_key_embedder_responder_test.cc.

1648 {
1649 EXPECT_EQ(g_call_records, nullptr);
1650 g_call_records = g_ptr_array_new_with_free_func(g_object_unref);
1651 FlKeyResponder* responder = FL_KEY_RESPONDER(
1652 fl_key_embedder_responder_new(record_calls, g_call_records));
1653
1654 g_expected_handled = true;
1655 guint32 now_time = 1;
1656 // A convenient shorthand to simulate events.
1657 auto send_key_event = [responder, &now_time](bool is_press, guint keyval,
1658 guint16 keycode,
1659 GdkModifierType state) {
1660 now_time += 1;
1661 int user_data = 123; // Arbitrary user data
1662 fl_key_responder_handle_event(
1663 responder,
1664 fl_key_event_new_by_mock(now_time, is_press, keyval, keycode, state,
1665 kIsModifier),
1666 verify_response_handled, &user_data);
1667 };
1668
1669 FlKeyEmbedderCallRecord* record;
1670
1671 send_key_event(kPress, GDK_KEY_Shift_L, kKeyCodeShiftLeft,
1672 GDK_MODIFIER_RESERVED_25_MASK);
1673 EXPECT_EQ(g_call_records->len, 1u);
1674 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
1675 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1676 EXPECT_EQ(record->event->physical, kPhysicalShiftLeft);
1677 EXPECT_EQ(record->event->logical, kLogicalShiftLeft);
1678 EXPECT_EQ(record->event->synthesized, false);
1679
1680 send_key_event(kPress, GDK_KEY_Meta_R, kKeyCodeAltRight,
1681 static_cast<GdkModifierType>(GDK_SHIFT_MASK |
1682 GDK_MODIFIER_RESERVED_25_MASK));
1683 EXPECT_EQ(g_call_records->len, 2u);
1684 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 1));
1685 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1686 EXPECT_EQ(record->event->physical, kPhysicalAltRight);
1687 EXPECT_EQ(record->event->logical, kLogicalMetaRight);
1688 EXPECT_EQ(record->event->synthesized, false);
1689
1690 send_key_event(kRelease, GDK_KEY_ISO_Next_Group, kKeyCodeShiftLeft,
1691 static_cast<GdkModifierType>(GDK_SHIFT_MASK | GDK_MOD1_MASK |
1692 GDK_MODIFIER_RESERVED_25_MASK));
1693 EXPECT_EQ(g_call_records->len, 5u);
1694 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 2));
1695 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1696 EXPECT_EQ(record->event->physical, kPhysicalAltLeft);
1697 EXPECT_EQ(record->event->logical, kLogicalAltLeft);
1698 EXPECT_EQ(record->event->synthesized, true);
1699
1700 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 3));
1701 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
1702 EXPECT_EQ(record->event->physical, kPhysicalAltRight);
1703 EXPECT_EQ(record->event->logical, kLogicalMetaRight);
1704 EXPECT_EQ(record->event->synthesized, true);
1705
1706 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 4));
1707 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
1708 EXPECT_EQ(record->event->physical, kPhysicalShiftLeft);
1709 EXPECT_EQ(record->event->logical, kLogicalShiftLeft);
1710 EXPECT_EQ(record->event->synthesized, false);
1711
1712 send_key_event(kPress, GDK_KEY_ISO_Next_Group, kKeyCodeShiftLeft,
1713 static_cast<GdkModifierType>(GDK_MOD1_MASK |
1714 GDK_MODIFIER_RESERVED_25_MASK));
1715 EXPECT_EQ(g_call_records->len, 6u);
1716 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 5));
1717 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1718 EXPECT_EQ(record->event->physical, kPhysicalShiftLeft);
1719 EXPECT_EQ(record->event->logical, kLogicalGroupNext);
1720 EXPECT_EQ(record->event->synthesized, false);
1721
1722 send_key_event(kRelease, GDK_KEY_ISO_Level3_Shift, kKeyCodeAltRight,
1723 static_cast<GdkModifierType>(GDK_MOD1_MASK |
1724 GDK_MODIFIER_RESERVED_13_MASK |
1725 GDK_MODIFIER_RESERVED_25_MASK));
1726 EXPECT_EQ(g_call_records->len, 7u);
1727 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 6));
1728 EXPECT_EQ(record->event->physical, 0u);
1729 EXPECT_EQ(record->event->logical, 0u);
1730
1731 send_key_event(kRelease, GDK_KEY_Shift_L, kKeyCodeShiftLeft,
1732 static_cast<GdkModifierType>(GDK_MODIFIER_RESERVED_13_MASK |
1733 GDK_MODIFIER_RESERVED_25_MASK));
1734 EXPECT_EQ(g_call_records->len, 9u);
1735 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 7));
1736 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
1737 EXPECT_EQ(record->event->physical, kPhysicalAltLeft);
1738 EXPECT_EQ(record->event->logical, kLogicalAltLeft);
1739 EXPECT_EQ(record->event->synthesized, true);
1740
1741 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 8));
1742 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
1743 EXPECT_EQ(record->event->physical, kPhysicalShiftLeft);
1744 EXPECT_EQ(record->event->logical, kLogicalGroupNext);
1745 EXPECT_EQ(record->event->synthesized, false);
1746
1747 clear_g_call_records();
1748 g_object_unref(responder);
1749 }

References clear_g_call_records(), fl_key_embedder_responder_new(), fl_key_event_new_by_mock(), fl_key_responder_handle_event(), g_expected_handled, record_calls(), send_key_event(), state, user_data, and verify_response_handled().

## ◆ TEST() [3/17]

TEST | ( | FlKeyEmbedderResponderTest | ,
|  | IgnoreAbruptUpEvent |
| ) |  |

Definition at line 1025 of file fl_key_embedder_responder_test.cc.

1025 {
1026 FlKeyEmbedderCallRecord* record;
1027
1028 EXPECT_EQ(g_call_records, nullptr);
1029 g_call_records = g_ptr_array_new_with_free_func(g_object_unref);
1030 FlKeyResponder* responder = FL_KEY_RESPONDER(
1031 fl_key_embedder_responder_new(record_calls, g_call_records));
1032 int user_data = 123; // Arbitrary user data
1033
1034 // Release KeyA before it was even pressed.
1035 g_expected_handled = true; // The empty event is always handled.
1036 fl_key_responder_handle_event(
1037 responder,
1038 fl_key_event_new_by_mock(103, kRelease, GDK_KEY_q, kKeyCodeKeyA,
1039 static_cast<GdkModifierType>(0), kIsNotModifier),
1040 verify_response_handled, &user_data);
1041
1042 EXPECT_EQ(g_call_records->len, 1u);
1043
1044 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
1045 EXPECT_EQ(record->event->physical, 0ull);
1046 EXPECT_EQ(record->event->logical, 0ull);
1047 EXPECT_STREQ(record->event->character, nullptr);
1048 EXPECT_EQ(record->event->synthesized, false);
1049 EXPECT_EQ(record->callback, nullptr);
1050
1051 clear_g_call_records();
1052 g_object_unref(responder);
1053 }

References clear_g_call_records(), fl_key_embedder_responder_new(), fl_key_event_new_by_mock(), fl_key_responder_handle_event(), g_expected_handled, record_calls(), user_data, and verify_response_handled().

## ◆ TEST() [4/17]

TEST | ( | FlKeyEmbedderResponderTest | ,
|  | PressShiftDuringLetterKeyTap |
| ) |  |

Definition at line 299 of file fl_key_embedder_responder_test.cc.

299 {
300 EXPECT_EQ(g_call_records, nullptr);
301 g_call_records = g_ptr_array_new_with_free_func(g_object_unref);
302 FlKeyResponder* responder = FL_KEY_RESPONDER(
303 fl_key_embedder_responder_new(record_calls, g_call_records));
304 int user_data = 123; // Arbitrary user data
305
306 FlKeyEmbedderCallRecord* record;
307
308 // Press shift right
309 fl_key_responder_handle_event(
310 responder,
311 fl_key_event_new_by_mock(101, kPress, GDK_KEY_Shift_R, kKeyCodeShiftRight,
312 static_cast<GdkModifierType>(0), kIsModifier),
313 verify_response_handled, &user_data);
314
315 EXPECT_EQ(g_call_records->len, 1u);
316 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
317 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
318 EXPECT_EQ(record->event->physical, kPhysicalShiftRight);
319 EXPECT_EQ(record->event->logical, kLogicalShiftRight);
320 EXPECT_STREQ(record->event->character, nullptr);
321 EXPECT_EQ(record->event->synthesized, false);
322
323 invoke_record_callback_and_verify(record, TRUE, &user_data);
324 g_ptr_array_clear(g_call_records);
325
326 // Press key A
327 fl_key_responder_handle_event(
328 responder,
329 fl_key_event_new_by_mock(102, kPress, GDK_KEY_A, kKeyCodeKeyA,
330 GDK_SHIFT_MASK, kIsNotModifier),
331 verify_response_handled, &user_data);
332
333 EXPECT_EQ(g_call_records->len, 1u);
334 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
335 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
336 EXPECT_EQ(record->event->physical, kPhysicalKeyA);
337 EXPECT_EQ(record->event->logical, kLogicalKeyA);
338 EXPECT_STREQ(record->event->character, "A");
339 EXPECT_EQ(record->event->synthesized, false);
340
341 invoke_record_callback_and_verify(record, TRUE, &user_data);
342 g_ptr_array_clear(g_call_records);
343
344 // Release shift right
345 fl_key_responder_handle_event(
346 responder,
347 fl_key_event_new_by_mock(103, kRelease, GDK_KEY_Shift_R,
348 kKeyCodeShiftRight, GDK_SHIFT_MASK, kIsModifier),
349 verify_response_handled, &user_data);
350
351 EXPECT_EQ(g_call_records->len, 1u);
352 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
353 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
354 EXPECT_EQ(record->event->physical, kPhysicalShiftRight);
355 EXPECT_EQ(record->event->logical, kLogicalShiftRight);
356 EXPECT_STREQ(record->event->character, nullptr);
357 EXPECT_EQ(record->event->synthesized, false);
358
359 invoke_record_callback_and_verify(record, TRUE, &user_data);
360 g_ptr_array_clear(g_call_records);
361
362 // Release key A
363 fl_key_responder_handle_event(
364 responder,
365 fl_key_event_new_by_mock(104, kRelease, GDK_KEY_A, kKeyCodeKeyA,
366 static_cast<GdkModifierType>(0), kIsNotModifier),
367 verify_response_handled, &user_data);
368
369 EXPECT_EQ(g_call_records->len, 1u);
370 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
371 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
372 EXPECT_EQ(record->event->physical, kPhysicalKeyA);
373 EXPECT_EQ(record->event->logical, kLogicalKeyA);
374 EXPECT_STREQ(record->event->character, nullptr);
375 EXPECT_EQ(record->event->synthesized, false);
376
377 invoke_record_callback_and_verify(record, TRUE, &user_data);
378 g_ptr_array_clear(g_call_records);
379
380 clear_g_call_records();
381 g_object_unref(responder);
382 }

References clear_g_call_records(), fl_key_embedder_responder_new(), fl_key_event_new_by_mock(), fl_key_responder_handle_event(), g_ptr_array_clear(), invoke_record_callback_and_verify(), record_calls(), TRUE, user_data, and verify_response_handled().

## ◆ TEST() [5/17]

TEST | ( | FlKeyEmbedderResponderTest | ,
|  | ReleaseShiftKeyBetweenDigitKeyEvents |
| ) |  |

Definition at line 553 of file fl_key_embedder_responder_test.cc.

553 {
554 EXPECT_EQ(g_call_records, nullptr);
555 g_call_records = g_ptr_array_new_with_free_func(g_object_unref);
556 FlKeyResponder* responder = FL_KEY_RESPONDER(
557 fl_key_embedder_responder_new(record_calls, g_call_records));
558 int user_data = 123; // Arbitrary user data
559
560 FlKeyEmbedderCallRecord* record;
561
562 GdkModifierType state = static_cast<GdkModifierType>(0);
563
564 // Press shift left
565 fl_key_responder_handle_event(
566 responder,
567 fl_key_event_new_by_mock(101, kPress, GDK_KEY_Shift_L, kKeyCodeShiftLeft,
568 state, kIsModifier),
569 verify_response_handled, &user_data);
570
571 EXPECT_EQ(g_call_records->len, 1u);
572 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
573 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
574 EXPECT_EQ(record->event->physical, kPhysicalShiftLeft);
575 EXPECT_EQ(record->event->logical, kLogicalShiftLeft);
576 EXPECT_STREQ(record->event->character, nullptr);
577 EXPECT_EQ(record->event->synthesized, false);
578
579 invoke_record_callback_and_verify(record, TRUE, &user_data);
580 g_ptr_array_clear(g_call_records);
581
582 state = GDK_SHIFT_MASK;
583
584 // Press digit 1, which is '!' on a US keyboard
585 fl_key_responder_handle_event(
586 responder,
587 fl_key_event_new_by_mock(102, kPress, GDK_KEY_exclam, kKeyCodeDigit1,
588 state, kIsNotModifier),
589 verify_response_handled, &user_data);
590
591 EXPECT_EQ(g_call_records->len, 1u);
592 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
593 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
594 EXPECT_EQ(record->event->physical, kPhysicalDigit1);
595 EXPECT_EQ(record->event->logical, kLogicalExclamation);
596 EXPECT_STREQ(record->event->character, "!");
597 EXPECT_EQ(record->event->synthesized, false);
598
599 invoke_record_callback_and_verify(record, TRUE, &user_data);
600 g_ptr_array_clear(g_call_records);
601
602 // Release shift
603 fl_key_responder_handle_event(
604 responder,
605 fl_key_event_new_by_mock(103, kRelease, GDK_KEY_Shift_L,
606 kKeyCodeShiftLeft, state, kIsModifier),
607 verify_response_handled, &user_data);
608
609 EXPECT_EQ(g_call_records->len, 1u);
610 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
611 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
612 EXPECT_EQ(record->event->physical, kPhysicalShiftLeft);
613 EXPECT_EQ(record->event->logical, kLogicalShiftLeft);
614 EXPECT_STREQ(record->event->character, nullptr);
615 EXPECT_EQ(record->event->synthesized, false);
616
617 invoke_record_callback_and_verify(record, TRUE, &user_data);
618 g_ptr_array_clear(g_call_records);
619
620 state = static_cast<GdkModifierType>(0);
621
622 // Release digit 1, which is "1" because shift has been released.
623 fl_key_responder_handle_event(
624 responder,
625 fl_key_event_new_by_mock(104, kRelease, GDK_KEY_1, kKeyCodeDigit1, state,
626 kIsNotModifier),
627 verify_response_handled, &user_data);
628
629 EXPECT_EQ(g_call_records->len, 1u);
630 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
631 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
632 EXPECT_EQ(record->event->physical, kPhysicalDigit1);
633 EXPECT_EQ(record->event->logical, kLogicalExclamation); // Important
634 EXPECT_STREQ(record->event->character, nullptr);
635 EXPECT_EQ(record->event->synthesized, false);
636
637 invoke_record_callback_and_verify(record, TRUE, &user_data);
638 g_ptr_array_clear(g_call_records);
639
640 clear_g_call_records();
641 g_object_unref(responder);
642 }

References clear_g_call_records(), fl_key_embedder_responder_new(), fl_key_event_new_by_mock(), fl_key_responder_handle_event(), g_ptr_array_clear(), invoke_record_callback_and_verify(), record_calls(), state, TRUE, user_data, and verify_response_handled().

## ◆ TEST() [6/17]

TEST | ( | FlKeyEmbedderResponderTest | ,
|  | SendKeyEvent |
| ) |  |

Definition at line 168 of file fl_key_embedder_responder_test.cc.

168 {
169 EXPECT_EQ(g_call_records, nullptr);
170 g_call_records = g_ptr_array_new_with_free_func(g_object_unref);
171 FlKeyResponder* responder = FL_KEY_RESPONDER(
172 fl_key_embedder_responder_new(record_calls, g_call_records));
173 int user_data = 123; // Arbitrary user data
174
175 FlKeyEmbedderCallRecord* record;
176
177 // On a QWERTY keyboard, press key Q (physically key A), and release.
178 // Key down
179 fl_key_responder_handle_event(
180 responder,
181 fl_key_event_new_by_mock(12345, kPress, GDK_KEY_a, kKeyCodeKeyA,
182 static_cast<GdkModifierType>(0), kIsNotModifier),
183 verify_response_handled, &user_data);
184
185 EXPECT_EQ(g_call_records->len, 1u);
186 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
187 EXPECT_EQ(record->event->struct_size, sizeof(FlutterKeyEvent));
188 EXPECT_EQ(record->event->timestamp, 12345000);
189 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
190 EXPECT_EQ(record->event->physical, kPhysicalKeyA);
191 EXPECT_EQ(record->event->logical, kLogicalKeyA);
192 EXPECT_STREQ(record->event->character, "a");
193 EXPECT_EQ(record->event->synthesized, false);
194
195 invoke_record_callback_and_verify(record, TRUE, &user_data);
196 g_ptr_array_clear(g_call_records);
197
198 // Key up
199 fl_key_responder_handle_event(
200 responder,
201 fl_key_event_new_by_mock(12346, kRelease, GDK_KEY_a, kKeyCodeKeyA,
202 static_cast<GdkModifierType>(0), kIsNotModifier),
203 verify_response_handled, &user_data);
204
205 EXPECT_EQ(g_call_records->len, 1u);
206 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
207 EXPECT_EQ(record->event->struct_size, sizeof(FlutterKeyEvent));
208 EXPECT_EQ(record->event->timestamp, 12346000);
209 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
210 EXPECT_EQ(record->event->physical, kPhysicalKeyA);
211 EXPECT_EQ(record->event->logical, kLogicalKeyA);
212 EXPECT_STREQ(record->event->character, nullptr);
213 EXPECT_EQ(record->event->synthesized, false);
214
215 invoke_record_callback_and_verify(record, FALSE, &user_data);
216 g_ptr_array_clear(g_call_records);
217
218 // On an AZERTY keyboard, press key Q (physically key A), and release.
219 // Key down
220 fl_key_responder_handle_event(
221 responder,
222 fl_key_event_new_by_mock(12347, kPress, GDK_KEY_q, kKeyCodeKeyA,
223 static_cast<GdkModifierType>(0), kIsNotModifier),
224 verify_response_handled, &user_data);
225
226 EXPECT_EQ(g_call_records->len, 1u);
227 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
228 EXPECT_EQ(record->event->struct_size, sizeof(FlutterKeyEvent));
229 EXPECT_EQ(record->event->timestamp, 12347000);
230 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
231 EXPECT_EQ(record->event->physical, kPhysicalKeyA);
232 EXPECT_EQ(record->event->logical, kLogicalKeyQ);
233 EXPECT_STREQ(record->event->character, "q");
234 EXPECT_EQ(record->event->synthesized, false);
235
236 invoke_record_callback_and_verify(record, TRUE, &user_data);
237 g_ptr_array_clear(g_call_records);
238
239 // Key up
240 fl_key_responder_handle_event(
241 responder,
242 fl_key_event_new_by_mock(12348, kRelease, GDK_KEY_q, kKeyCodeKeyA,
243 static_cast<GdkModifierType>(0), kIsNotModifier),
244 verify_response_handled, &user_data);
245
246 EXPECT_EQ(g_call_records->len, 1u);
247 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
248 EXPECT_EQ(record->event->struct_size, sizeof(FlutterKeyEvent));
249 EXPECT_EQ(record->event->timestamp, 12348000);
250 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
251 EXPECT_EQ(record->event->physical, kPhysicalKeyA);
252 EXPECT_EQ(record->event->logical, kLogicalKeyQ);
253 EXPECT_STREQ(record->event->character, nullptr);
254 EXPECT_EQ(record->event->synthesized, false);
255
256 invoke_record_callback_and_verify(record, FALSE, &user_data);
257 g_ptr_array_clear(g_call_records);
258
259 clear_g_call_records();
260 g_object_unref(responder);
261 }

References clear_g_call_records(), fl_key_embedder_responder_new(), fl_key_event_new_by_mock(), fl_key_responder_handle_event(), g_ptr_array_clear(), invoke_record_callback_and_verify(), record_calls(), TRUE, user_data, and verify_response_handled().

## ◆ TEST() [7/17]

TEST | ( | FlKeyEmbedderResponderTest | ,
|  | SynthesizationOccursOnIgnoredEvents |
| ) |  |

Definition at line 1594 of file fl_key_embedder_responder_test.cc.

1594 {
1595 EXPECT_EQ(g_call_records, nullptr);
1596 g_call_records = g_ptr_array_new_with_free_func(g_object_unref);
1597 FlKeyResponder* responder = FL_KEY_RESPONDER(
1598 fl_key_embedder_responder_new(record_calls, g_call_records));
1599 int user_data = 123; // Arbitrary user data
1600
1601 FlKeyEmbedderCallRecord* record;
1602
1603 // The NumLock is desynchronized by being enabled, and Control is pressed.
1604 GdkModifierType state =
1605 static_cast<GdkModifierType>(GDK_MOD2_MASK | GDK_CONTROL_MASK);
1606
1607 // Send a KeyA up event, which will be ignored.
1608 g_expected_handled = true; // The ignored event is always handled.
1609 fl_key_responder_handle_event(
1610 responder,
1611 fl_key_event_new_by_mock(101, kRelease, GDK_KEY_a, kKeyCodeKeyA, state,
1612 kIsNotModifier),
1613 verify_response_handled, &user_data);
1614
1615 EXPECT_EQ(g_call_records->len, 2u);
1616 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
1617 EXPECT_EQ(record->event->timestamp, 101000);
1618 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1619 EXPECT_EQ(record->event->physical, kPhysicalNumLock);
1620 EXPECT_EQ(record->event->logical, kLogicalNumLock);
1621 EXPECT_STREQ(record->event->character, nullptr);
1622 EXPECT_EQ(record->event->synthesized, true);
1623
1624 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 1));
1625 EXPECT_EQ(record->event->timestamp, 101000);
1626 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1627 EXPECT_EQ(record->event->physical, kPhysicalControlLeft);
1628 EXPECT_EQ(record->event->logical, kLogicalControlLeft);
1629 EXPECT_STREQ(record->event->character, nullptr);
1630 EXPECT_EQ(record->event->synthesized, true);
1631
1632 g_ptr_array_clear(g_call_records);
1633
1634 clear_g_call_records();
1635 g_object_unref(responder);
1636 }

References clear_g_call_records(), fl_key_embedder_responder_new(), fl_key_event_new_by_mock(), fl_key_responder_handle_event(), g_expected_handled, g_ptr_array_clear(), record_calls(), state, user_data, and verify_response_handled().

## ◆ TEST() [8/17]

TEST | ( | FlKeyEmbedderResponderTest | ,
|  | SynthesizeForDesyncLockModeOnNonSelfEvents |
| ) |  |

Definition at line 1387 of file fl_key_embedder_responder_test.cc.

1387 {
1388 EXPECT_EQ(g_call_records, nullptr);
1389 g_call_records = g_ptr_array_new_with_free_func(g_object_unref);
1390 FlKeyResponder* responder = FL_KEY_RESPONDER(
1391 fl_key_embedder_responder_new(record_calls, g_call_records));
1392 int user_data = 123; // Arbitrary user data
1393
1394 FlKeyEmbedderCallRecord* record;
1395
1396 // The NumLock is desynchronized by being enabled.
1397 GdkModifierType state = GDK_MOD2_MASK;
1398
1399 // Send a normal event
1400 fl_key_responder_handle_event(
1401 responder,
1402 fl_key_event_new_by_mock(101, kPress, GDK_KEY_a, kKeyCodeKeyA, state,
1403 kIsNotModifier),
1404 verify_response_handled, &user_data);
1405
1406 EXPECT_EQ(g_call_records->len, 2u);
1407 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
1408 EXPECT_EQ(record->event->timestamp, 101000);
1409 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1410 EXPECT_EQ(record->event->physical, kPhysicalNumLock);
1411 EXPECT_EQ(record->event->logical, kLogicalNumLock);
1412 EXPECT_STREQ(record->event->character, nullptr);
1413 EXPECT_EQ(record->event->synthesized, true);
1414
1415 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 1));
1416 EXPECT_EQ(record->event->timestamp, 101000);
1417 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1418 EXPECT_EQ(record->event->physical, kPhysicalKeyA);
1419 EXPECT_EQ(record->event->logical, kLogicalKeyA);
1420 EXPECT_STREQ(record->event->character, "a");
1421 EXPECT_EQ(record->event->synthesized, false);
1422
1423 invoke_record_callback_and_verify(record, TRUE, &user_data);
1424 g_ptr_array_clear(g_call_records);
1425
1426 // The NumLock is desynchronized by being disabled.
1427 state = static_cast<GdkModifierType>(0);
1428
1429 // Release key A
1430 fl_key_responder_handle_event(
1431 responder,
1432 fl_key_event_new_by_mock(102, kRelease, GDK_KEY_A, kKeyCodeKeyA, state,
1433 kIsNotModifier),
1434 verify_response_handled, &user_data);
1435
1436 EXPECT_EQ(g_call_records->len, 4u);
1437 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
1438 EXPECT_EQ(record->event->timestamp, 102000);
1439 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
1440 EXPECT_EQ(record->event->physical, kPhysicalNumLock);
1441 EXPECT_EQ(record->event->logical, kLogicalNumLock);
1442 EXPECT_STREQ(record->event->character, nullptr);
1443 EXPECT_EQ(record->event->synthesized, true);
1444
1445 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 1));
1446 EXPECT_EQ(record->event->timestamp, 102000);
1447 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1448 EXPECT_EQ(record->event->physical, kPhysicalNumLock);
1449 EXPECT_EQ(record->event->logical, kLogicalNumLock);
1450 EXPECT_STREQ(record->event->character, nullptr);
1451 EXPECT_EQ(record->event->synthesized, true);
1452
1453 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 2));
1454 EXPECT_EQ(record->event->timestamp, 102000);
1455 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
1456 EXPECT_EQ(record->event->physical, kPhysicalNumLock);
1457 EXPECT_EQ(record->event->logical, kLogicalNumLock);
1458 EXPECT_STREQ(record->event->character, nullptr);
1459 EXPECT_EQ(record->event->synthesized, true);
1460
1461 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 3));
1462 EXPECT_EQ(record->event->timestamp, 102000);
1463 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
1464 EXPECT_EQ(record->event->physical, kPhysicalKeyA);
1465 EXPECT_EQ(record->event->logical, kLogicalKeyA);
1466 EXPECT_STREQ(record->event->character, nullptr);
1467 EXPECT_EQ(record->event->synthesized, false);
1468
1469 invoke_record_callback_and_verify(record, TRUE, &user_data);
1470 g_ptr_array_clear(g_call_records);
1471
1472 // Release NumLock. Since the previous event should have synthesized NumLock
1473 // to be released, this should result in only an empty event.
1474 g_expected_handled = true;
1475 fl_key_responder_handle_event(
1476 responder,
1477 fl_key_event_new_by_mock(103, kRelease, GDK_KEY_Num_Lock, kKeyCodeNumLock,
1478 state, kIsModifier),
1479 verify_response_handled, &user_data);
1480
1481 EXPECT_EQ(g_call_records->len, 1u);
1482 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
1483 EXPECT_EQ(record->event->physical, 0ull);
1484 EXPECT_EQ(record->event->logical, 0ull);
1485 EXPECT_STREQ(record->event->character, nullptr);
1486 EXPECT_EQ(record->event->synthesized, false);
1487 EXPECT_EQ(record->callback, nullptr);
1488
1489 clear_g_call_records();
1490 g_object_unref(responder);
1491 }

References clear_g_call_records(), fl_key_embedder_responder_new(), fl_key_event_new_by_mock(), fl_key_responder_handle_event(), g_expected_handled, g_ptr_array_clear(), invoke_record_callback_and_verify(), record_calls(), state, TRUE, user_data, and verify_response_handled().

## ◆ TEST() [9/17]

TEST | ( | FlKeyEmbedderResponderTest | ,
|  | SynthesizeForDesyncLockModeOnSelfEvents |
| ) |  |

Definition at line 1495 of file fl_key_embedder_responder_test.cc.

1495 {
1496 EXPECT_EQ(g_call_records, nullptr);
1497 g_call_records = g_ptr_array_new_with_free_func(g_object_unref);
1498 FlKeyResponder* responder = FL_KEY_RESPONDER(
1499 fl_key_embedder_responder_new(record_calls, g_call_records));
1500 int user_data = 123; // Arbitrary user data
1501
1502 FlKeyEmbedderCallRecord* record;
1503
1504 // The NumLock is desynchronized by being enabled.
1505 GdkModifierType state = GDK_MOD2_MASK;
1506
1507 // NumLock down
1508 fl_key_responder_handle_event(
1509 responder,
1510 fl_key_event_new_by_mock(101, kPress, GDK_KEY_Num_Lock, kKeyCodeNumLock,
1511 state, kIsModifier),
1512 verify_response_handled, &user_data);
1513
1514 EXPECT_EQ(g_call_records->len, 3u);
1515 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
1516 EXPECT_EQ(record->event->timestamp, 101000);
1517 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1518 EXPECT_EQ(record->event->physical, kPhysicalNumLock);
1519 EXPECT_EQ(record->event->logical, kLogicalNumLock);
1520 EXPECT_STREQ(record->event->character, nullptr);
1521 EXPECT_EQ(record->event->synthesized, true);
1522
1523 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 1));
1524 EXPECT_EQ(record->event->timestamp, 101000);
1525 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
1526 EXPECT_EQ(record->event->physical, kPhysicalNumLock);
1527 EXPECT_EQ(record->event->logical, kLogicalNumLock);
1528 EXPECT_STREQ(record->event->character, nullptr);
1529 EXPECT_EQ(record->event->synthesized, true);
1530
1531 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 2));
1532 EXPECT_EQ(record->event->timestamp, 101000);
1533 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1534 EXPECT_EQ(record->event->physical, kPhysicalNumLock);
1535 EXPECT_EQ(record->event->logical, kLogicalNumLock);
1536 EXPECT_STREQ(record->event->character, nullptr);
1537 EXPECT_EQ(record->event->synthesized, false);
1538
1539 invoke_record_callback_and_verify(record, TRUE, &user_data);
1540 g_ptr_array_clear(g_call_records);
1541
1542 // The NumLock is desynchronized by being enabled in a press event.
1543 state = GDK_MOD2_MASK;
1544
1545 // NumLock up
1546 fl_key_responder_handle_event(
1547 responder,
1548 fl_key_event_new_by_mock(102, kPress, GDK_KEY_Num_Lock, kKeyCodeNumLock,
1549 state, kIsModifier),
1550 verify_response_handled, &user_data);
1551
1552 EXPECT_EQ(g_call_records->len, 4u);
1553 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
1554 EXPECT_EQ(record->event->timestamp, 102000);
1555 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
1556 EXPECT_EQ(record->event->physical, kPhysicalNumLock);
1557 EXPECT_EQ(record->event->logical, kLogicalNumLock);
1558 EXPECT_STREQ(record->event->character, nullptr);
1559 EXPECT_EQ(record->event->synthesized, true);
1560
1561 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 1));
1562 EXPECT_EQ(record->event->timestamp, 102000);
1563 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1564 EXPECT_EQ(record->event->physical, kPhysicalNumLock);
1565 EXPECT_EQ(record->event->logical, kLogicalNumLock);
1566 EXPECT_STREQ(record->event->character, nullptr);
1567 EXPECT_EQ(record->event->synthesized, true);
1568
1569 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 2));
1570 EXPECT_EQ(record->event->timestamp, 102000);
1571 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
1572 EXPECT_EQ(record->event->physical, kPhysicalNumLock);
1573 EXPECT_EQ(record->event->logical, kLogicalNumLock);
1574 EXPECT_STREQ(record->event->character, nullptr);
1575 EXPECT_EQ(record->event->synthesized, true);
1576
1577 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 3));
1578 EXPECT_EQ(record->event->timestamp, 102000);
1579 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1580 EXPECT_EQ(record->event->physical, kPhysicalNumLock);
1581 EXPECT_EQ(record->event->logical, kLogicalNumLock);
1582 EXPECT_STREQ(record->event->character, nullptr);
1583 EXPECT_EQ(record->event->synthesized, false);
1584
1585 invoke_record_callback_and_verify(record, TRUE, &user_data);
1586 g_ptr_array_clear(g_call_records);
1587
1588 clear_g_call_records();
1589 g_object_unref(responder);
1590 }

References clear_g_call_records(), fl_key_embedder_responder_new(), fl_key_event_new_by_mock(), fl_key_responder_handle_event(), g_ptr_array_clear(), invoke_record_callback_and_verify(), record_calls(), state, TRUE, user_data, and verify_response_handled().

## ◆ TEST() [10/17]

TEST | ( | FlKeyEmbedderResponderTest | ,
|  | SynthesizeForDesyncPressingStateOnNonSelfEvents |
| ) |  |

Definition at line 1187 of file fl_key_embedder_responder_test.cc.

1188 {
1189 EXPECT_EQ(g_call_records, nullptr);
1190 g_call_records = g_ptr_array_new_with_free_func(g_object_unref);
1191 FlKeyResponder* responder = FL_KEY_RESPONDER(
1192 fl_key_embedder_responder_new(record_calls, g_call_records));
1193 int user_data = 123; // Arbitrary user data
1194
1195 FlKeyEmbedderCallRecord* record;
1196
1197 // A key down of control left is missed.
1198 GdkModifierType state = GDK_CONTROL_MASK;
1199
1200 // Send a normal event (KeyA down)
1201 fl_key_responder_handle_event(
1202 responder,
1203 fl_key_event_new_by_mock(101, kPress, GDK_KEY_a, kKeyCodeKeyA, state,
1204 kIsNotModifier),
1205 verify_response_handled, &user_data);
1206
1207 EXPECT_EQ(g_call_records->len, 2u);
1208 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
1209 EXPECT_EQ(record->event->timestamp, 101000);
1210 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1211 EXPECT_EQ(record->event->physical, kPhysicalControlLeft);
1212 EXPECT_EQ(record->event->logical, kLogicalControlLeft);
1213 EXPECT_STREQ(record->event->character, nullptr);
1214 EXPECT_EQ(record->event->synthesized, true);
1215
1216 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 1));
1217 EXPECT_EQ(record->event->timestamp, 101000);
1218 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1219 EXPECT_EQ(record->event->physical, kPhysicalKeyA);
1220 EXPECT_EQ(record->event->logical, kLogicalKeyA);
1221 EXPECT_STREQ(record->event->character, "a");
1222 EXPECT_EQ(record->event->synthesized, false);
1223
1224 invoke_record_callback_and_verify(record, TRUE, &user_data);
1225 g_ptr_array_clear(g_call_records);
1226
1227 // A key up of control left is missed.
1228 state = static_cast<GdkModifierType>(0);
1229
1230 // Send a normal event (KeyA up)
1231 fl_key_responder_handle_event(
1232 responder,
1233 fl_key_event_new_by_mock(102, kRelease, GDK_KEY_A, kKeyCodeKeyA, state,
1234 kIsNotModifier),
1235 verify_response_handled, &user_data);
1236
1237 EXPECT_EQ(g_call_records->len, 2u);
1238 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
1239 EXPECT_EQ(record->event->timestamp, 102000);
1240 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
1241 EXPECT_EQ(record->event->physical, kPhysicalControlLeft);
1242 EXPECT_EQ(record->event->logical, kLogicalControlLeft);
1243 EXPECT_STREQ(record->event->character, nullptr);
1244 EXPECT_EQ(record->event->synthesized, true);
1245
1246 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 1));
1247 EXPECT_EQ(record->event->timestamp, 102000);
1248 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
1249 EXPECT_EQ(record->event->physical, kPhysicalKeyA);
1250 EXPECT_EQ(record->event->logical, kLogicalKeyA);
1251 EXPECT_STREQ(record->event->character, nullptr);
1252 EXPECT_EQ(record->event->synthesized, false);
1253
1254 invoke_record_callback_and_verify(record, TRUE, &user_data);
1255 g_ptr_array_clear(g_call_records);
1256
1257 // Test non-default key mapping.
1258
1259 // Press a key with physical CapsLock and logical ControlLeft.
1260 state = static_cast<GdkModifierType>(0);
1261
1262 fl_key_responder_handle_event(
1263 responder,
1264 fl_key_event_new_by_mock(101, kPress, GDK_KEY_Control_L, kKeyCodeCapsLock,
1265 state, kIsModifier),
1266 verify_response_handled, &user_data);
1267
1268 EXPECT_EQ(g_call_records->len, 1u);
1269 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
1270 EXPECT_EQ(record->event->timestamp, 101000);
1271 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1272 EXPECT_EQ(record->event->physical, kPhysicalCapsLock);
1273 EXPECT_EQ(record->event->logical, kLogicalControlLeft);
1274 EXPECT_STREQ(record->event->character, nullptr);
1275 EXPECT_EQ(record->event->synthesized, false);
1276
1277 invoke_record_callback_and_verify(record, TRUE, &user_data);
1278 g_ptr_array_clear(g_call_records);
1279
1280 // The key up of the control left press is missed.
1281 state = static_cast<GdkModifierType>(0);
1282
1283 // Send a normal event (KeyA down).
1284 fl_key_responder_handle_event(
1285 responder,
1286 fl_key_event_new_by_mock(102, kPress, GDK_KEY_A, kKeyCodeKeyA, state,
1287 kIsNotModifier),
1288 verify_response_handled, &user_data);
1289
1290 // The synthesized event should have physical CapsLock and logical
1291 // ControlLeft.
1292 EXPECT_EQ(g_call_records->len, 2u);
1293 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
1294 EXPECT_EQ(record->event->timestamp, 102000);
1295 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
1296 EXPECT_EQ(record->event->physical, kPhysicalCapsLock);
1297 EXPECT_EQ(record->event->logical, kLogicalControlLeft);
1298 EXPECT_STREQ(record->event->character, nullptr);
1299 EXPECT_EQ(record->event->synthesized, true);
1300
1301 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 1));
1302 EXPECT_EQ(record->event->timestamp, 102000);
1303 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1304 EXPECT_EQ(record->event->physical, kPhysicalKeyA);
1305 EXPECT_EQ(record->event->logical, kLogicalKeyA);
1306 EXPECT_STREQ(record->event->character, "A");
1307 EXPECT_EQ(record->event->synthesized, false);
1308
1309 invoke_record_callback_and_verify(record, TRUE, &user_data);
1310 g_ptr_array_clear(g_call_records);
1311
1312 clear_g_call_records();
1313 g_object_unref(responder);
1314 }

References clear_g_call_records(), fl_key_embedder_responder_new(), fl_key_event_new_by_mock(), fl_key_responder_handle_event(), g_ptr_array_clear(), invoke_record_callback_and_verify(), record_calls(), state, TRUE, user_data, and verify_response_handled().

## ◆ TEST() [11/17]

TEST | ( | FlKeyEmbedderResponderTest | ,
|  | SynthesizeForDesyncPressingStateOnRemappedEvents |
| ) |  |

Definition at line 1318 of file fl_key_embedder_responder_test.cc.

1319 {
1320 EXPECT_EQ(g_call_records, nullptr);
1321 g_call_records = g_ptr_array_new_with_free_func(g_object_unref);
1322 FlKeyResponder* responder = FL_KEY_RESPONDER(
1323 fl_key_embedder_responder_new(record_calls, g_call_records));
1324 int user_data = 123; // Arbitrary user data
1325
1326 FlKeyEmbedderCallRecord* record;
1327
1328 // Press a key with physical CapsLock and logical ControlLeft.
1329 GdkModifierType state = static_cast<GdkModifierType>(0);
1330
1331 fl_key_responder_handle_event(
1332 responder,
1333 fl_key_event_new_by_mock(101, kPress, GDK_KEY_Control_L, kKeyCodeCapsLock,
1334 state, kIsModifier),
1335 verify_response_handled, &user_data);
1336
1337 EXPECT_EQ(g_call_records->len, 1u);
1338 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
1339 EXPECT_EQ(record->event->timestamp, 101000);
1340 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1341 EXPECT_EQ(record->event->physical, kPhysicalCapsLock);
1342 EXPECT_EQ(record->event->logical, kLogicalControlLeft);
1343 EXPECT_STREQ(record->event->character, nullptr);
1344 EXPECT_EQ(record->event->synthesized, false);
1345
1346 invoke_record_callback_and_verify(record, TRUE, &user_data);
1347 g_ptr_array_clear(g_call_records);
1348
1349 // The key up of the control left press is missed.
1350 state = static_cast<GdkModifierType>(0);
1351
1352 // Send a normal event (KeyA down).
1353 fl_key_responder_handle_event(
1354 responder,
1355 fl_key_event_new_by_mock(102, kPress, GDK_KEY_A, kKeyCodeKeyA, state,
1356 kIsNotModifier),
1357 verify_response_handled, &user_data);
1358
1359 // The synthesized event should have physical CapsLock and logical
1360 // ControlLeft.
1361 EXPECT_EQ(g_call_records->len, 2u);
1362 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
1363 EXPECT_EQ(record->event->timestamp, 102000);
1364 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
1365 EXPECT_EQ(record->event->physical, kPhysicalCapsLock);
1366 EXPECT_EQ(record->event->logical, kLogicalControlLeft);
1367 EXPECT_STREQ(record->event->character, nullptr);
1368 EXPECT_EQ(record->event->synthesized, true);
1369
1370 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 1));
1371 EXPECT_EQ(record->event->timestamp, 102000);
1372 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1373 EXPECT_EQ(record->event->physical, kPhysicalKeyA);
1374 EXPECT_EQ(record->event->logical, kLogicalKeyA);
1375 EXPECT_STREQ(record->event->character, "A");
1376 EXPECT_EQ(record->event->synthesized, false);
1377
1378 invoke_record_callback_and_verify(record, TRUE, &user_data);
1379 g_ptr_array_clear(g_call_records);
1380
1381 clear_g_call_records();
1382 g_object_unref(responder);
1383 }

References clear_g_call_records(), fl_key_embedder_responder_new(), fl_key_event_new_by_mock(), fl_key_responder_handle_event(), g_ptr_array_clear(), invoke_record_callback_and_verify(), record_calls(), state, TRUE, user_data, and verify_response_handled().

## ◆ TEST() [12/17]

TEST | ( | FlKeyEmbedderResponderTest | ,
|  | SynthesizeForDesyncPressingStateOnSelfEvents |
| ) |  |

Definition at line 1057 of file fl_key_embedder_responder_test.cc.

1057 {
1058 EXPECT_EQ(g_call_records, nullptr);
1059 g_call_records = g_ptr_array_new_with_free_func(g_object_unref);
1060 FlKeyResponder* responder = FL_KEY_RESPONDER(
1061 fl_key_embedder_responder_new(record_calls, g_call_records));
1062 int user_data = 123; // Arbitrary user data
1063
1064 FlKeyEmbedderCallRecord* record;
1065
1066 // Test 1: synthesize key down.
1067
1068 // A key down of control left is missed.
1069 GdkModifierType state = GDK_CONTROL_MASK;
1070
1071 // Send a ControlLeft up
1072 fl_key_responder_handle_event(
1073 responder,
1074 fl_key_event_new_by_mock(101, kRelease, GDK_KEY_Control_L,
1075 kKeyCodeControlLeft, state, kIsModifier),
1076 verify_response_handled, &user_data);
1077
1078 EXPECT_EQ(g_call_records->len, 2u);
1079 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
1080 EXPECT_EQ(record->event->timestamp, 101000);
1081 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1082 EXPECT_EQ(record->event->physical, kPhysicalControlLeft);
1083 EXPECT_EQ(record->event->logical, kLogicalControlLeft);
1084 EXPECT_STREQ(record->event->character, nullptr);
1085 EXPECT_EQ(record->event->synthesized, true);
1086
1087 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 1));
1088 EXPECT_EQ(record->event->timestamp, 101000);
1089 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
1090 EXPECT_EQ(record->event->physical, kPhysicalControlLeft);
1091 EXPECT_EQ(record->event->logical, kLogicalControlLeft);
1092 EXPECT_STREQ(record->event->character, nullptr);
1093 EXPECT_EQ(record->event->synthesized, false);
1094
1095 invoke_record_callback_and_verify(record, TRUE, &user_data);
1096 g_ptr_array_clear(g_call_records);
1097
1098 // Test 2: synthesize key up.
1099
1100 // Send a ControlLeft down.
1101 state = static_cast<GdkModifierType>(0);
1102 fl_key_responder_handle_event(
1103 responder,
1104 fl_key_event_new_by_mock(102, kPress, GDK_KEY_Control_L,
1105 kKeyCodeControlLeft, state, kIsModifier),
1106 verify_response_handled, &user_data);
1107 EXPECT_EQ(g_call_records->len, 1u);
1108 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
1109 invoke_record_callback_and_verify(record, TRUE, &user_data);
1110 g_ptr_array_clear(g_call_records);
1111
1112 // A key up of control left is missed.
1113 state = static_cast<GdkModifierType>(0);
1114
1115 // Send another ControlLeft down
1116 fl_key_responder_handle_event(
1117 responder,
1118 fl_key_event_new_by_mock(103, kPress, GDK_KEY_Control_L,
1119 kKeyCodeControlLeft, state, kIsModifier),
1120 verify_response_handled, &user_data);
1121
1122 EXPECT_EQ(g_call_records->len, 2u);
1123 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
1124 EXPECT_EQ(record->event->timestamp, 103000);
1125 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
1126 EXPECT_EQ(record->event->physical, kPhysicalControlLeft);
1127 EXPECT_EQ(record->event->logical, kLogicalControlLeft);
1128 EXPECT_STREQ(record->event->character, nullptr);
1129 EXPECT_EQ(record->event->synthesized, true);
1130
1131 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 1));
1132 EXPECT_EQ(record->event->timestamp, 103000);
1133 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1134 EXPECT_EQ(record->event->physical, kPhysicalControlLeft);
1135 EXPECT_EQ(record->event->logical, kLogicalControlLeft);
1136 EXPECT_STREQ(record->event->character, nullptr);
1137 EXPECT_EQ(record->event->synthesized, false);
1138
1139 invoke_record_callback_and_verify(record, TRUE, &user_data);
1140 g_ptr_array_clear(g_call_records);
1141
1142 // Send a ControlLeft up to clear up state.
1143 state = GDK_CONTROL_MASK;
1144 fl_key_responder_handle_event(
1145 responder,
1146 fl_key_event_new_by_mock(104, kRelease, GDK_KEY_Control_L,
1147 kKeyCodeControlLeft, state, kIsModifier),
1148 verify_response_handled, &user_data);
1149 EXPECT_EQ(g_call_records->len, 1u);
1150 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
1151 invoke_record_callback_and_verify(record, TRUE, &user_data);
1152 g_ptr_array_clear(g_call_records);
1153
1154 // Test 3: synthesize by right modifier.
1155
1156 // A key down of control right is missed.
1157 state = GDK_CONTROL_MASK;
1158
1159 // Send a ControlRight up.
1160 fl_key_responder_handle_event(
1161 responder,
1162 fl_key_event_new_by_mock(105, kRelease, GDK_KEY_Control_R,
1163 kKeyCodeControlRight, state, kIsModifier),
1164 verify_response_handled, &user_data);
1165
1166 // A ControlLeft down is synthesized, with an empty event.
1167 // Reason: The ControlLeft down is synthesized to synchronize the state
1168 // showing Control as pressed. The ControlRight event is ignored because
1169 // the event is considered a duplicate up event.
1170 EXPECT_EQ(g_call_records->len, 1u);
1171 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
1172 EXPECT_EQ(record->event->timestamp, 105000);
1173 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
1174 EXPECT_EQ(record->event->physical, kPhysicalControlLeft);
1175 EXPECT_EQ(record->event->logical, kLogicalControlLeft);
1176 EXPECT_STREQ(record->event->character, nullptr);
1177 EXPECT_EQ(record->event->synthesized, true);
1178
1179 g_ptr_array_clear(g_call_records);
1180
1181 clear_g_call_records();
1182 g_object_unref(responder);
1183 }

References clear_g_call_records(), fl_key_embedder_responder_new(), fl_key_event_new_by_mock(), fl_key_responder_handle_event(), g_ptr_array_clear(), invoke_record_callback_and_verify(), record_calls(), state, TRUE, user_data, and verify_response_handled().

## ◆ TEST() [13/17]

TEST | ( | FlKeyEmbedderResponderTest | ,
|  | TapLetterKeysBetweenCapsLockEvents |
| ) |  |

Definition at line 648 of file fl_key_embedder_responder_test.cc.

648 {
649 EXPECT_EQ(g_call_records, nullptr);
650 g_call_records = g_ptr_array_new_with_free_func(g_object_unref);
651 FlKeyResponder* responder = FL_KEY_RESPONDER(
652 fl_key_embedder_responder_new(record_calls, g_call_records));
653 int user_data = 123; // Arbitrary user data
654
655 FlKeyEmbedderCallRecord* record;
656
657 // Press CapsLock (stage 0 -> 1)
658 fl_key_responder_handle_event(
659 responder,
660 fl_key_event_new_by_mock(101, kPress, GDK_KEY_Caps_Lock, kKeyCodeCapsLock,
661 static_cast<GdkModifierType>(0), kIsModifier),
662 verify_response_handled, &user_data);
663
664 EXPECT_EQ(g_call_records->len, 1u);
665 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
666 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
667 EXPECT_EQ(record->event->physical, kPhysicalCapsLock);
668 EXPECT_EQ(record->event->logical, kLogicalCapsLock);
669 EXPECT_STREQ(record->event->character, nullptr);
670 EXPECT_EQ(record->event->synthesized, false);
671
672 invoke_record_callback_and_verify(record, TRUE, &user_data);
673 g_ptr_array_clear(g_call_records);
674
675 // Press key A (stage 1)
676 fl_key_responder_handle_event(
677 responder,
678 fl_key_event_new_by_mock(102, kPress, GDK_KEY_A, kKeyCodeKeyA,
679 GDK_LOCK_MASK, kIsNotModifier),
680 verify_response_handled, &user_data);
681
682 EXPECT_EQ(g_call_records->len, 1u);
683 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
684 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
685 EXPECT_EQ(record->event->physical, kPhysicalKeyA);
686 EXPECT_EQ(record->event->logical, kLogicalKeyA);
687 EXPECT_STREQ(record->event->character, "A");
688 EXPECT_EQ(record->event->synthesized, false);
689
690 invoke_record_callback_and_verify(record, TRUE, &user_data);
691 g_ptr_array_clear(g_call_records);
692
693 // Release CapsLock (stage 1 -> 2)
694 fl_key_responder_handle_event(
695 responder,
696 fl_key_event_new_by_mock(103, kRelease, GDK_KEY_Caps_Lock,
697 kKeyCodeCapsLock, GDK_LOCK_MASK, kIsModifier),
698 verify_response_handled, &user_data);
699
700 EXPECT_EQ(g_call_records->len, 1u);
701 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
702 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
703 EXPECT_EQ(record->event->physical, kPhysicalCapsLock);
704 EXPECT_EQ(record->event->logical, kLogicalCapsLock);
705 EXPECT_STREQ(record->event->character, nullptr);
706 EXPECT_EQ(record->event->synthesized, false);
707
708 invoke_record_callback_and_verify(record, TRUE, &user_data);
709 g_ptr_array_clear(g_call_records);
710
711 // Release key A (stage 2)
712 fl_key_responder_handle_event(
713 responder,
714 fl_key_event_new_by_mock(104, kRelease, GDK_KEY_A, kKeyCodeKeyA,
715 GDK_LOCK_MASK, kIsNotModifier),
716 verify_response_handled, &user_data);
717
718 EXPECT_EQ(g_call_records->len, 1u);
719 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
720 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
721 EXPECT_EQ(record->event->physical, kPhysicalKeyA);
722 EXPECT_EQ(record->event->logical, kLogicalKeyA);
723 EXPECT_STREQ(record->event->character, nullptr);
724 EXPECT_EQ(record->event->synthesized, false);
725
726 invoke_record_callback_and_verify(record, TRUE, &user_data);
727 g_ptr_array_clear(g_call_records);
728
729 // Press CapsLock (stage 2 -> 3)
730 fl_key_responder_handle_event(
731 responder,
732 fl_key_event_new_by_mock(105, kPress, GDK_KEY_Caps_Lock, kKeyCodeCapsLock,
733 GDK_LOCK_MASK, kIsModifier),
734 verify_response_handled, &user_data);
735
736 EXPECT_EQ(g_call_records->len, 1u);
737 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
738 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
739 EXPECT_EQ(record->event->physical, kPhysicalCapsLock);
740 EXPECT_EQ(record->event->logical, kLogicalCapsLock);
741 EXPECT_STREQ(record->event->character, nullptr);
742 EXPECT_EQ(record->event->synthesized, false);
743
744 invoke_record_callback_and_verify(record, TRUE, &user_data);
745 g_ptr_array_clear(g_call_records);
746
747 // Press key A (stage 3)
748 fl_key_responder_handle_event(
749 responder,
750 fl_key_event_new_by_mock(106, kPress, GDK_KEY_A, kKeyCodeKeyA,
751 GDK_LOCK_MASK, kIsNotModifier),
752 verify_response_handled, &user_data);
753
754 EXPECT_EQ(g_call_records->len, 1u);
755 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
756 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
757 EXPECT_EQ(record->event->physical, kPhysicalKeyA);
758 EXPECT_EQ(record->event->logical, kLogicalKeyA);
759 EXPECT_STREQ(record->event->character, "A");
760 EXPECT_EQ(record->event->synthesized, false);
761
762 invoke_record_callback_and_verify(record, TRUE, &user_data);
763 g_ptr_array_clear(g_call_records);
764
765 // Release CapsLock (stage 3 -> 0)
766 fl_key_responder_handle_event(
767 responder,
768 fl_key_event_new_by_mock(107, kRelease, GDK_KEY_Caps_Lock,
769 kKeyCodeCapsLock, GDK_LOCK_MASK, kIsModifier),
770 verify_response_handled, &user_data);
771
772 EXPECT_EQ(g_call_records->len, 1u);
773 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
774 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
775 EXPECT_EQ(record->event->physical, kPhysicalCapsLock);
776 EXPECT_EQ(record->event->logical, kLogicalCapsLock);
777 EXPECT_STREQ(record->event->character, nullptr);
778 EXPECT_EQ(record->event->synthesized, false);
779
780 invoke_record_callback_and_verify(record, TRUE, &user_data);
781 g_ptr_array_clear(g_call_records);
782
783 // Release key A (stage 0)
784 fl_key_responder_handle_event(
785 responder,
786 fl_key_event_new_by_mock(108, kRelease, GDK_KEY_a, kKeyCodeKeyA,
787 static_cast<GdkModifierType>(0), kIsNotModifier),
788 verify_response_handled, &user_data);
789
790 EXPECT_EQ(g_call_records->len, 1u);
791 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
792 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
793 EXPECT_EQ(record->event->physical, kPhysicalKeyA);
794 EXPECT_EQ(record->event->logical, kLogicalKeyA);
795 EXPECT_STREQ(record->event->character, nullptr);
796 EXPECT_EQ(record->event->synthesized, false);
797
798 invoke_record_callback_and_verify(record, TRUE, &user_data);
799 g_ptr_array_clear(g_call_records);
800
801 clear_g_call_records();
802 g_object_unref(responder);
803 }

References clear_g_call_records(), fl_key_embedder_responder_new(), fl_key_event_new_by_mock(), fl_key_responder_handle_event(), g_ptr_array_clear(), invoke_record_callback_and_verify(), record_calls(), TRUE, user_data, and verify_response_handled().

## ◆ TEST() [14/17]

TEST | ( | FlKeyEmbedderResponderTest | ,
|  | TapLetterKeysBetweenCapsLockEventsReversed |
| ) |  |

Definition at line 809 of file fl_key_embedder_responder_test.cc.

809 {
810 EXPECT_EQ(g_call_records, nullptr);
811 g_call_records = g_ptr_array_new_with_free_func(g_object_unref);
812 FlKeyResponder* responder = FL_KEY_RESPONDER(
813 fl_key_embedder_responder_new(record_calls, g_call_records));
814 int user_data = 123; // Arbitrary user data
815
816 FlKeyEmbedderCallRecord* record;
817
818 // Press key A (stage 0)
819 fl_key_responder_handle_event(
820 responder,
821 fl_key_event_new_by_mock(101, kPress, GDK_KEY_a, kKeyCodeKeyA,
822 static_cast<GdkModifierType>(0), kIsNotModifier),
823 verify_response_handled, &user_data);
824
825 EXPECT_EQ(g_call_records->len, 1u);
826 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
827 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
828 EXPECT_EQ(record->event->physical, kPhysicalKeyA);
829 EXPECT_EQ(record->event->logical, kLogicalKeyA);
830 EXPECT_STREQ(record->event->character, "a");
831 EXPECT_EQ(record->event->synthesized, false);
832
833 invoke_record_callback_and_verify(record, TRUE, &user_data);
834 g_ptr_array_clear(g_call_records);
835
836 // Press CapsLock (stage 0 -> 1)
837 fl_key_responder_handle_event(
838 responder,
839 fl_key_event_new_by_mock(102, kPress, GDK_KEY_Caps_Lock, kKeyCodeCapsLock,
840 GDK_LOCK_MASK, kIsModifier),
841 verify_response_handled, &user_data);
842
843 EXPECT_EQ(g_call_records->len, 1u);
844 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
845 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
846 EXPECT_EQ(record->event->physical, kPhysicalCapsLock);
847 EXPECT_EQ(record->event->logical, kLogicalCapsLock);
848 EXPECT_STREQ(record->event->character, nullptr);
849 EXPECT_EQ(record->event->synthesized, false);
850
851 invoke_record_callback_and_verify(record, TRUE, &user_data);
852 g_ptr_array_clear(g_call_records);
853
854 // Release CapsLock (stage 1 -> 2)
855 fl_key_responder_handle_event(
856 responder,
857 fl_key_event_new_by_mock(103, kRelease, GDK_KEY_Caps_Lock,
858 kKeyCodeCapsLock, GDK_LOCK_MASK, kIsModifier),
859 verify_response_handled, &user_data);
860
861 EXPECT_EQ(g_call_records->len, 1u);
862 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
863 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
864 EXPECT_EQ(record->event->physical, kPhysicalCapsLock);
865 EXPECT_EQ(record->event->logical, kLogicalCapsLock);
866 EXPECT_STREQ(record->event->character, nullptr);
867 EXPECT_EQ(record->event->synthesized, false);
868
869 invoke_record_callback_and_verify(record, TRUE, &user_data);
870 g_ptr_array_clear(g_call_records);
871
872 // Release key A (stage 2)
873 fl_key_responder_handle_event(
874 responder,
875 fl_key_event_new_by_mock(104, kRelease, GDK_KEY_A, kKeyCodeKeyA,
876 GDK_LOCK_MASK, kIsNotModifier),
877 verify_response_handled, &user_data);
878
879 EXPECT_EQ(g_call_records->len, 1u);
880 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
881 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
882 EXPECT_EQ(record->event->physical, kPhysicalKeyA);
883 EXPECT_EQ(record->event->logical, kLogicalKeyA);
884 EXPECT_STREQ(record->event->character, nullptr);
885 EXPECT_EQ(record->event->synthesized, false);
886
887 invoke_record_callback_and_verify(record, TRUE, &user_data);
888 g_ptr_array_clear(g_call_records);
889
890 // Press key A (stage 2)
891 fl_key_responder_handle_event(
892 responder,
893 fl_key_event_new_by_mock(105, kPress, GDK_KEY_A, kKeyCodeKeyA,
894 GDK_LOCK_MASK, kIsNotModifier),
895 verify_response_handled, &user_data);
896
897 EXPECT_EQ(g_call_records->len, 1u);
898 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
899 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
900 EXPECT_EQ(record->event->physical, kPhysicalKeyA);
901 EXPECT_EQ(record->event->logical, kLogicalKeyA);
902 EXPECT_STREQ(record->event->character, "A");
903 EXPECT_EQ(record->event->synthesized, false);
904
905 invoke_record_callback_and_verify(record, TRUE, &user_data);
906 g_ptr_array_clear(g_call_records);
907
908 // Press CapsLock (stage 2 -> 3)
909 fl_key_responder_handle_event(
910 responder,
911 fl_key_event_new_by_mock(106, kPress, GDK_KEY_Caps_Lock, kKeyCodeCapsLock,
912 static_cast<GdkModifierType>(0), kIsModifier),
913 verify_response_handled, &user_data);
914
915 EXPECT_EQ(g_call_records->len, 1u);
916 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
917 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
918 EXPECT_EQ(record->event->physical, kPhysicalCapsLock);
919 EXPECT_EQ(record->event->logical, kLogicalCapsLock);
920 EXPECT_STREQ(record->event->character, nullptr);
921 EXPECT_EQ(record->event->synthesized, false);
922
923 invoke_record_callback_and_verify(record, TRUE, &user_data);
924 g_ptr_array_clear(g_call_records);
925
926 // Release CapsLock (stage 3 -> 0)
927 fl_key_responder_handle_event(
928 responder,
929 fl_key_event_new_by_mock(107, kRelease, GDK_KEY_Caps_Lock,
930 kKeyCodeCapsLock, GDK_LOCK_MASK, kIsModifier),
931 verify_response_handled, &user_data);
932
933 EXPECT_EQ(g_call_records->len, 1u);
934 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
935 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
936 EXPECT_EQ(record->event->physical, kPhysicalCapsLock);
937 EXPECT_EQ(record->event->logical, kLogicalCapsLock);
938 EXPECT_STREQ(record->event->character, nullptr);
939 EXPECT_EQ(record->event->synthesized, false);
940
941 invoke_record_callback_and_verify(record, TRUE, &user_data);
942 g_ptr_array_clear(g_call_records);
943
944 // Release key A (stage 0)
945 fl_key_responder_handle_event(
946 responder,
947 fl_key_event_new_by_mock(108, kRelease, GDK_KEY_a, kKeyCodeKeyA,
948 static_cast<GdkModifierType>(0), kIsNotModifier),
949 verify_response_handled, &user_data);
950
951 EXPECT_EQ(g_call_records->len, 1u);
952 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
953 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
954 EXPECT_EQ(record->event->physical, kPhysicalKeyA);
955 EXPECT_EQ(record->event->logical, kLogicalKeyA);
956 EXPECT_STREQ(record->event->character, nullptr);
957 EXPECT_EQ(record->event->synthesized, false);
958
959 invoke_record_callback_and_verify(record, TRUE, &user_data);
960 g_ptr_array_clear(g_call_records);
961
962 clear_g_call_records();
963 g_object_unref(responder);
964 }

References clear_g_call_records(), fl_key_embedder_responder_new(), fl_key_event_new_by_mock(), fl_key_responder_handle_event(), g_ptr_array_clear(), invoke_record_callback_and_verify(), record_calls(), TRUE, user_data, and verify_response_handled().

## ◆ TEST() [15/17]

TEST | ( | FlKeyEmbedderResponderTest | ,
|  | TapNumPadKeysBetweenNumLockEvents |
| ) |  |

Definition at line 392 of file fl_key_embedder_responder_test.cc.

392 {
393 EXPECT_EQ(g_call_records, nullptr);
394 g_call_records = g_ptr_array_new_with_free_func(g_object_unref);
395 FlKeyResponder* responder = FL_KEY_RESPONDER(
396 fl_key_embedder_responder_new(record_calls, g_call_records));
397 int user_data = 123; // Arbitrary user data
398
399 FlKeyEmbedderCallRecord* record;
400
401 // Press Numpad 1 (stage 0)
402 fl_key_responder_handle_event(
403 responder,
404 fl_key_event_new_by_mock(101, kPress, GDK_KEY_KP_End, kKeyCodeNumpad1,
405 static_cast<GdkModifierType>(0), kIsNotModifier),
406 verify_response_handled, &user_data);
407
408 EXPECT_EQ(g_call_records->len, 1u);
409 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
410 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
411 EXPECT_EQ(record->event->physical, kPhysicalNumpad1);
412 EXPECT_EQ(record->event->logical, kLogicalNumpad1);
413 EXPECT_STREQ(record->event->character, nullptr); // TODO(chrome-bot):
414 EXPECT_EQ(record->event->synthesized, false);
415
416 invoke_record_callback_and_verify(record, TRUE, &user_data);
417 g_ptr_array_clear(g_call_records);
418
419 // Press NumLock (stage 0 -> 1)
420 fl_key_responder_handle_event(
421 responder,
422 fl_key_event_new_by_mock(102, kPress, GDK_KEY_Num_Lock, kKeyCodeNumLock,
423 static_cast<GdkModifierType>(0), kIsNotModifier),
424 verify_response_handled, &user_data);
425
426 EXPECT_EQ(g_call_records->len, 1u);
427 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
428 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
429 EXPECT_EQ(record->event->physical, kPhysicalNumLock);
430 EXPECT_EQ(record->event->logical, kLogicalNumLock);
431 EXPECT_STREQ(record->event->character, nullptr);
432 EXPECT_EQ(record->event->synthesized, false);
433
434 invoke_record_callback_and_verify(record, TRUE, &user_data);
435 g_ptr_array_clear(g_call_records);
436
437 // Release numpad 1 (stage 1)
438 fl_key_responder_handle_event(
439 responder,
440 fl_key_event_new_by_mock(104, kRelease, GDK_KEY_KP_1, kKeyCodeNumpad1,
441 GDK_MOD2_MASK, kIsNotModifier),
442 verify_response_handled, &user_data);
443
444 EXPECT_EQ(g_call_records->len, 1u);
445 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
446 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
447 EXPECT_EQ(record->event->physical, kPhysicalNumpad1);
448 EXPECT_EQ(record->event->logical, kLogicalNumpad1);
449 EXPECT_STREQ(record->event->character, nullptr);
450 EXPECT_EQ(record->event->synthesized, false);
451
452 invoke_record_callback_and_verify(record, TRUE, &user_data);
453 g_ptr_array_clear(g_call_records);
454
455 // Release NumLock (stage 1 -> 2)
456 fl_key_responder_handle_event(
457 responder,
458 fl_key_event_new_by_mock(103, kRelease, GDK_KEY_Num_Lock, kKeyCodeNumLock,
459 GDK_MOD2_MASK, kIsModifier),
460 verify_response_handled, &user_data);
461
462 EXPECT_EQ(g_call_records->len, 1u);
463 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
464 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
465 EXPECT_EQ(record->event->physical, kPhysicalNumLock);
466 EXPECT_EQ(record->event->logical, kLogicalNumLock);
467 EXPECT_STREQ(record->event->character, nullptr);
468 EXPECT_EQ(record->event->synthesized, false);
469
470 invoke_record_callback_and_verify(record, TRUE, &user_data);
471 g_ptr_array_clear(g_call_records);
472
473 // Press Numpad 1 (stage 2)
474 fl_key_responder_handle_event(
475 responder,
476 fl_key_event_new_by_mock(101, kPress, GDK_KEY_KP_End, kKeyCodeNumpad1,
477 GDK_MOD2_MASK, kIsNotModifier),
478 verify_response_handled, &user_data);
479
480 EXPECT_EQ(g_call_records->len, 1u);
481 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
482 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
483 EXPECT_EQ(record->event->physical, kPhysicalNumpad1);
484 EXPECT_EQ(record->event->logical, kLogicalNumpad1);
485 EXPECT_STREQ(record->event->character, nullptr); // TODO(chrome-bot):
486 EXPECT_EQ(record->event->synthesized, false);
487
488 invoke_record_callback_and_verify(record, TRUE, &user_data);
489 g_ptr_array_clear(g_call_records);
490
491 // Press NumLock (stage 2 -> 3)
492 fl_key_responder_handle_event(
493 responder,
494 fl_key_event_new_by_mock(102, kPress, GDK_KEY_Num_Lock, kKeyCodeNumLock,
495 GDK_MOD2_MASK, kIsNotModifier),
496 verify_response_handled, &user_data);
497
498 EXPECT_EQ(g_call_records->len, 1u);
499 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
500 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
501 EXPECT_EQ(record->event->physical, kPhysicalNumLock);
502 EXPECT_EQ(record->event->logical, kLogicalNumLock);
503 EXPECT_STREQ(record->event->character, nullptr);
504 EXPECT_EQ(record->event->synthesized, false);
505
506 invoke_record_callback_and_verify(record, TRUE, &user_data);
507 g_ptr_array_clear(g_call_records);
508
509 // Release numpad 1 (stage 3)
510 fl_key_responder_handle_event(
511 responder,
512 fl_key_event_new_by_mock(104, kRelease, GDK_KEY_KP_1, kKeyCodeNumpad1,
513 GDK_MOD2_MASK, kIsNotModifier),
514 verify_response_handled, &user_data);
515
516 EXPECT_EQ(g_call_records->len, 1u);
517 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
518 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
519 EXPECT_EQ(record->event->physical, kPhysicalNumpad1);
520 EXPECT_EQ(record->event->logical, kLogicalNumpad1);
521 EXPECT_STREQ(record->event->character, nullptr);
522 EXPECT_EQ(record->event->synthesized, false);
523
524 invoke_record_callback_and_verify(record, TRUE, &user_data);
525 g_ptr_array_clear(g_call_records);
526
527 // Release NumLock (stage 3 -> 0)
528 fl_key_responder_handle_event(
529 responder,
530 fl_key_event_new_by_mock(103, kRelease, GDK_KEY_Num_Lock, kKeyCodeNumLock,
531 GDK_MOD2_MASK, kIsModifier),
532 verify_response_handled, &user_data);
533
534 EXPECT_EQ(g_call_records->len, 1u);
535 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
536 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeUp);
537 EXPECT_EQ(record->event->physical, kPhysicalNumLock);
538 EXPECT_EQ(record->event->logical, kLogicalNumLock);
539 EXPECT_STREQ(record->event->character, nullptr);
540 EXPECT_EQ(record->event->synthesized, false);
541
542 invoke_record_callback_and_verify(record, TRUE, &user_data);
543 g_ptr_array_clear(g_call_records);
544
545 clear_g_call_records();
546 g_object_unref(responder);
547 }

References clear_g_call_records(), fl_key_embedder_responder_new(), fl_key_event_new_by_mock(), fl_key_responder_handle_event(), g_ptr_array_clear(), invoke_record_callback_and_verify(), record_calls(), TRUE, user_data, and verify_response_handled().

## ◆ TEST() [16/17]

TEST | ( | FlKeyEmbedderResponderTest | ,
|  | TurnDuplicateDownEventsToRepeats |
| ) |  |

Definition at line 966 of file fl_key_embedder_responder_test.cc.

966 {
967 EXPECT_EQ(g_call_records, nullptr);
968 g_call_records = g_ptr_array_new_with_free_func(g_object_unref);
969 FlKeyResponder* responder = FL_KEY_RESPONDER(
970 fl_key_embedder_responder_new(record_calls, g_call_records));
971 int user_data = 123; // Arbitrary user data
972
973 FlKeyEmbedderCallRecord* record;
974
975 // Press KeyA
976 fl_key_responder_handle_event(
977 responder,
978 fl_key_event_new_by_mock(101, kPress, GDK_KEY_a, kKeyCodeKeyA,
979 static_cast<GdkModifierType>(0), kIsNotModifier),
980 verify_response_handled, &user_data);
981
982 EXPECT_EQ(g_call_records->len, 1u);
983
984 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
985 invoke_record_callback_and_verify(record, TRUE, &user_data);
986 g_ptr_array_clear(g_call_records);
987
988 // Another KeyA down events, which usually means a repeated event.
989 g_expected_handled = false;
990 fl_key_responder_handle_event(
991 responder,
992 fl_key_event_new_by_mock(102, kPress, GDK_KEY_a, kKeyCodeKeyA,
993 static_cast<GdkModifierType>(0), kIsNotModifier),
994 verify_response_handled, &user_data);
995
996 EXPECT_EQ(g_call_records->len, 1u);
997
998 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
999 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeRepeat);
1000 EXPECT_EQ(record->event->physical, kPhysicalKeyA);
1001 EXPECT_EQ(record->event->logical, kLogicalKeyA);
1002 EXPECT_STREQ(record->event->character, "a");
1003 EXPECT_EQ(record->event->synthesized, false);
1004 EXPECT_NE(record->callback, nullptr);
1005
1006 invoke_record_callback_and_verify(record, TRUE, &user_data);
1007 g_ptr_array_clear(g_call_records);
1008
1009 // Release KeyA
1010 fl_key_responder_handle_event(
1011 responder,
1012 fl_key_event_new_by_mock(103, kRelease, GDK_KEY_q, kKeyCodeKeyA,
1013 static_cast<GdkModifierType>(0), kIsNotModifier),
1014 verify_response_handled, &user_data);
1015
1016 EXPECT_EQ(g_call_records->len, 1u);
1017 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
1018 invoke_record_callback_and_verify(record, TRUE, &user_data);
1019 g_ptr_array_clear(g_call_records);
1020
1021 clear_g_call_records();
1022 g_object_unref(responder);
1023 }

References clear_g_call_records(), fl_key_embedder_responder_new(), fl_key_event_new_by_mock(), fl_key_responder_handle_event(), g_expected_handled, g_ptr_array_clear(), invoke_record_callback_and_verify(), record_calls(), TRUE, user_data, and verify_response_handled().

## ◆ TEST() [17/17]

TEST | ( | FlKeyEmbedderResponderTest | ,
|  | UsesSpecifiedLogicalKey |
| ) |  |

Definition at line 264 of file fl_key_embedder_responder_test.cc.

264 {
265 EXPECT_EQ(g_call_records, nullptr);
266 g_call_records = g_ptr_array_new_with_free_func(g_object_unref);
267 FlKeyResponder* responder = FL_KEY_RESPONDER(
268 fl_key_embedder_responder_new(record_calls, g_call_records));
269 int user_data = 123; // Arbitrary user data
270
271 FlKeyEmbedderCallRecord* record;
272
273 // On an AZERTY keyboard, press physical key 1, and release.
274 // Key down
275 fl_key_responder_handle_event(
276 responder,
277 fl_key_event_new_by_mock(12345, kPress, GDK_KEY_ampersand, kKeyCodeDigit1,
278 static_cast<GdkModifierType>(0), kIsNotModifier),
279 verify_response_handled, &user_data, kLogicalDigit1);
280
281 EXPECT_EQ(g_call_records->len, 1u);
282 record = FL_KEY_EMBEDDER_CALL_RECORD(g_ptr_array_index(g_call_records, 0));
283 EXPECT_EQ(record->event->struct_size, sizeof(FlutterKeyEvent));
284 EXPECT_EQ(record->event->timestamp, 12345000);
285 EXPECT_EQ(record->event->type, kFlutterKeyEventTypeDown);
286 EXPECT_EQ(record->event->physical, kPhysicalDigit1);
287 EXPECT_EQ(record->event->logical, kLogicalDigit1);
288 EXPECT_STREQ(record->event->character, "&");
289 EXPECT_EQ(record->event->synthesized, false);
290
291 invoke_record_callback_and_verify(record, TRUE, &user_data);
292 g_ptr_array_clear(g_call_records);
293
294 clear_g_call_records();
295 g_object_unref(responder);
296 }

References clear_g_call_records(), fl_key_embedder_responder_new(), fl_key_event_new_by_mock(), fl_key_responder_handle_event(), g_ptr_array_clear(), invoke_record_callback_and_verify(), record_calls(), TRUE, user_data, and verify_response_handled().

## ◆ verify_response_handled()

static void verify_response_handled | ( | bool | handled,
|  | gpointer | user_data
| ) |  |
| static

Definition at line 133 of file fl_key_embedder_responder_test.cc.

133 {
134 EXPECT_EQ(handled, g_expected_handled);
135 }

References g_expected_handled.

Referenced by TEST().

## Variable Documentation

## ◆ g_expected_handled

gboolean g_expected_handled
| static

Definition at line 130 of file fl_key_embedder_responder_test.cc.

Referenced by invoke_record_callback_and_verify(), TEST(), and verify_response_handled().

## ◆ g_expected_user_data

gpointer g_expected_user_data
| static

Definition at line 131 of file fl_key_embedder_responder_test.cc.

Referenced by invoke_record_callback_and_verify().

event
FlKeyEvent * event
Definition: fl_key_channel_responder.cc:118
clear_g_call_records
static void clear_g_call_records()
Definition: fl_key_embedder_responder_test.cc:162
user_data
FlKeyEvent uint64_t FlKeyResponderAsyncCallback gpointer user_data
Definition: fl_key_channel_responder.cc:121
state
AtkStateType state
Definition: fl_accessible_node.cc:10
record_calls
static void record_calls(const FlutterKeyEvent *event, FlutterKeyEventCallback callback, void *callback_user_data, void *send_key_event_user_data)
Definition: fl_key_embedder_responder_test.cc:150
fl_key_embedder_responder_new
FlKeyEmbedderResponder * fl_key_embedder_responder_new(EmbedderSendKeyEvent send_key_event, void *send_key_event_user_data)
Definition: fl_key_embedder_responder.cc:263
fl_key_event_new_by_mock
static FlKeyEvent * fl_key_event_new_by_mock(guint32 time_in_milliseconds, bool is_press, guint keyval, guint16 keycode, GdkModifierType state, gboolean is_modifier)
Definition: fl_key_embedder_responder_test.cc:115
fl_key_responder_handle_event
void fl_key_responder_handle_event(FlKeyResponder *self, FlKeyEvent *event, FlKeyResponderAsyncCallback callback, gpointer user_data, uint64_t specified_logical_key)
Definition: fl_key_responder.cc:11
TRUE
return TRUE
Definition: fl_pixel_buffer_texture_test.cc:53
fl_key_embedder_call_record_dispose
static void fl_key_embedder_call_record_dispose(GObject *object)
Definition: fl_key_embedder_responder_test.cc:62
fl_key_embedder_call_record_new
static FlKeyEmbedderCallRecord * fl_key_embedder_call_record_new(const FlutterKeyEvent *event, FlutterKeyEventCallback callback, gpointer user_data)
Definition: fl_key_embedder_responder_test.cc:79
g_expected_handled
static gboolean g_expected_handled
Definition: fl_key_embedder_responder_test.cc:130
invoke_record_callback_and_verify
static void invoke_record_callback_and_verify(FlKeyEmbedderCallRecord *record, bool expected_handled, void *expected_user_data)
Definition: fl_key_embedder_responder_test.cc:137
g_ptr_array_clear
static void g_ptr_array_clear(GPtrArray *array)
Definition: fl_key_embedder_responder_test.cc:37
g_expected_user_data
static gpointer g_expected_user_data
Definition: fl_key_embedder_responder_test.cc:131
verify_response_handled
static void verify_response_handled(bool handled, gpointer user_data)
Definition: fl_key_embedder_responder_test.cc:133
send_key_event
static void send_key_event(FlTextInputPlugin *plugin, gint keyval, gint state=0)
Definition: fl_text_input_plugin_test.cc:181
callback
FlKeyEvent uint64_t FlKeyResponderAsyncCallback callback
Definition: fl_key_channel_responder.cc:120
expected_handled
static gboolean expected_handled
Definition: fl_key_channel_responder_test.cc:14