4 * An OpenGL based 'interactive canvas' library.
6 * Authored By Matthew Allum <mallum@openedhand.com>
8 * Copyright (C) 2006 OpenedHand
10 * This library is free software; you can redistribute it and/or
11 * modify it under the terms of the GNU Lesser General Public
12 * License as published by the Free Software Foundation; either
13 * version 2 of the License, or (at your option) any later version.
15 * This library is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
18 * Lesser General Public License for more details.
20 * You should have received a copy of the GNU Lesser General Public
21 * License along with this library. If not, see <http://www.gnu.org/licenses/>.
30 #include "clutter-backend-private.h"
31 #include "clutter-debug.h"
32 #include "clutter-event-private.h"
33 #include "clutter-keysyms.h"
34 #include "clutter-private.h"
37 * SECTION:clutter-event
38 * @short_description: User and window system events
40 * Windowing events handled by Clutter.
42 * The events usually come from the windowing backend, but can also
43 * be synthesized by Clutter itself or by the application code.
46 typedef struct _ClutterEventPrivate {
49 ClutterInputDevice *device;
50 ClutterInputDevice *source_device;
55 gpointer platform_data;
57 guint is_pointer_emulated : 1;
58 } ClutterEventPrivate;
60 static GHashTable *all_events = NULL;
62 G_DEFINE_BOXED_TYPE (ClutterEvent, clutter_event,
67 is_event_allocated (const ClutterEvent *event)
69 if (all_events == NULL)
72 return g_hash_table_lookup (all_events, event) != NULL;
76 * _clutter_event_get_platform_data:
77 * @event: a #ClutterEvent
79 * Retrieves the pointer to platform-specific data inside an event
81 * Return value: a pointer to platform-specific data
86 _clutter_event_get_platform_data (const ClutterEvent *event)
88 if (!is_event_allocated (event))
91 return ((ClutterEventPrivate *) event)->platform_data;
95 * _clutter_event_set_platform_data:
96 * @event: a #ClutterEvent
97 * @data: a pointer to platform-specific data
99 * Sets the pointer to platform-specific data inside an event
104 _clutter_event_set_platform_data (ClutterEvent *event,
107 if (!is_event_allocated (event))
110 ((ClutterEventPrivate *) event)->platform_data = data;
114 _clutter_event_set_pointer_emulated (ClutterEvent *event,
115 gboolean is_emulated)
117 if (!is_event_allocated (event))
120 ((ClutterEventPrivate *) event)->is_pointer_emulated = !!is_emulated;
124 * clutter_event_type:
125 * @event: a #ClutterEvent
127 * Retrieves the type of the event.
129 * Return value: a #ClutterEventType
132 clutter_event_type (const ClutterEvent *event)
134 g_return_val_if_fail (event != NULL, CLUTTER_NOTHING);
140 * clutter_event_get_time:
141 * @event: a #ClutterEvent
143 * Retrieves the time of the event.
145 * Return value: the time of the event, or %CLUTTER_CURRENT_TIME
150 clutter_event_get_time (const ClutterEvent *event)
152 g_return_val_if_fail (event != NULL, CLUTTER_CURRENT_TIME);
154 return event->any.time;
158 * clutter_event_set_time:
159 * @event: a #ClutterEvent
160 * @time_: the time of the event
162 * Sets the time of the event.
167 clutter_event_set_time (ClutterEvent *event,
170 g_return_if_fail (event != NULL);
172 event->any.time = time_;
176 * clutter_event_get_state:
177 * @event: a #ClutterEvent
179 * Retrieves the modifier state of the event.
181 * Return value: the modifier state parameter, or 0
186 clutter_event_get_state (const ClutterEvent *event)
188 g_return_val_if_fail (event != NULL, 0);
192 case CLUTTER_KEY_PRESS:
193 case CLUTTER_KEY_RELEASE:
194 return event->key.modifier_state;
196 case CLUTTER_BUTTON_PRESS:
197 case CLUTTER_BUTTON_RELEASE:
198 return event->button.modifier_state;
200 case CLUTTER_TOUCH_BEGIN:
201 case CLUTTER_TOUCH_UPDATE:
202 case CLUTTER_TOUCH_END:
203 case CLUTTER_TOUCH_CANCEL:
204 return event->touch.modifier_state;
207 return event->motion.modifier_state;
210 return event->scroll.modifier_state;
220 * clutter_event_set_state:
221 * @event: a #ClutterEvent
222 * @state: the modifier state to set
224 * Sets the modifier state of the event.
229 clutter_event_set_state (ClutterEvent *event,
230 ClutterModifierType state)
232 g_return_if_fail (event != NULL);
236 case CLUTTER_KEY_PRESS:
237 case CLUTTER_KEY_RELEASE:
238 event->key.modifier_state = state;
241 case CLUTTER_BUTTON_PRESS:
242 case CLUTTER_BUTTON_RELEASE:
243 event->button.modifier_state = state;
247 event->motion.modifier_state = state;
250 case CLUTTER_TOUCH_BEGIN:
251 case CLUTTER_TOUCH_UPDATE:
252 case CLUTTER_TOUCH_END:
253 case CLUTTER_TOUCH_CANCEL:
254 event->touch.modifier_state = state;
258 event->scroll.modifier_state = state;
267 * clutter_event_get_coords:
268 * @event: a #ClutterEvent
269 * @x: (out): return location for the X coordinate, or %NULL
270 * @y: (out): return location for the Y coordinate, or %NULL
272 * Retrieves the coordinates of @event and puts them into @x and @y.
277 clutter_event_get_coords (const ClutterEvent *event,
281 gfloat event_x, event_y;
283 g_return_if_fail (event != NULL);
285 event_x = event_y = 0;
289 case CLUTTER_NOTHING:
290 case CLUTTER_KEY_PRESS:
291 case CLUTTER_KEY_RELEASE:
292 case CLUTTER_STAGE_STATE:
293 case CLUTTER_DESTROY_NOTIFY:
294 case CLUTTER_CLIENT_MESSAGE:
296 case CLUTTER_EVENT_LAST:
301 event_x = event->crossing.x;
302 event_y = event->crossing.y;
305 case CLUTTER_BUTTON_PRESS:
306 case CLUTTER_BUTTON_RELEASE:
307 event_x = event->button.x;
308 event_y = event->button.y;
312 event_x = event->motion.x;
313 event_y = event->motion.y;
316 case CLUTTER_TOUCH_BEGIN:
317 case CLUTTER_TOUCH_UPDATE:
318 case CLUTTER_TOUCH_END:
319 case CLUTTER_TOUCH_CANCEL:
320 event_x = event->touch.x;
321 event_y = event->touch.y;
325 event_x = event->scroll.x;
326 event_y = event->scroll.y;
338 * clutter_event_set_coords:
339 * @event: a #ClutterEvent
340 * @x: the X coordinate of the event
341 * @y: the Y coordinate of the event
343 * Sets the coordinates of the @event.
348 clutter_event_set_coords (ClutterEvent *event,
352 g_return_if_fail (event != NULL);
356 case CLUTTER_NOTHING:
357 case CLUTTER_KEY_PRESS:
358 case CLUTTER_KEY_RELEASE:
359 case CLUTTER_STAGE_STATE:
360 case CLUTTER_DESTROY_NOTIFY:
361 case CLUTTER_CLIENT_MESSAGE:
363 case CLUTTER_EVENT_LAST:
368 event->crossing.x = x;
369 event->crossing.y = y;
372 case CLUTTER_BUTTON_PRESS:
373 case CLUTTER_BUTTON_RELEASE:
383 case CLUTTER_TOUCH_BEGIN:
384 case CLUTTER_TOUCH_UPDATE:
385 case CLUTTER_TOUCH_END:
386 case CLUTTER_TOUCH_CANCEL:
399 * clutter_event_get_source:
400 * @event: a #ClutterEvent
402 * Retrieves the source #ClutterActor the event originated from, or
403 * NULL if the event has no source.
405 * Return value: (transfer none): a #ClutterActor
410 clutter_event_get_source (const ClutterEvent *event)
412 g_return_val_if_fail (event != NULL, NULL);
414 return event->any.source;
418 * clutter_event_set_source:
419 * @event: a #ClutterEvent
420 * @actor: (allow-none): a #ClutterActor, or %NULL
422 * Sets the source #ClutterActor of @event.
427 clutter_event_set_source (ClutterEvent *event,
430 g_return_if_fail (event != NULL);
431 g_return_if_fail (actor == NULL || CLUTTER_IS_ACTOR (actor));
433 event->any.source = actor;
437 * clutter_event_get_stage:
438 * @event: a #ClutterEvent
440 * Retrieves the source #ClutterStage the event originated for, or
441 * %NULL if the event has no stage.
443 * Return value: (transfer none): a #ClutterStage
448 clutter_event_get_stage (const ClutterEvent *event)
450 g_return_val_if_fail (event != NULL, NULL);
452 return event->any.stage;
456 * clutter_event_set_stage:
457 * @event: a #ClutterEvent
458 * @stage: (allow-none): a #ClutterStage, or %NULL
460 * Sets the source #ClutterStage of the event.
465 clutter_event_set_stage (ClutterEvent *event,
468 g_return_if_fail (event != NULL);
469 g_return_if_fail (stage == NULL || CLUTTER_IS_STAGE (stage));
471 if (event->any.stage == stage)
474 event->any.stage = stage;
478 * clutter_event_get_flags:
479 * @event: a #ClutterEvent
481 * Retrieves the #ClutterEventFlags of @event
483 * Return value: the event flags
488 clutter_event_get_flags (const ClutterEvent *event)
490 g_return_val_if_fail (event != NULL, CLUTTER_EVENT_NONE);
492 return event->any.flags;
496 * clutter_event_set_flags:
497 * @event: a #ClutterEvent
498 * @flags: a binary OR of #ClutterEventFlags values
500 * Sets the #ClutterEventFlags of @event
505 clutter_event_set_flags (ClutterEvent *event,
506 ClutterEventFlags flags)
508 g_return_if_fail (event != NULL);
510 if (event->any.flags == flags)
513 event->any.flags = flags;
514 event->any.flags |= CLUTTER_EVENT_FLAG_SYNTHETIC;
518 * clutter_event_get_related:
519 * @event: a #ClutterEvent of type %CLUTTER_ENTER or of
520 * type %CLUTTER_LEAVE
522 * Retrieves the related actor of a crossing event.
524 * Return value: (transfer none): the related #ClutterActor, or %NULL
529 clutter_event_get_related (const ClutterEvent *event)
531 g_return_val_if_fail (event != NULL, NULL);
532 g_return_val_if_fail (event->type == CLUTTER_ENTER ||
533 event->type == CLUTTER_LEAVE, NULL);
535 return event->crossing.related;
539 * clutter_event_set_related:
540 * @event: a #ClutterEvent of type %CLUTTER_ENTER or %CLUTTER_LEAVE
541 * @actor: (allow-none): a #ClutterActor or %NULL
543 * Sets the related actor of a crossing event
548 clutter_event_set_related (ClutterEvent *event,
551 g_return_if_fail (event != NULL);
552 g_return_if_fail (event->type == CLUTTER_ENTER ||
553 event->type == CLUTTER_LEAVE);
554 g_return_if_fail (actor == NULL || CLUTTER_IS_ACTOR (actor));
556 if (event->crossing.related == actor)
559 event->crossing.related = actor;
563 * clutter_event_set_scroll_delta:
564 * @event: a #ClutterEvent of type %CLUTTER_SCROLL
565 * @dx: delta on the horizontal axis
566 * @dy: delta on the vertical axis
568 * Sets the precise scrolling information of @event.
573 clutter_event_set_scroll_delta (ClutterEvent *event,
577 g_return_if_fail (event != NULL);
578 g_return_if_fail (event->type == CLUTTER_SCROLL);
580 if (!is_event_allocated (event))
583 event->scroll.direction = CLUTTER_SCROLL_SMOOTH;
585 ((ClutterEventPrivate *) event)->delta_x = dx;
586 ((ClutterEventPrivate *) event)->delta_y = dy;
590 * clutter_event_get_scroll_delta:
591 * @event: a #ClutterEvent of type %CLUTTER_SCROLL
592 * @dx: (out): return location for the delta on the horizontal axis
593 * @dy: (out): return location for the delta on the vertical axis
595 * Retrieves the precise scrolling information of @event.
597 * The @event has to have a #ClutterScrollEvent.direction value
598 * of %CLUTTER_SCROLL_SMOOTH.
603 clutter_event_get_scroll_delta (const ClutterEvent *event,
607 gdouble delta_x, delta_y;
609 g_return_if_fail (event != NULL);
610 g_return_if_fail (event->type == CLUTTER_SCROLL);
611 g_return_if_fail (event->scroll.direction == CLUTTER_SCROLL_SMOOTH);
613 delta_x = delta_y = 0;
615 if (is_event_allocated (event))
617 delta_x = ((ClutterEventPrivate *) event)->delta_x;
618 delta_y = ((ClutterEventPrivate *) event)->delta_y;
629 * clutter_event_get_scroll_direction:
630 * @event: a #ClutterEvent of type %CLUTTER_SCROLL
632 * Retrieves the direction of the scrolling of @event
634 * Return value: the scrolling direction
638 ClutterScrollDirection
639 clutter_event_get_scroll_direction (const ClutterEvent *event)
641 g_return_val_if_fail (event != NULL, CLUTTER_SCROLL_UP);
642 g_return_val_if_fail (event->type == CLUTTER_SCROLL, CLUTTER_SCROLL_UP);
644 return event->scroll.direction;
648 * clutter_event_set_scroll_direction:
649 * @event: a #ClutterEvent
650 * @direction: the scrolling direction
652 * Sets the direction of the scrolling of @event
657 clutter_event_set_scroll_direction (ClutterEvent *event,
658 ClutterScrollDirection direction)
660 g_return_if_fail (event != NULL);
661 g_return_if_fail (event->type == CLUTTER_SCROLL);
663 event->scroll.direction = direction;
667 * clutter_event_get_button:
668 * @event: a #ClutterEvent of type %CLUTTER_BUTTON_PRESS or
669 * of type %CLUTTER_BUTTON_RELEASE
671 * Retrieves the button number of @event
673 * Return value: the button number
678 clutter_event_get_button (const ClutterEvent *event)
680 g_return_val_if_fail (event != NULL, 0);
681 g_return_val_if_fail (event->type == CLUTTER_BUTTON_PRESS ||
682 event->type == CLUTTER_BUTTON_RELEASE, 0);
684 return event->button.button;
688 * clutter_event_set_button:
689 * @event: a #ClutterEvent or type %CLUTTER_BUTTON_PRESS or
690 * of type %CLUTTER_BUTTON_RELEASE
691 * @button: the button number
693 * Sets the button number of @event
698 clutter_event_set_button (ClutterEvent *event,
701 g_return_if_fail (event != NULL);
702 g_return_if_fail (event->type == CLUTTER_BUTTON_PRESS ||
703 event->type == CLUTTER_BUTTON_RELEASE);
705 event->button.button = button;
709 * clutter_event_get_click_count:
710 * @event: a #ClutterEvent of type %CLUTTER_BUTTON_PRESS or
711 * of type %CLUTTER_BUTTON_RELEASE
713 * Retrieves the number of clicks of @event
715 * Return value: the click count
720 clutter_event_get_click_count (const ClutterEvent *event)
722 g_return_val_if_fail (event != NULL, 0);
723 g_return_val_if_fail (event->type == CLUTTER_BUTTON_PRESS ||
724 event->type == CLUTTER_BUTTON_RELEASE, 0);
726 return event->button.click_count;
732 * clutter_event_get_key_symbol:
733 * @event: a #ClutterEvent of type %CLUTTER_KEY_PRESS or
734 * of type %CLUTTER_KEY_RELEASE
736 * Retrieves the key symbol of @event
738 * Return value: the key symbol representing the key
743 clutter_event_get_key_symbol (const ClutterEvent *event)
745 g_return_val_if_fail (event != NULL, 0);
746 g_return_val_if_fail (event->type == CLUTTER_KEY_PRESS ||
747 event->type == CLUTTER_KEY_RELEASE, 0);
749 return event->key.keyval;
753 * clutter_event_set_key_symbol:
754 * @event: a #ClutterEvent of type %CLUTTER_KEY_PRESS
755 * or %CLUTTER_KEY_RELEASE
756 * @key_sym: the key symbol representing the key
758 * Sets the key symbol of @event.
763 clutter_event_set_key_symbol (ClutterEvent *event,
766 g_return_if_fail (event != NULL);
767 g_return_if_fail (event->type == CLUTTER_KEY_PRESS ||
768 event->type == CLUTTER_KEY_RELEASE);
770 event->key.keyval = key_sym;
774 * clutter_event_get_key_code:
775 * @event: a #ClutterEvent of type %CLUTTER_KEY_PRESS or
776 * of type %CLUTTER_KEY_RELEASE
778 * Retrieves the keycode of the key that caused @event
780 * Return value: The keycode representing the key
785 clutter_event_get_key_code (const ClutterEvent *event)
787 g_return_val_if_fail (event != NULL, 0);
788 g_return_val_if_fail (event->type == CLUTTER_KEY_PRESS ||
789 event->type == CLUTTER_KEY_RELEASE, 0);
791 return event->key.hardware_keycode;
795 * clutter_event_set_key_code:
796 * @event: a #ClutterEvent of type %CLUTTER_KEY_PRESS
797 * or %CLUTTER_KEY_RELEASE
798 * @key_code: the keycode representing the key
800 * Sets the keycode of the @event.
805 clutter_event_set_key_code (ClutterEvent *event,
808 g_return_if_fail (event != NULL);
809 g_return_if_fail (event->type == CLUTTER_KEY_PRESS ||
810 event->type == CLUTTER_KEY_RELEASE);
812 event->key.hardware_keycode = key_code;
816 * clutter_event_get_key_unicode:
817 * @event: a #ClutterEvent of type %CLUTTER_KEY_PRESS
818 * or %CLUTTER_KEY_RELEASE
820 * Retrieves the unicode value for the key that caused @keyev.
822 * Return value: The unicode value representing the key
825 clutter_event_get_key_unicode (const ClutterEvent *event)
827 g_return_val_if_fail (event != NULL, 0);
828 g_return_val_if_fail (event->type == CLUTTER_KEY_PRESS ||
829 event->type == CLUTTER_KEY_RELEASE, 0);
831 if (event->key.unicode_value)
832 return event->key.unicode_value;
834 return clutter_keysym_to_unicode (event->key.keyval);
838 * clutter_event_set_key_unicode:
839 * @event: a #ClutterEvent of type %CLUTTER_KEY_PRESS
840 * or %CLUTTER_KEY_RELEASE
841 * @key_unicode: the Unicode value representing the key
843 * Sets the Unicode value of @event.
848 clutter_event_set_key_unicode (ClutterEvent *event,
851 g_return_if_fail (event != NULL);
852 g_return_if_fail (event->type == CLUTTER_KEY_PRESS ||
853 event->type == CLUTTER_KEY_RELEASE);
855 event->key.unicode_value = key_unicode;
859 * clutter_event_get_event_sequence:
860 * @event: a #ClutterEvent of type %CLUTTER_TOUCH_BEGIN,
861 * %CLUTTER_TOUCH_UPDATE, %CLUTTER_TOUCH_END, or
862 * %CLUTTER_TOUCH_CANCEL
864 * Retrieves the #ClutterEventSequence of @event.
866 * Return value: (transfer none): the event sequence, or %NULL
870 ClutterEventSequence *
871 clutter_event_get_event_sequence (const ClutterEvent *event)
873 g_return_val_if_fail (event != NULL, NULL);
875 if (event->type == CLUTTER_TOUCH_BEGIN ||
876 event->type == CLUTTER_TOUCH_UPDATE ||
877 event->type == CLUTTER_TOUCH_END ||
878 event->type == CLUTTER_TOUCH_CANCEL)
879 return event->touch.sequence;
885 * clutter_event_get_device_id:
886 * @event: a clutter event
888 * Retrieves the events device id if set.
890 * Return value: A unique identifier for the device or -1 if the event has
891 * no specific device set.
894 clutter_event_get_device_id (const ClutterEvent *event)
896 ClutterInputDevice *device = NULL;
898 g_return_val_if_fail (event != NULL, CLUTTER_POINTER_DEVICE);
900 device = clutter_event_get_device (event);
902 return clutter_input_device_get_device_id (device);
908 * clutter_event_get_device_type:
909 * @event: a #ClutterEvent
911 * Retrieves the type of the device for @event
913 * Return value: the #ClutterInputDeviceType for the device, if
918 ClutterInputDeviceType
919 clutter_event_get_device_type (const ClutterEvent *event)
921 ClutterInputDevice *device = NULL;
923 g_return_val_if_fail (event != NULL, CLUTTER_POINTER_DEVICE);
925 device = clutter_event_get_device (event);
927 return clutter_input_device_get_device_type (device);
929 return CLUTTER_POINTER_DEVICE;
933 * clutter_event_set_device:
934 * @event: a #ClutterEvent
935 * @device: (allow-none): a #ClutterInputDevice, or %NULL
937 * Sets the device for @event.
942 clutter_event_set_device (ClutterEvent *event,
943 ClutterInputDevice *device)
945 g_return_if_fail (event != NULL);
946 g_return_if_fail (device == NULL || CLUTTER_IS_INPUT_DEVICE (device));
948 if (is_event_allocated (event))
950 ClutterEventPrivate *real_event = (ClutterEventPrivate *) event;
952 real_event->device = device;
957 case CLUTTER_NOTHING:
958 case CLUTTER_STAGE_STATE:
959 case CLUTTER_DESTROY_NOTIFY:
960 case CLUTTER_CLIENT_MESSAGE:
962 case CLUTTER_EVENT_LAST:
967 event->crossing.device = device;
970 case CLUTTER_BUTTON_PRESS:
971 case CLUTTER_BUTTON_RELEASE:
972 event->button.device = device;
976 event->motion.device = device;
980 event->scroll.device = device;
983 case CLUTTER_TOUCH_BEGIN:
984 case CLUTTER_TOUCH_UPDATE:
985 case CLUTTER_TOUCH_END:
986 case CLUTTER_TOUCH_CANCEL:
987 event->touch.device = device;
990 case CLUTTER_KEY_PRESS:
991 case CLUTTER_KEY_RELEASE:
992 event->key.device = device;
998 * clutter_event_get_device:
999 * @event: a #ClutterEvent
1001 * Retrieves the #ClutterInputDevice for the event.
1003 * The #ClutterInputDevice structure is completely opaque and should
1004 * be cast to the platform-specific implementation.
1006 * Return value: (transfer none): the #ClutterInputDevice or %NULL. The
1007 * returned device is owned by the #ClutterEvent and it should not
1012 ClutterInputDevice *
1013 clutter_event_get_device (const ClutterEvent *event)
1015 ClutterInputDevice *device = NULL;
1017 g_return_val_if_fail (event != NULL, NULL);
1019 if (is_event_allocated (event))
1021 ClutterEventPrivate *real_event = (ClutterEventPrivate *) event;
1023 if (real_event->device != NULL)
1024 return real_event->device;
1027 switch (event->type)
1029 case CLUTTER_NOTHING:
1030 case CLUTTER_STAGE_STATE:
1031 case CLUTTER_DESTROY_NOTIFY:
1032 case CLUTTER_CLIENT_MESSAGE:
1033 case CLUTTER_DELETE:
1034 case CLUTTER_EVENT_LAST:
1039 device = event->crossing.device;
1042 case CLUTTER_BUTTON_PRESS:
1043 case CLUTTER_BUTTON_RELEASE:
1044 device = event->button.device;
1047 case CLUTTER_MOTION:
1048 device = event->motion.device;
1051 case CLUTTER_SCROLL:
1052 device = event->scroll.device;
1055 case CLUTTER_TOUCH_BEGIN:
1056 case CLUTTER_TOUCH_UPDATE:
1057 case CLUTTER_TOUCH_END:
1058 case CLUTTER_TOUCH_CANCEL:
1059 device = event->touch.device;
1062 case CLUTTER_KEY_PRESS:
1063 case CLUTTER_KEY_RELEASE:
1064 device = event->key.device;
1072 * clutter_event_new:
1073 * @type: The type of event.
1075 * Creates a new #ClutterEvent of the specified type.
1077 * Return value: (transfer full): A newly allocated #ClutterEvent.
1080 clutter_event_new (ClutterEventType type)
1082 ClutterEvent *new_event;
1083 ClutterEventPrivate *priv;
1085 priv = g_slice_new0 (ClutterEventPrivate);
1087 new_event = (ClutterEvent *) priv;
1088 new_event->type = new_event->any.type = type;
1090 if (G_UNLIKELY (all_events == NULL))
1091 all_events = g_hash_table_new (NULL, NULL);
1093 g_hash_table_replace (all_events, priv, GUINT_TO_POINTER (1));
1099 * clutter_event_copy:
1100 * @event: A #ClutterEvent.
1104 * Return value: (transfer full): A newly allocated #ClutterEvent
1107 clutter_event_copy (const ClutterEvent *event)
1109 ClutterEvent *new_event;
1110 ClutterEventPrivate *new_real_event;
1111 ClutterInputDevice *device;
1114 g_return_val_if_fail (event != NULL, NULL);
1116 new_event = clutter_event_new (CLUTTER_NOTHING);
1117 new_real_event = (ClutterEventPrivate *) new_event;
1119 *new_event = *event;
1121 if (is_event_allocated (event))
1123 ClutterEventPrivate *real_event = (ClutterEventPrivate *) event;
1125 new_real_event->device = real_event->device;
1126 new_real_event->source_device = real_event->source_device;
1127 new_real_event->delta_x = real_event->delta_x;
1128 new_real_event->delta_y = real_event->delta_y;
1131 device = clutter_event_get_device (event);
1133 n_axes = clutter_input_device_get_n_axes (device);
1135 switch (event->type)
1137 case CLUTTER_BUTTON_PRESS:
1138 case CLUTTER_BUTTON_RELEASE:
1139 if (event->button.axes != NULL)
1140 new_event->button.axes = g_memdup (event->button.axes,
1141 sizeof (gdouble) * n_axes);
1144 case CLUTTER_SCROLL:
1145 if (event->scroll.axes != NULL)
1146 new_event->scroll.axes = g_memdup (event->scroll.axes,
1147 sizeof (gdouble) * n_axes);
1150 case CLUTTER_MOTION:
1151 if (event->motion.axes != NULL)
1152 new_event->motion.axes = g_memdup (event->motion.axes,
1153 sizeof (gdouble) * n_axes);
1156 case CLUTTER_TOUCH_BEGIN:
1157 case CLUTTER_TOUCH_UPDATE:
1158 case CLUTTER_TOUCH_END:
1159 case CLUTTER_TOUCH_CANCEL:
1160 if (event->touch.axes != NULL)
1161 new_event->touch.axes = g_memdup (event->motion.axes,
1162 sizeof (gdouble) * n_axes);
1169 if (is_event_allocated (event))
1170 _clutter_backend_copy_event_data (clutter_get_default_backend (),
1178 * clutter_event_free:
1179 * @event: A #ClutterEvent.
1181 * Frees all resources used by @event.
1184 clutter_event_free (ClutterEvent *event)
1186 if (G_LIKELY (event != NULL))
1188 _clutter_backend_free_event_data (clutter_get_default_backend (), event);
1190 switch (event->type)
1192 case CLUTTER_BUTTON_PRESS:
1193 case CLUTTER_BUTTON_RELEASE:
1194 g_free (event->button.axes);
1197 case CLUTTER_MOTION:
1198 g_free (event->motion.axes);
1201 case CLUTTER_SCROLL:
1202 g_free (event->scroll.axes);
1205 case CLUTTER_TOUCH_BEGIN:
1206 case CLUTTER_TOUCH_UPDATE:
1207 case CLUTTER_TOUCH_END:
1208 case CLUTTER_TOUCH_CANCEL:
1209 g_free (event->touch.axes);
1216 g_hash_table_remove (all_events, event);
1217 g_slice_free (ClutterEventPrivate, (ClutterEventPrivate *) event);
1222 * clutter_event_get:
1224 * Pops an event off the event queue. Applications should not need to call
1227 * Return value: A #ClutterEvent or NULL if queue empty
1232 clutter_event_get (void)
1234 ClutterMainContext *context = _clutter_context_get_default ();
1236 if (context->events_queue == NULL)
1239 if (g_queue_is_empty (context->events_queue))
1242 return g_queue_pop_tail (context->events_queue);
1246 * clutter_event_peek:
1248 * Returns a pointer to the first event from the event queue but
1249 * does not remove it.
1251 * Return value: (transfer none): A #ClutterEvent or NULL if queue empty.
1256 clutter_event_peek (void)
1258 ClutterMainContext *context = _clutter_context_get_default ();
1260 g_return_val_if_fail (context != NULL, NULL);
1262 if (context->events_queue == NULL)
1265 if (g_queue_is_empty (context->events_queue))
1268 return g_queue_peek_tail (context->events_queue);
1272 _clutter_event_push (const ClutterEvent *event,
1275 ClutterMainContext *context = _clutter_context_get_default ();
1276 ClutterInputDevice *device;
1278 g_assert (context != NULL);
1280 if (context->events_queue == NULL)
1281 context->events_queue = g_queue_new ();
1283 /* disabled devices don't propagate events */
1284 device = clutter_event_get_device (event);
1287 if (!clutter_input_device_get_enabled (device))
1295 copy = clutter_event_copy (event);
1299 g_queue_push_head (context->events_queue, (gpointer) event);
1303 * clutter_event_put:
1304 * @event: a #ClutterEvent
1306 * Puts a copy of the event on the back of the event queue. The event will
1307 * have the %CLUTTER_EVENT_FLAG_SYNTHETIC flag set. If the source is set
1308 * event signals will be emitted for this source and capture/bubbling for
1309 * its ancestors. If the source is not set it will be generated by picking
1310 * or use the actor that currently has keyboard focus
1315 clutter_event_put (const ClutterEvent *event)
1317 _clutter_event_push (event, TRUE);
1321 * clutter_events_pending:
1323 * Checks if events are pending in the event queue.
1325 * Return value: TRUE if there are pending events, FALSE otherwise.
1330 clutter_events_pending (void)
1332 ClutterMainContext *context = _clutter_context_get_default ();
1334 g_return_val_if_fail (context != NULL, FALSE);
1336 if (context->events_queue == NULL)
1339 return g_queue_is_empty (context->events_queue) == FALSE;
1343 * clutter_get_current_event_time:
1345 * Retrieves the timestamp of the last event, if there is an
1346 * event or if the event has a timestamp.
1348 * Return value: the event timestamp, or %CLUTTER_CURRENT_TIME
1353 clutter_get_current_event_time (void)
1355 ClutterMainContext *context = _clutter_context_get_default ();
1357 g_return_val_if_fail (context != NULL, FALSE);
1359 if (context->last_event_time != 0)
1360 return context->last_event_time;
1362 return CLUTTER_CURRENT_TIME;
1366 * clutter_get_current_event:
1368 * If an event is currently being processed, return that event.
1369 * This function is intended to be used to access event state
1370 * that might not be exposed by higher-level widgets. For
1371 * example, to get the key modifier state from a Button 'clicked'
1374 * Return value: (transfer none): The current ClutterEvent, or %NULL if none
1378 const ClutterEvent *
1379 clutter_get_current_event (void)
1381 ClutterMainContext *context = _clutter_context_get_default ();
1383 g_return_val_if_fail (context != NULL, NULL);
1385 return context->current_event;
1389 * clutter_event_get_source_device:
1390 * @event: a #ClutterEvent
1392 * Retrieves the hardware device that originated the event.
1394 * If you need the virtual device, use clutter_event_get_device().
1396 * If no hardware device originated this event, this function will
1397 * return the same device as clutter_event_get_device().
1399 * Return value: (transfer none): a pointer to a #ClutterInputDevice
1404 ClutterInputDevice *
1405 clutter_event_get_source_device (const ClutterEvent *event)
1407 ClutterEventPrivate *real_event;
1409 if (!is_event_allocated (event))
1412 real_event = (ClutterEventPrivate *) event;
1414 if (real_event->source_device != NULL)
1415 return real_event->source_device;
1417 return clutter_event_get_device (event);
1421 * clutter_event_set_source_device:
1422 * @event: a #ClutterEvent
1423 * @device: (allow-none): a #ClutterInputDevice
1425 * Sets the source #ClutterInputDevice for @event.
1427 * The #ClutterEvent must have been created using clutter_event_new().
1432 clutter_event_set_source_device (ClutterEvent *event,
1433 ClutterInputDevice *device)
1435 ClutterEventPrivate *real_event;
1437 g_return_if_fail (event != NULL);
1438 g_return_if_fail (device == NULL || CLUTTER_IS_INPUT_DEVICE (device));
1440 if (!is_event_allocated (event))
1443 real_event = (ClutterEventPrivate *) event;
1444 real_event->source_device = device;
1448 * clutter_event_get_axes:
1449 * @event: a #ClutterEvent
1450 * @n_axes: (out): return location for the number of axes returned
1452 * Retrieves the array of axes values attached to the event.
1454 * Return value: (transfer none): an array of axis values
1459 clutter_event_get_axes (const ClutterEvent *event,
1462 gdouble *retval = NULL;
1465 switch (event->type)
1467 case CLUTTER_NOTHING:
1468 case CLUTTER_STAGE_STATE:
1469 case CLUTTER_DESTROY_NOTIFY:
1470 case CLUTTER_CLIENT_MESSAGE:
1471 case CLUTTER_DELETE:
1474 case CLUTTER_KEY_PRESS:
1475 case CLUTTER_KEY_RELEASE:
1476 case CLUTTER_EVENT_LAST:
1479 case CLUTTER_SCROLL:
1480 retval = event->scroll.axes;
1483 case CLUTTER_BUTTON_PRESS:
1484 case CLUTTER_BUTTON_RELEASE:
1485 retval = event->button.axes;
1488 case CLUTTER_TOUCH_BEGIN:
1489 case CLUTTER_TOUCH_UPDATE:
1490 case CLUTTER_TOUCH_END:
1491 case CLUTTER_TOUCH_CANCEL:
1492 retval = event->touch.axes;
1495 case CLUTTER_MOTION:
1496 retval = event->motion.axes;
1502 ClutterInputDevice *device;
1504 device = clutter_event_get_device (event);
1506 len = clutter_input_device_get_n_axes (device);