gdk: Add enum to indicate the unit of scroll deltas

Add a new GdkScrollUnit enum that represent the
unit of scroll deltas provided by GdkScrollEvent.
The unit is accessible through
gdk_scroll_event_get_unit().
This commit is contained in:
panoplie 2022-02-21 16:22:57 +01:00
parent 8f9ee48aaa
commit fb4927827b
7 changed files with 97 additions and 13 deletions

View File

@ -597,7 +597,8 @@ _gdk_event_unqueue (GdkDisplay *display)
/*
* If the last N events in the event queue are smooth scroll events
* for the same surface and device, combine them into one.
* for the same surface, the same device and the same scroll unit,
* combine them into one.
*
* We give the remaining event a history with N items, and deltas
* that are the sum over the history entries.
@ -611,6 +612,8 @@ gdk_event_queue_handle_scroll_compression (GdkDisplay *display)
GdkEvent *last_event = NULL;
GList *scrolls = NULL;
GArray *history = NULL;
GdkScrollUnit scroll_unit = GDK_SCROLL_UNIT_WHEEL;
gboolean scroll_unit_defined = FALSE;
GdkTimeCoord hist;
l = g_queue_peek_tail_link (&display->queued_events);
@ -618,6 +621,7 @@ gdk_event_queue_handle_scroll_compression (GdkDisplay *display)
while (l)
{
GdkEvent *event = l->data;
GdkScrollEvent *scroll_event = (GdkScrollEvent *) event;
if (event->flags & GDK_EVENT_PENDING)
break;
@ -634,11 +638,17 @@ gdk_event_queue_handle_scroll_compression (GdkDisplay *display)
device != event->device)
break;
if (scroll_unit_defined &&
scroll_unit != scroll_event->unit)
break;
if (!last_event)
last_event = event;
surface = event->surface;
device = event->device;
scroll_unit = scroll_event->unit;
scroll_unit_defined = TRUE;
scrolls = l;
l = l->prev;
@ -710,7 +720,8 @@ gdk_event_queue_handle_scroll_compression (GdkDisplay *display)
gdk_event_get_modifier_state (old_event),
dx,
dy,
gdk_scroll_event_is_stop (old_event));
gdk_scroll_event_is_stop (old_event),
scroll_unit);
((GdkScrollEvent *)event)->history = history;
@ -2334,7 +2345,8 @@ gdk_scroll_event_new (GdkSurface *surface,
GdkModifierType state,
double delta_x,
double delta_y,
gboolean is_stop)
gboolean is_stop,
GdkScrollUnit unit)
{
GdkScrollEvent *self = gdk_event_alloc (GDK_SCROLL, surface, device, time);
@ -2344,6 +2356,7 @@ gdk_scroll_event_new (GdkSurface *surface,
self->delta_x = delta_x;
self->delta_y = delta_y;
self->is_stop = is_stop;
self->unit = unit;
return (GdkEvent *) self;
}
@ -2363,6 +2376,7 @@ gdk_scroll_event_new_discrete (GdkSurface *surface,
self->state = state;
self->direction = direction;
self->pointer_emulated = emulated;
self->unit = GDK_SCROLL_UNIT_WHEEL;
return (GdkEvent *) self;
}
@ -2396,6 +2410,9 @@ gdk_scroll_event_get_direction (GdkEvent *event)
*
* The deltas will be zero unless the scroll direction
* is %GDK_SCROLL_SMOOTH.
*
* For the representation unit of these deltas, see
* [method@Gdk.ScrollEvent.get_unit].
*/
void
gdk_scroll_event_get_deltas (GdkEvent *event,
@ -2438,6 +2455,31 @@ gdk_scroll_event_is_stop (GdkEvent *event)
return self->is_stop;
}
/**
* gdk_scroll_event_get_unit:
* @event: (type GdkScrollEvent): a scroll event.
*
* Extracts the scroll delta unit of a scroll event.
*
* The unit will always be %GDK_SCROLL_UNIT_WHEEL if the scroll direction is not
* %GDK_SCROLL_SMOOTH.
*
* Returns: the scroll unit.
*
* Since: 4.8
*/
GdkScrollUnit
gdk_scroll_event_get_unit (GdkEvent *event)
{
GdkScrollEvent *self = (GdkScrollEvent *) event;
g_return_val_if_fail (GDK_IS_EVENT (event), GDK_SCROLL_UNIT_WHEEL);
g_return_val_if_fail (GDK_IS_EVENT_TYPE (event, GDK_SCROLL),
GDK_SCROLL_UNIT_WHEEL);
return self->unit;
}
/* }}} */
/* {{{ GdkTouchpadEvent */

View File

@ -265,6 +265,37 @@ typedef enum
GDK_SCROLL_SMOOTH
} GdkScrollDirection;
/**
* GdkScrollUnit:
* @GDK_SCROLL_UNIT_WHEEL: The delta is in number of wheel clicks.
* @GDK_SCROLL_UNIT_SURFACE: The delta is in surface pixels to scroll directly
* on screen.
*
* Specifies the unit of scroll deltas.
*
* When you get %GDK_SCROLL_UNIT_WHEEL, a delta of 1.0 means 1 wheel detent
* click in the south direction, 2.0 means 2 wheel detent clicks in the south
* direction... This is the same logic for negative values but in the north
* direction.
*
* If you get %GDK_SCROLL_UNIT_SURFACE, are managing a scrollable view and get a
* value of 123, you have to scroll 123 surface logical pixels right if it's
* @delta_x or down if it's @delta_y. This is the same logic for negative values
* but you have to scroll left instead of right if it's @delta_x and up instead
* of down if it's @delta_y.
*
* 1 surface logical pixel is equal to 1 real screen pixel multiplied by the
* final scale factor of your graphical interface (the product of the desktop
* scale factor and eventually a custom scale factor in your app).
*
* Since: 4.8
*/
typedef enum
{
GDK_SCROLL_UNIT_WHEEL,
GDK_SCROLL_UNIT_SURFACE
} GdkScrollUnit;
/**
* GdkNotifyType:
* @GDK_NOTIFY_ANCESTOR: the surface is entered from an ancestor or
@ -395,6 +426,8 @@ GDK_AVAILABLE_IN_ALL
void gdk_scroll_event_get_deltas (GdkEvent *event,
double *delta_x,
double *delta_y);
GDK_AVAILABLE_IN_4_8
GdkScrollUnit gdk_scroll_event_get_unit (GdkEvent *event);
GDK_AVAILABLE_IN_ALL
gboolean gdk_scroll_event_is_stop (GdkEvent *event);

View File

@ -212,6 +212,7 @@ struct _GdkTouchEvent
* @history: (element-type GdkTimeCoord): array of times and deltas
* for other scroll events that were compressed before delivering the
* current event
* @unit: The scroll unit in which delta_x and delta_y are represented.
*
* Generated from button presses for the buttons 4 to 7. Wheel mice are
* usually configured to generate button press events for buttons 4 and 5
@ -234,6 +235,7 @@ struct _GdkScrollEvent
gboolean is_stop;
GdkDeviceTool *tool;
GArray *history; /* <GdkTimeCoord> */
GdkScrollUnit unit;
};
/*
@ -486,7 +488,8 @@ GdkEvent * gdk_scroll_event_new (GdkSurface *surface,
GdkModifierType state,
double delta_x,
double delta_y,
gboolean is_stop);
gboolean is_stop,
GdkScrollUnit unit);
GdkEvent * gdk_scroll_event_new_discrete (GdkSurface *surface,
GdkDevice *device,

View File

@ -665,7 +665,8 @@ fill_scroll_event (GdkMacosDisplay *self,
state,
-sx,
-sy,
FALSE);
FALSE,
GDK_SCROLL_UNIT_SURFACE);
/* Fall through for scroll emulation */
}
@ -714,7 +715,8 @@ fill_scroll_event (GdkMacosDisplay *self,
NULL,
get_time_from_ns_event (nsevent),
state,
0.0, 0.0, TRUE);
0.0, 0.0, TRUE,
GDK_SCROLL_UNIT_SURFACE);
}
return g_steal_pointer (&ret);

View File

@ -1416,7 +1416,8 @@ flush_smooth_scroll_event (GdkWaylandSeat *seat,
seat->pointer_info.time,
device_get_modifiers (seat->logical_pointer),
delta_x, delta_y,
is_stop);
is_stop,
GDK_SCROLL_UNIT_SURFACE);
_gdk_wayland_display_deliver_event (seat->display, event);
}
@ -1755,10 +1756,10 @@ pointer_handle_axis (void *data,
switch (axis)
{
case WL_POINTER_AXIS_VERTICAL_SCROLL:
pointer_frame->delta_y = wl_fixed_to_double (value) / 10.0;
pointer_frame->delta_y = wl_fixed_to_double (value);
break;
case WL_POINTER_AXIS_HORIZONTAL_SCROLL:
pointer_frame->delta_x = wl_fixed_to_double (value) / 10.0;
pointer_frame->delta_x = wl_fixed_to_double (value);
break;
default:
g_return_if_reached ();
@ -1768,7 +1769,7 @@ pointer_handle_axis (void *data,
GDK_SEAT_NOTE (seat, EVENTS,
g_message ("scroll, axis %s, value %f, seat %p",
get_axis_name (axis), wl_fixed_to_double (value) / 10.0,
get_axis_name (axis), wl_fixed_to_double (value),
seat));
if (display->seat_version < WL_POINTER_HAS_FRAME)
@ -3994,7 +3995,8 @@ tablet_tool_handle_wheel (void *data,
tablet->pointer_info.time,
device_get_modifiers (tablet->logical_device),
0, clicks,
FALSE);
FALSE,
GDK_SCROLL_UNIT_WHEEL);
_gdk_wayland_display_deliver_event (seat->display, event);

View File

@ -2742,7 +2742,8 @@ gdk_event_translate (MSG *msg,
build_pointer_event_state (msg),
delta_x,
delta_y,
FALSE);
FALSE,
GDK_SCROLL_UNIT_WHEEL);
/* Append the discrete version too */
direction = 0;

View File

@ -1778,7 +1778,8 @@ gdk_x11_device_manager_xi2_translate_event (GdkEventTranslator *translator,
state,
delta_x,
delta_y,
delta_x == 0.0 && delta_y == 0.0);
delta_x == 0.0 && delta_y == 0.0,
GDK_SCROLL_UNIT_WHEEL);
}
break;
}