2020// is used in unit tests.
2121#define DEBUG_PRINT_LAYOUT
2222
23- /* Declarations of private classes */
24-
25- G_DECLARE_FINAL_TYPE (FlKeyboardManagerData,
26- fl_keyboard_manager_data,
27- FL,
28- KEYBOARD_MANAGER_DATA,
29- GObject);
30-
31- /* End declarations */
32-
3323namespace {
3424
3525static bool is_eascii (uint16_t character) {
@@ -63,55 +53,6 @@ void debug_format_layout_data(std::string& debug_layout_data,
6353
6454} // namespace
6555
66- /* Define FlKeyboardManagerData */
67-
68- /* *
69- * FlKeyboardManagerData:
70- * The user_data used when #FlKeyboardManager sends event to
71- * responders.
72- */
73-
74- struct _FlKeyboardManagerData {
75- GObject parent_instance;
76-
77- // The owner manager.
78- GWeakRef manager;
79-
80- FlKeyboardPendingEvent* pending;
81- };
82-
83- G_DEFINE_TYPE (FlKeyboardManagerData, fl_keyboard_manager_data, G_TYPE_OBJECT)
84-
85- static void fl_keyboard_manager_data_dispose(GObject* object) {
86- g_return_if_fail (FL_IS_KEYBOARD_MANAGER_DATA (object));
87- FlKeyboardManagerData* self = FL_KEYBOARD_MANAGER_DATA (object);
88-
89- g_weak_ref_clear (&self->manager );
90-
91- G_OBJECT_CLASS (fl_keyboard_manager_data_parent_class)->dispose (object);
92- }
93-
94- static void fl_keyboard_manager_data_class_init (
95- FlKeyboardManagerDataClass* klass) {
96- G_OBJECT_CLASS (klass)->dispose = fl_keyboard_manager_data_dispose;
97- }
98-
99- static void fl_keyboard_manager_data_init (FlKeyboardManagerData* self) {}
100-
101- // Creates a new FlKeyboardManagerData private class with all information.
102- static FlKeyboardManagerData* fl_keyboard_manager_data_new (
103- FlKeyboardManager* manager,
104- FlKeyboardPendingEvent* pending) {
105- FlKeyboardManagerData* self = FL_KEYBOARD_MANAGER_DATA (
106- g_object_new (fl_keyboard_manager_data_get_type (), nullptr ));
107-
108- g_weak_ref_init (&self->manager , manager);
109- self->pending = FL_KEYBOARD_PENDING_EVENT (g_object_ref (pending));
110- return self;
111- }
112-
113- /* Define FlKeyboardManager */
114-
11556struct _FlKeyboardManager {
11657 GObject parent_instance;
11758
@@ -211,25 +152,6 @@ static gboolean compare_pending_by_hash(gconstpointer a, gconstpointer b) {
211152 return fl_keyboard_pending_event_get_hash (pending) == hash;
212153}
213154
214- // Try to remove a pending event from `pending_redispatches` with the target
215- // hash.
216- //
217- // Returns true if the event is found and removed.
218- static bool fl_keyboard_manager_remove_redispatched (FlKeyboardManager* self,
219- uint64_t hash) {
220- guint result_index;
221- gboolean found = g_ptr_array_find_with_equal_func1 (
222- self->pending_redispatches , static_cast <const uint64_t *>(&hash),
223- compare_pending_by_hash, &result_index);
224- if (found) {
225- // The removed object is freed due to `pending_redispatches`'s free_func.
226- g_ptr_array_remove_index_fast (self->pending_redispatches , result_index);
227- return TRUE ;
228- } else {
229- return FALSE ;
230- }
231- }
232-
233155// The callback used by a responder after the event was dispatched.
234156static void responder_handle_event_callback (FlKeyboardManager* self,
235157 FlKeyboardPendingEvent* pending) {
@@ -262,25 +184,33 @@ static void responder_handle_event_callback(FlKeyboardManager* self,
262184 }
263185}
264186
187+ static void complete_handle_event (FlKeyboardManager* self, GTask* task) {
188+ FlKeyboardPendingEvent* pending =
189+ FL_KEYBOARD_PENDING_EVENT (g_task_get_task_data (task));
190+
191+ if (fl_keyboard_pending_event_is_complete (pending)) {
192+ g_task_return_boolean (task, TRUE );
193+ }
194+ }
195+
265196static void responder_handle_embedder_event_callback (bool handled,
266197 gpointer user_data) {
267- g_autoptr (FlKeyboardManagerData) data = FL_KEYBOARD_MANAGER_DATA (user_data);
268-
269- fl_keyboard_pending_event_mark_embedder_replied (data->pending , handled);
198+ g_autoptr (GTask) task = G_TASK (user_data);
199+ FlKeyboardManager* self = FL_KEYBOARD_MANAGER (g_task_get_source_object (task));
270200
271- g_autoptr (FlKeyboardManager) self =
272- FL_KEYBOARD_MANAGER (g_weak_ref_get (&data->manager ));
273- if (self == nullptr ) {
274- return ;
275- }
201+ FlKeyboardPendingEvent* pending =
202+ FL_KEYBOARD_PENDING_EVENT (g_task_get_task_data (task));
203+ fl_keyboard_pending_event_mark_embedder_replied (pending, handled);
204+ responder_handle_event_callback (self, pending);
276205
277- responder_handle_event_callback (self, data-> pending );
206+ complete_handle_event (self, task );
278207}
279208
280209static void responder_handle_channel_event_cb (GObject* object,
281210 GAsyncResult* result,
282211 gpointer user_data) {
283- g_autoptr (FlKeyboardManagerData) data = FL_KEYBOARD_MANAGER_DATA (user_data);
212+ g_autoptr (GTask) task = G_TASK (user_data);
213+ FlKeyboardManager* self = FL_KEYBOARD_MANAGER (g_task_get_source_object (task));
284214
285215 g_autoptr (GError) error = nullptr ;
286216 gboolean handled;
@@ -289,18 +219,15 @@ static void responder_handle_channel_event_cb(GObject* object,
289219 if (!g_error_matches (error, G_IO_ERROR, G_IO_ERROR_CANCELLED)) {
290220 g_warning (" Failed to handle key event in platform: %s" , error->message );
291221 }
292- return ;
293- }
294-
295- g_autoptr (FlKeyboardManager) self =
296- FL_KEYBOARD_MANAGER (g_weak_ref_get (&data->manager ));
297- if (self == nullptr ) {
298- return ;
222+ handled = FALSE ;
299223 }
300224
301- fl_keyboard_pending_event_mark_channel_replied (data->pending , handled);
225+ FlKeyboardPendingEvent* pending =
226+ FL_KEYBOARD_PENDING_EVENT (g_task_get_task_data (task));
227+ fl_keyboard_pending_event_mark_channel_replied (pending, handled);
228+ responder_handle_event_callback (self, pending);
302229
303- responder_handle_event_callback (self, data-> pending );
230+ complete_handle_event (self, task );
304231}
305232
306233static uint16_t convert_key_to_char (FlKeyboardManager* self,
@@ -519,34 +446,58 @@ FlKeyboardManager* fl_keyboard_manager_new(
519446 return self;
520447}
521448
522- gboolean fl_keyboard_manager_handle_event (FlKeyboardManager* self,
523- FlKeyEvent* event) {
449+ gboolean fl_keyboard_manager_is_redispatched (FlKeyboardManager* self,
450+ FlKeyEvent* event) {
524451 g_return_val_if_fail (FL_IS_KEYBOARD_MANAGER (self), FALSE );
525- g_return_val_if_fail (event != nullptr , FALSE );
526452
527- guarantee_layout (self, event);
453+ uint64_t hash = fl_key_event_hash ( event);
528454
529- uint64_t incoming_hash = fl_key_event_hash (event);
530- if (fl_keyboard_manager_remove_redispatched (self, incoming_hash)) {
455+ guint result_index;
456+ gboolean found = g_ptr_array_find_with_equal_func1 (
457+ self->pending_redispatches , static_cast <const uint64_t *>(&hash),
458+ compare_pending_by_hash, &result_index);
459+ if (found) {
460+ // The removed object is freed due to `pending_redispatches`'s free_func.
461+ g_ptr_array_remove_index_fast (self->pending_redispatches , result_index);
462+ return TRUE ;
463+ } else {
531464 return FALSE ;
532465 }
466+ }
533467
534- FlKeyboardPendingEvent* pending = fl_keyboard_pending_event_new (event);
468+ void fl_keyboard_manager_handle_event (FlKeyboardManager* self,
469+ FlKeyEvent* event,
470+ GCancellable* cancellable,
471+ GAsyncReadyCallback callback,
472+ gpointer user_data) {
473+ g_return_if_fail (FL_IS_KEYBOARD_MANAGER (self));
474+ g_return_if_fail (event != nullptr );
475+
476+ g_autoptr (GTask) task = g_task_new (self, cancellable, callback, user_data);
477+
478+ guarantee_layout (self, event);
535479
480+ FlKeyboardPendingEvent* pending = fl_keyboard_pending_event_new (event);
536481 g_ptr_array_add (self->pending_responds , pending);
537- g_autoptr (FlKeyboardManagerData) data =
538- fl_keyboard_manager_data_new (self, pending);
482+ g_task_set_task_data (task, g_object_ref (pending), g_object_unref);
483+
539484 uint64_t specified_logical_key = fl_keyboard_layout_get_logical_key (
540485 self->derived_layout , fl_key_event_get_group (event),
541486 fl_key_event_get_keycode (event));
542487 fl_key_embedder_responder_handle_event (
543488 self->key_embedder_responder , event, specified_logical_key,
544- responder_handle_embedder_event_callback, g_object_ref (data ));
489+ responder_handle_embedder_event_callback, g_object_ref (task ));
545490 fl_key_channel_responder_handle_event (
546491 self->key_channel_responder , event, specified_logical_key,
547- self->cancellable , responder_handle_channel_event_cb, g_object_ref (data));
492+ self->cancellable , responder_handle_channel_event_cb, g_object_ref (task));
493+ }
548494
549- return TRUE ;
495+ gboolean fl_keyboard_manager_handle_event_finish (FlKeyboardManager* self,
496+ GAsyncResult* result,
497+ GError** error) {
498+ g_return_val_if_fail (FL_IS_KEYBOARD_MANAGER (self), FALSE );
499+ g_return_val_if_fail (g_task_is_valid (result, self), FALSE );
500+ return g_task_propagate_boolean (G_TASK (result), error);
550501}
551502
552503gboolean fl_keyboard_manager_is_state_clear (FlKeyboardManager* self) {
0 commit comments