diff --git a/gdk/gdkevents.c b/gdk/gdkevents.c index e63c54fcb4..6bb9c91a74 100644 --- a/gdk/gdkevents.c +++ b/gdk/gdkevents.c @@ -1174,9 +1174,16 @@ gdk_event_get_axes (GdkEvent *event, double **axes, guint *n_axes) { + gboolean ret; + g_return_val_if_fail (GDK_IS_EVENT (event), FALSE); - return GDK_EVENT_GET_CLASS (event)->get_axes (event, axes, n_axes); + ret = GDK_EVENT_GET_CLASS (event)->get_axes (event, axes, n_axes); + + if (*axes == NULL) + return FALSE; + + return ret; } double * diff --git a/gtk/gtkgesturestylus.c b/gtk/gtkgesturestylus.c index d10dfe1a05..bc3da9351d 100644 --- a/gtk/gtkgesturestylus.c +++ b/gtk/gtkgesturestylus.c @@ -34,7 +34,16 @@ #include "gtkmain.h" #include "gtknative.h" -G_DEFINE_TYPE (GtkGestureStylus, gtk_gesture_stylus, GTK_TYPE_GESTURE_SINGLE) +typedef struct { + gboolean stylus_only; +} GtkGestureStylusPrivate; + +G_DEFINE_TYPE_WITH_PRIVATE (GtkGestureStylus, gtk_gesture_stylus, GTK_TYPE_GESTURE_SINGLE) + +enum { + PROP_STYLUS_ONLY = 1, + N_PROPERTIES +}; enum { PROXIMITY, @@ -44,20 +53,57 @@ enum { N_SIGNALS }; +static GParamSpec *obj_properties[N_PROPERTIES] = { NULL, }; static guint signals[N_SIGNALS] = { 0, }; +static void gtk_gesture_stylus_get_property (GObject *object, + guint prop_id, + GValue *value, + GParamSpec *pspec) +{ + GtkGestureStylus *gesture = GTK_GESTURE_STYLUS (object); + + switch (prop_id) + { + case PROP_STYLUS_ONLY: + g_value_set_boolean (value, gtk_gesture_stylus_get_stylus_only (gesture)); + break; + default: + G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); + } +} + +static void gtk_gesture_stylus_set_property (GObject *object, + guint prop_id, + const GValue *value, + GParamSpec *pspec) +{ + GtkGestureStylus *gesture = GTK_GESTURE_STYLUS (object); + + switch (prop_id) + { + case PROP_STYLUS_ONLY: + gtk_gesture_stylus_set_stylus_only (gesture, g_value_get_boolean (value)); + break; + default: + G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); + } +} + static gboolean gtk_gesture_stylus_handle_event (GtkEventController *controller, GdkEvent *event, double x, double y) { + GtkGestureStylusPrivate* priv; GdkModifierType modifiers; guint n_signal; + priv = gtk_gesture_stylus_get_instance_private (GTK_GESTURE_STYLUS (controller)); GTK_EVENT_CONTROLLER_CLASS (gtk_gesture_stylus_parent_class)->handle_event (controller, event, x, y); - if (!gdk_event_get_device_tool (event)) + if (!(priv->stylus_only || gdk_event_get_device_tool (event))) return FALSE; switch ((guint) gdk_event_get_event_type (event)) @@ -88,8 +134,27 @@ gtk_gesture_stylus_handle_event (GtkEventController *controller, static void gtk_gesture_stylus_class_init (GtkGestureStylusClass *klass) { + GObjectClass* object_class; GtkEventControllerClass *event_controller_class; + object_class = G_OBJECT_CLASS (klass); + object_class->get_property = gtk_gesture_stylus_get_property; + object_class->set_property = gtk_gesture_stylus_set_property; + + /** + * GtkGestureStylus:stylus-only: (attributes org.gtk.Property.get=gtk_gesture_stylus_get_stylus_only org.gtk.Property.set=gtk_gesture_stylus_set_stylus_only) + * + * If this gesture should exclusively react to stylus input devices. + * + * Since: 4.10 + */ + obj_properties[PROP_STYLUS_ONLY] = g_param_spec_boolean ("stylus-only", NULL, NULL, + TRUE, + G_PARAM_READWRITE | + G_PARAM_EXPLICIT_NOTIFY | + G_PARAM_CONSTRUCT); + g_object_class_install_properties (object_class, N_PROPERTIES, obj_properties); + event_controller_class = GTK_EVENT_CONTROLLER_CLASS (klass); event_controller_class->handle_event = gtk_gesture_stylus_handle_event; @@ -177,6 +242,9 @@ gtk_gesture_stylus_class_init (GtkGestureStylusClass *klass) static void gtk_gesture_stylus_init (GtkGestureStylus *gesture) { + GtkGestureStylusPrivate* priv = gtk_gesture_stylus_get_instance_private(gesture); + + priv->stylus_only = TRUE; } /** @@ -193,6 +261,56 @@ gtk_gesture_stylus_new (void) NULL); } +/** + * gtk_gesture_stylus_get_stylus_only: (attributes org.gtk.Method.get_property=stylus-only) + * @gesture: the gesture + * + * Checks whether the gesture is for styluses only. + * + * Stylus-only gestures will signal events exclusively from stylus + * input devices. + * + * Returns: %TRUE if the gesture is only for stylus events + * + * Since: 4.10 + */ +gboolean +gtk_gesture_stylus_get_stylus_only (GtkGestureStylus *gesture) +{ + GtkGestureStylusPrivate *priv = gtk_gesture_stylus_get_instance_private (gesture); + + g_return_val_if_fail (GTK_IS_GESTURE_STYLUS (gesture), FALSE); + + return priv->stylus_only; +} + +/** + * gtk_gesture_stylus_set_stylus_only: (attributes org.gtk.Method.set_property=stylus-only) + * @gesture: the gesture + * @stylus_only: whether the gesture is used exclusivly for stylus events + * + * Sets the state of stylus-only + * + * If true, the gesture will exclusivly handle events from stylus input deivces, + * otherwise it'll handle events from any pointing device. + * + * Since: 4.10 + */ +void +gtk_gesture_stylus_set_stylus_only (GtkGestureStylus *gesture, gboolean stylus_only) +{ + GtkGestureStylusPrivate *priv = gtk_gesture_stylus_get_instance_private (gesture); + + g_return_if_fail (GTK_IS_GESTURE_STYLUS (gesture)); + + if (priv->stylus_only == stylus_only) + return; + + priv->stylus_only = stylus_only; + + g_object_notify_by_pspec (G_OBJECT (gesture), obj_properties[PROP_STYLUS_ONLY]); +} + /** * gtk_gesture_stylus_get_axis: * @gesture: a `GtkGestureStylus` diff --git a/gtk/gtkgesturestylus.h b/gtk/gtkgesturestylus.h index df31f5277a..ea7784d249 100644 --- a/gtk/gtkgesturestylus.h +++ b/gtk/gtkgesturestylus.h @@ -43,6 +43,12 @@ GType gtk_gesture_stylus_get_type (void) G_GNUC_CONST; GDK_AVAILABLE_IN_ALL GtkGesture * gtk_gesture_stylus_new (void); +GDK_AVAILABLE_IN_4_10 +gboolean gtk_gesture_stylus_get_stylus_only (GtkGestureStylus *gesture); +GDK_AVAILABLE_IN_4_10 +void gtk_gesture_stylus_set_stylus_only (GtkGestureStylus *gesture, + gboolean stylus_only); + GDK_AVAILABLE_IN_ALL gboolean gtk_gesture_stylus_get_axis (GtkGestureStylus *gesture, GdkAxisUse axis,