1 | //! Pointer event types |
2 | #![allow (deprecated)] |
3 | |
4 | use super::EventTrait; |
5 | use crate::{ffi, AsRaw, Context, FromRaw, Libinput}; |
6 | |
7 | /// Common functions for all Pointer-Events implement. |
8 | pub trait PointerEventTrait: AsRaw<ffi::libinput_event_pointer> + Context { |
9 | ffi_func!( |
10 | /// The event time for this event |
11 | fn time, ffi::libinput_event_pointer_get_time, u32); |
12 | ffi_func!( |
13 | /// The event time for this event in microseconds |
14 | fn time_usec, ffi::libinput_event_pointer_get_time_usec, u64); |
15 | |
16 | /// Convert into a general `TouchEvent` again |
17 | fn into_pointer_event(self) -> PointerEvent |
18 | where |
19 | Self: Sized, |
20 | { |
21 | unsafe { PointerEvent::from_raw(self.as_raw_mut(), self.context()) } |
22 | } |
23 | } |
24 | |
25 | impl<T: AsRaw<ffi::libinput_event_pointer> + Context> PointerEventTrait for T {} |
26 | |
27 | /// A pointer related `Event` |
28 | #[derive (Debug, PartialEq, Eq, Hash)] |
29 | #[non_exhaustive ] |
30 | pub enum PointerEvent { |
31 | /// An event related to moving a pointer |
32 | Motion(PointerMotionEvent), |
33 | /// An event related to absolute pointer movement |
34 | MotionAbsolute(PointerMotionAbsoluteEvent), |
35 | /// An event related to button pressed on a pointer device |
36 | Button(PointerButtonEvent), |
37 | /// An event related to moving axis on a pointer device |
38 | #[cfg_attr ( |
39 | feature = "libinput_1_19" , |
40 | deprecated = "Use `PointerEvent::Scroll*` events instead" |
41 | )] |
42 | Axis(PointerAxisEvent), |
43 | /// A scroll event from a wheel. |
44 | #[cfg (feature = "libinput_1_19" )] |
45 | ScrollWheel(PointerScrollWheelEvent), |
46 | /// A scroll event caused by the movement of one or more fingers on a device. |
47 | #[cfg (feature = "libinput_1_19" )] |
48 | ScrollFinger(PointerScrollFingerEvent), |
49 | /// A scroll event from a continuous scroll source, e.g. button scrolling. |
50 | #[cfg (feature = "libinput_1_19" )] |
51 | ScrollContinuous(PointerScrollContinuousEvent), |
52 | } |
53 | |
54 | impl EventTrait for PointerEvent { |
55 | #[doc (hidden)] |
56 | fn as_raw_event(&self) -> *mut ffi::libinput_event { |
57 | match self { |
58 | PointerEvent::Motion(event: &PointerMotionEvent) => event.as_raw_event(), |
59 | PointerEvent::MotionAbsolute(event: &PointerMotionAbsoluteEvent) => event.as_raw_event(), |
60 | PointerEvent::Button(event: &PointerButtonEvent) => event.as_raw_event(), |
61 | PointerEvent::Axis(event: &PointerAxisEvent) => event.as_raw_event(), |
62 | #[cfg (feature = "libinput_1_19" )] |
63 | PointerEvent::ScrollWheel(event: &PointerScrollWheelEvent) => event.as_raw_event(), |
64 | #[cfg (feature = "libinput_1_19" )] |
65 | PointerEvent::ScrollFinger(event: &PointerScrollFingerEvent) => event.as_raw_event(), |
66 | #[cfg (feature = "libinput_1_19" )] |
67 | PointerEvent::ScrollContinuous(event: &PointerScrollContinuousEvent) => event.as_raw_event(), |
68 | } |
69 | } |
70 | } |
71 | |
72 | impl FromRaw<ffi::libinput_event_pointer> for PointerEvent { |
73 | unsafe fn try_from_raw( |
74 | event: *mut ffi::libinput_event_pointer, |
75 | context: &Libinput, |
76 | ) -> Option<Self> { |
77 | let base = ffi::libinput_event_pointer_get_base_event(event); |
78 | match ffi::libinput_event_get_type(base) { |
79 | ffi::libinput_event_type_LIBINPUT_EVENT_POINTER_MOTION => Some(PointerEvent::Motion( |
80 | PointerMotionEvent::try_from_raw(event, context)?, |
81 | )), |
82 | ffi::libinput_event_type_LIBINPUT_EVENT_POINTER_MOTION_ABSOLUTE => { |
83 | Some(PointerEvent::MotionAbsolute( |
84 | PointerMotionAbsoluteEvent::try_from_raw(event, context)?, |
85 | )) |
86 | } |
87 | ffi::libinput_event_type_LIBINPUT_EVENT_POINTER_BUTTON => Some(PointerEvent::Button( |
88 | PointerButtonEvent::try_from_raw(event, context)?, |
89 | )), |
90 | ffi::libinput_event_type_LIBINPUT_EVENT_POINTER_AXIS => Some(PointerEvent::Axis( |
91 | PointerAxisEvent::try_from_raw(event, context)?, |
92 | )), |
93 | #[cfg (feature = "libinput_1_19" )] |
94 | ffi::libinput_event_type_LIBINPUT_EVENT_POINTER_SCROLL_WHEEL => Some( |
95 | PointerEvent::ScrollWheel(PointerScrollWheelEvent::try_from_raw(event, context)?), |
96 | ), |
97 | #[cfg (feature = "libinput_1_19" )] |
98 | ffi::libinput_event_type_LIBINPUT_EVENT_POINTER_SCROLL_FINGER => Some( |
99 | PointerEvent::ScrollFinger(PointerScrollFingerEvent::try_from_raw(event, context)?), |
100 | ), |
101 | #[cfg (feature = "libinput_1_19" )] |
102 | ffi::libinput_event_type_LIBINPUT_EVENT_POINTER_SCROLL_CONTINUOUS => { |
103 | Some(PointerEvent::ScrollContinuous( |
104 | PointerScrollContinuousEvent::try_from_raw(event, context)?, |
105 | )) |
106 | } |
107 | _ => None, |
108 | } |
109 | } |
110 | unsafe fn from_raw(event: *mut ffi::libinput_event_pointer, context: &Libinput) -> Self { |
111 | Self::try_from_raw(event, context).expect("Unknown pointer event type" ) |
112 | } |
113 | } |
114 | |
115 | impl AsRaw<ffi::libinput_event_pointer> for PointerEvent { |
116 | fn as_raw(&self) -> *const ffi::libinput_event_pointer { |
117 | match self { |
118 | PointerEvent::Motion(event: &PointerMotionEvent) => event.as_raw(), |
119 | PointerEvent::MotionAbsolute(event: &PointerMotionAbsoluteEvent) => event.as_raw(), |
120 | PointerEvent::Button(event: &PointerButtonEvent) => event.as_raw(), |
121 | PointerEvent::Axis(event: &PointerAxisEvent) => event.as_raw(), |
122 | #[cfg (feature = "libinput_1_19" )] |
123 | PointerEvent::ScrollWheel(event: &PointerScrollWheelEvent) => event.as_raw(), |
124 | #[cfg (feature = "libinput_1_19" )] |
125 | PointerEvent::ScrollFinger(event: &PointerScrollFingerEvent) => event.as_raw(), |
126 | #[cfg (feature = "libinput_1_19" )] |
127 | PointerEvent::ScrollContinuous(event: &PointerScrollContinuousEvent) => event.as_raw(), |
128 | } |
129 | } |
130 | } |
131 | |
132 | impl Context for PointerEvent { |
133 | fn context(&self) -> &Libinput { |
134 | match self { |
135 | PointerEvent::Motion(event: &PointerMotionEvent) => event.context(), |
136 | PointerEvent::MotionAbsolute(event: &PointerMotionAbsoluteEvent) => event.context(), |
137 | PointerEvent::Button(event: &PointerButtonEvent) => event.context(), |
138 | PointerEvent::Axis(event: &PointerAxisEvent) => event.context(), |
139 | #[cfg (feature = "libinput_1_19" )] |
140 | PointerEvent::ScrollWheel(event: &PointerScrollWheelEvent) => event.context(), |
141 | #[cfg (feature = "libinput_1_19" )] |
142 | PointerEvent::ScrollFinger(event: &PointerScrollFingerEvent) => event.context(), |
143 | #[cfg (feature = "libinput_1_19" )] |
144 | PointerEvent::ScrollContinuous(event: &PointerScrollContinuousEvent) => event.context(), |
145 | } |
146 | } |
147 | } |
148 | |
149 | ffi_event_struct!( |
150 | /// An event related to moving a pointer |
151 | struct PointerMotionEvent, ffi::libinput_event_pointer, ffi::libinput_event_pointer_get_base_event); |
152 | |
153 | impl PointerMotionEvent { |
154 | ffi_func!( |
155 | /// Return the delta between the last event and the current event. |
156 | /// |
157 | /// If a device employs pointer acceleration, the delta returned by this |
158 | /// function is the accelerated delta. |
159 | /// |
160 | /// Relative motion deltas are to be interpreted as pixel movement of a |
161 | /// standardized mouse. See [Normalization of relative motion](https://wayland.freedesktop.org/libinput/doc/latest/motion_normalization.html) |
162 | /// for more details. |
163 | pub fn dx, ffi::libinput_event_pointer_get_dx, f64); |
164 | ffi_func!( |
165 | /// Return the relative delta of the unaccelerated motion vector of the |
166 | /// current event. |
167 | /// |
168 | /// Relative unaccelerated motion deltas are raw device coordinates. Note that |
169 | /// these coordinates are subject to the device's native resolution. Touchpad |
170 | /// coordinates represent raw device coordinates in the X resolution of the |
171 | /// touchpad. See [Normalization of relative motion](https://wayland.freedesktop.org/libinput/doc/latest/motion_normalization.html) |
172 | /// for more details. |
173 | /// |
174 | /// Any rotation applied to the device also applies to unaccelerated motion |
175 | /// (see `Device::rotation_set_angle`). |
176 | pub fn dx_unaccelerated, ffi::libinput_event_pointer_get_dx_unaccelerated, f64); |
177 | ffi_func!( |
178 | /// Return the delta between the last event and the current event. |
179 | /// |
180 | /// If a device employs pointer acceleration, the delta returned by this |
181 | /// function is the accelerated delta. |
182 | /// |
183 | /// Relative motion deltas are to be interpreted as pixel movement of a |
184 | /// standardized mouse. See [Normalization of relative motion](https://wayland.freedesktop.org/libinput/doc/latest/motion_normalization.html) |
185 | /// for more details. |
186 | pub fn dy, ffi::libinput_event_pointer_get_dy, f64); |
187 | ffi_func!( |
188 | /// Return the relative delta of the unaccelerated motion vector of the |
189 | /// current event. |
190 | /// |
191 | /// Relative unaccelerated motion deltas are raw device coordinates. Note that |
192 | /// these coordinates are subject to the device's native resolution. Touchpad |
193 | /// coordinates represent raw device coordinates in the X resolution of the |
194 | /// touchpad. See [Normalization of relative motion](https://wayland.freedesktop.org/libinput/doc/latest/motion_normalization.html) |
195 | /// for more details. |
196 | /// |
197 | /// Any rotation applied to the device also applies to unaccelerated motion |
198 | /// (see `Device::rotation_set_angle`). |
199 | pub fn dy_unaccelerated, ffi::libinput_event_pointer_get_dy_unaccelerated, f64); |
200 | } |
201 | |
202 | ffi_event_struct!( |
203 | /// An event related to absolute pointer movement |
204 | struct PointerMotionAbsoluteEvent, ffi::libinput_event_pointer, ffi::libinput_event_pointer_get_base_event); |
205 | |
206 | impl PointerMotionAbsoluteEvent { |
207 | ffi_func!( |
208 | /// Return the current absolute x coordinate of the pointer event, in mm from |
209 | /// the top left corner of the device. |
210 | /// |
211 | /// To get the corresponding output screen coordinate, use |
212 | /// `absolute_x_transformed`. |
213 | pub fn absolute_x, ffi::libinput_event_pointer_get_absolute_x, f64); |
214 | ffi_func!( |
215 | /// Return the current absolute y coordinate of the pointer event, in mm from |
216 | /// the top left corner of the device. |
217 | /// |
218 | /// To get the corresponding output screen coordinate, use |
219 | /// `absolute_y_transformed`. |
220 | pub fn absolute_y, ffi::libinput_event_pointer_get_absolute_y, f64); |
221 | |
222 | /// Return the current absolute x coordinate of the pointer event, transformed |
223 | /// to screen coordinates. |
224 | /// |
225 | /// ## Arguments |
226 | /// |
227 | /// - width - The current output screen width |
228 | pub fn absolute_x_transformed(&self, width: u32) -> f64 { |
229 | unsafe { ffi::libinput_event_pointer_get_absolute_x_transformed(self.as_raw_mut(), width) } |
230 | } |
231 | |
232 | /// Return the current absolute y coordinate of the pointer event, transformed |
233 | /// to screen coordinates. |
234 | /// |
235 | /// ## Arguments |
236 | /// |
237 | /// - height - The current output screen height |
238 | pub fn absolute_y_transformed(&self, height: u32) -> f64 { |
239 | unsafe { ffi::libinput_event_pointer_get_absolute_y_transformed(self.as_raw_mut(), height) } |
240 | } |
241 | } |
242 | |
243 | /// State of a Button |
244 | #[derive (Debug, Clone, Copy, PartialEq, Eq, Hash)] |
245 | pub enum ButtonState { |
246 | /// Button is pressed |
247 | Pressed, |
248 | /// Button is released |
249 | Released, |
250 | } |
251 | |
252 | ffi_event_struct!( |
253 | /// An event related to button pressed on a pointer device |
254 | struct PointerButtonEvent, ffi::libinput_event_pointer, ffi::libinput_event_pointer_get_base_event); |
255 | |
256 | impl PointerButtonEvent { |
257 | ffi_func!( |
258 | /// Return the button that triggered this event. |
259 | pub fn button, ffi::libinput_event_pointer_get_button, u32); |
260 | ffi_func!( |
261 | /// For the button returns the total number of buttons pressed on all devices |
262 | /// on the associated seat after the event was triggered. |
263 | pub fn seat_button_count, ffi::libinput_event_pointer_get_seat_button_count, u32); |
264 | |
265 | /// Return the button state that triggered this event. |
266 | pub fn button_state(&self) -> ButtonState { |
267 | match unsafe { ffi::libinput_event_pointer_get_button_state(self.as_raw_mut()) } { |
268 | ffi::libinput_button_state_LIBINPUT_BUTTON_STATE_PRESSED => ButtonState::Pressed, |
269 | ffi::libinput_button_state_LIBINPUT_BUTTON_STATE_RELEASED => ButtonState::Released, |
270 | _ => panic!("libinput returned invalid 'libinput_button_state'" ), |
271 | } |
272 | } |
273 | } |
274 | |
275 | /// The source for a `PointerAxisEvent`. |
276 | #[cfg_attr ( |
277 | feature = "libinput_1_19" , |
278 | deprecated = "Use `PointerEvent::Scroll*` events instead" |
279 | )] |
280 | #[derive (Debug, Clone, Copy, PartialEq, Eq, Hash)] |
281 | pub enum AxisSource { |
282 | /// The event is caused by the rotation of a wheel. |
283 | Wheel, |
284 | /// The event is caused by the movement of one or more fingers on a device. |
285 | Finger, |
286 | /// The event is caused by the motion of some device. |
287 | Continuous, |
288 | /// The event is caused by the tilting of a mouse wheel rather than its rotation. |
289 | /// |
290 | /// This method is commonly used on mice without separate horizontal scroll wheels. |
291 | #[cfg_attr ( |
292 | feature = "libinput_1_19" , |
293 | deprecated = "No device has ever sent this source." |
294 | )] |
295 | WheelTilt, |
296 | } |
297 | |
298 | /// Axes on a device with the pointer capability that are not x or y coordinates. |
299 | /// |
300 | /// The two scroll axes `Vertical` and `Horizontal` are engaged separately, |
301 | /// depending on the device. libinput provides some scroll direction locking but |
302 | /// it is up to the caller to determine which axis is needed and appropriate in |
303 | /// the current interaction |
304 | #[derive (Debug, Clone, Copy, PartialEq, Eq, Hash)] |
305 | pub enum Axis { |
306 | /// Vertical axis |
307 | Vertical, |
308 | /// Horizontal axis |
309 | Horizontal, |
310 | } |
311 | |
312 | ffi_event_struct!( |
313 | /// An event related to moving axis on a pointer device |
314 | #[cfg_attr (feature = "libinput_1_19" , deprecated = "Use `PointerEvent::Scroll*` events instead" )] |
315 | struct PointerAxisEvent, ffi::libinput_event_pointer, ffi::libinput_event_pointer_get_base_event); |
316 | |
317 | impl PointerAxisEvent { |
318 | /// Check if the event has a valid value for the given axis. |
319 | /// |
320 | /// If this function returns true for an axis and `axis_value` returns a |
321 | /// value of 0, the event is a scroll stop event. |
322 | #[cfg_attr ( |
323 | feature = "libinput_1_19" , |
324 | deprecated = "Use `PointerScrollEvent::has_axis` instead" |
325 | )] |
326 | pub fn has_axis(&self, axis: Axis) -> bool { |
327 | unsafe { |
328 | ffi::libinput_event_pointer_has_axis( |
329 | self.as_raw_mut(), |
330 | match axis { |
331 | Axis::Vertical => { |
332 | ffi::libinput_pointer_axis_LIBINPUT_POINTER_AXIS_SCROLL_VERTICAL |
333 | } |
334 | Axis::Horizontal => { |
335 | ffi::libinput_pointer_axis_LIBINPUT_POINTER_AXIS_SCROLL_HORIZONTAL |
336 | } |
337 | }, |
338 | ) != 0 |
339 | } |
340 | } |
341 | |
342 | /// Return the source for a given axis event. |
343 | /// |
344 | /// Axis events (scroll events) can be caused by a hardware item such as a |
345 | /// scroll wheel or emulated from other input sources, such as two-finger or |
346 | /// edge scrolling on a touchpad. |
347 | /// |
348 | /// If the source is `Finger`, libinput guarantees that a scroll sequence is |
349 | /// terminated with a scroll value of 0. A caller may use this information to |
350 | /// decide on whether kinetic scrolling should be triggered on this scroll |
351 | /// sequence. The coordinate system is identical to the cursor movement, i.e. |
352 | /// a scroll value of 1 represents the equivalent relative motion of 1. |
353 | /// |
354 | /// If the source is `Wheel`, no terminating event is guaranteed (though it |
355 | /// may happen). Scrolling is in discrete steps, the value is the angle the |
356 | /// wheel moved in degrees. The default is 15 degrees per wheel click, but |
357 | /// some mice may have differently grained wheels. It is up to the caller how |
358 | /// to interpret such different step sizes. |
359 | /// |
360 | /// If the source is `Continuous`, no terminating event is guaranteed (though |
361 | /// it may happen). The coordinate system is identical to the cursor movement, |
362 | /// i.e. a scroll value of 1 represents the equivalent relative motion of 1. |
363 | /// |
364 | /// If the source is `WheelTilt`, no terminating event is guaranteed (though |
365 | /// it may happen). Scrolling is in discrete steps and there is no physical |
366 | /// equivalent for the value returned here. For backwards compatibility, the |
367 | /// value returned by this function is identical to a single mouse wheel |
368 | /// rotation by this device (see the documentation for `WheelTilt` above). |
369 | /// Callers should not use this value but instead exclusively refer to the |
370 | //. value returned by `axis_value_discrete`. |
371 | #[cfg_attr ( |
372 | feature = "libinput_1_19" , |
373 | deprecated = "Use `PointerScroll*` events instead" |
374 | )] |
375 | pub fn axis_source(&self) -> AxisSource { |
376 | match unsafe { ffi::libinput_event_pointer_get_axis_source(self.as_raw_mut()) } { |
377 | ffi::libinput_pointer_axis_source_LIBINPUT_POINTER_AXIS_SOURCE_WHEEL => { |
378 | AxisSource::Wheel |
379 | } |
380 | ffi::libinput_pointer_axis_source_LIBINPUT_POINTER_AXIS_SOURCE_FINGER => { |
381 | AxisSource::Finger |
382 | } |
383 | ffi::libinput_pointer_axis_source_LIBINPUT_POINTER_AXIS_SOURCE_CONTINUOUS => { |
384 | AxisSource::Continuous |
385 | } |
386 | ffi::libinput_pointer_axis_source_LIBINPUT_POINTER_AXIS_SOURCE_WHEEL_TILT => { |
387 | AxisSource::WheelTilt |
388 | } |
389 | // Axis Event is deprecated, no new variants will be added |
390 | _ => unreachable!(), |
391 | } |
392 | } |
393 | |
394 | /// Return the axis value of the given axis. |
395 | /// |
396 | /// The interpretation of the value depends on the axis. For the two scrolling |
397 | /// axes `Vertical` and `Horizontal`, the value of the event is in relative |
398 | /// scroll units, with the positive direction being down or right, |
399 | /// respectively. For the interpretation of the value, see `axis_source`. |
400 | /// |
401 | /// If `has_axis` returns `false` for an axis, this function returns 0 for |
402 | /// that axis. |
403 | #[cfg_attr ( |
404 | feature = "libinput_1_19" , |
405 | deprecated = "Use `PointerScrollEvent::scroll_value` instead" |
406 | )] |
407 | pub fn axis_value(&self, axis: Axis) -> f64 { |
408 | unsafe { |
409 | ffi::libinput_event_pointer_get_axis_value( |
410 | self.as_raw_mut(), |
411 | match axis { |
412 | Axis::Vertical => { |
413 | ffi::libinput_pointer_axis_LIBINPUT_POINTER_AXIS_SCROLL_VERTICAL |
414 | } |
415 | Axis::Horizontal => { |
416 | ffi::libinput_pointer_axis_LIBINPUT_POINTER_AXIS_SCROLL_HORIZONTAL |
417 | } |
418 | }, |
419 | ) |
420 | } |
421 | } |
422 | |
423 | /// Return the axis value in discrete steps for a given axis event. |
424 | /// |
425 | /// How a value translates into a discrete step depends on the source. |
426 | /// |
427 | /// If the source is `Wheel`, the discrete value correspond to the number of |
428 | /// physical mouse wheel clicks. |
429 | /// |
430 | /// If the source is `Continuous` or `Finger`, the discrete value is always |
431 | /// `None`. |
432 | #[cfg_attr ( |
433 | feature = "libinput_1_19" , |
434 | deprecated = "Use `PointerScrollWheelEvent::scroll_value_v120` instead" |
435 | )] |
436 | pub fn axis_value_discrete(&self, axis: Axis) -> Option<f64> { |
437 | match self.axis_source() { |
438 | AxisSource::Continuous | AxisSource::Finger => None, |
439 | _ => Some(unsafe { |
440 | ffi::libinput_event_pointer_get_axis_value_discrete( |
441 | self.as_raw_mut(), |
442 | match axis { |
443 | Axis::Vertical => { |
444 | ffi::libinput_pointer_axis_LIBINPUT_POINTER_AXIS_SCROLL_VERTICAL |
445 | } |
446 | Axis::Horizontal => { |
447 | ffi::libinput_pointer_axis_LIBINPUT_POINTER_AXIS_SCROLL_HORIZONTAL |
448 | } |
449 | }, |
450 | ) |
451 | }), |
452 | } |
453 | } |
454 | } |
455 | |
456 | #[cfg (feature = "libinput_1_19" )] |
457 | ffi_event_struct!( |
458 | /// An event related to moving a scroll whell on a pointer device |
459 | struct PointerScrollWheelEvent, ffi::libinput_event_pointer, ffi::libinput_event_pointer_get_base_event); |
460 | |
461 | #[cfg (feature = "libinput_1_19" )] |
462 | ffi_event_struct!( |
463 | /// An event related to moving a finger on a pointer device |
464 | struct PointerScrollFingerEvent, ffi::libinput_event_pointer, ffi::libinput_event_pointer_get_base_event); |
465 | |
466 | #[cfg (feature = "libinput_1_19" )] |
467 | ffi_event_struct!( |
468 | /// An event related to a continuous scroll source on a pointer device |
469 | struct PointerScrollContinuousEvent, ffi::libinput_event_pointer, ffi::libinput_event_pointer_get_base_event); |
470 | |
471 | #[cfg (feature = "libinput_1_19" )] |
472 | /// Common functions of PointerScroll type events |
473 | pub trait PointerScrollEvent: AsRaw<ffi::libinput_event_pointer> { |
474 | /// Check if the event has a valid value for the given axis. |
475 | /// |
476 | /// If this function returns true for an axis and `axis_value` returns a |
477 | /// value of 0, the event is a scroll stop event. |
478 | fn has_axis(&self, axis: Axis) -> bool { |
479 | unsafe { |
480 | ffi::libinput_event_pointer_has_axis( |
481 | self.as_raw_mut(), |
482 | match axis { |
483 | Axis::Vertical => { |
484 | ffi::libinput_pointer_axis_LIBINPUT_POINTER_AXIS_SCROLL_VERTICAL |
485 | } |
486 | Axis::Horizontal => { |
487 | ffi::libinput_pointer_axis_LIBINPUT_POINTER_AXIS_SCROLL_HORIZONTAL |
488 | } |
489 | }, |
490 | ) != 0 |
491 | } |
492 | } |
493 | |
494 | /// Return the axis value of the given axis. |
495 | /// |
496 | /// The interpretation of the value depends on the axis. For the two scrolling axes [`Axis::Vertical`] and [`Axis::Horizontal`], |
497 | /// the value of the event is in relative scroll units, with the positive direction being down or right, |
498 | /// respectively. If [`PointerScrollEvent::has_axis`] returns false for an axis, this function returns 0 for that axis. |
499 | /// |
500 | /// If the event is a [`PointerScrollFingerEvent`], libinput guarantees that a scroll sequence is terminated with a scroll value of 0. |
501 | /// A caller may use this information to decide on whether kinetic scrolling should be triggered on this scroll sequence. |
502 | /// The coordinate system is identical to the cursor movement, i.e. a scroll value of 1 represents the equivalent relative motion of 1. |
503 | /// |
504 | /// If the event is a [`PointerScrollWheelEvent`], no terminating event is guaranteed (though it may happen). |
505 | /// Scrolling is in discrete steps, the value is the angle the wheel moved in degrees. The default is 15 degrees per wheel click, |
506 | /// but some mice may have differently grained wheels. It is up to the caller how to interpret such different step sizes. |
507 | /// Callers should use [`PointerScrollWheelEvent::scroll_value_v120`] for a simpler API of handling scroll wheel events of different step sizes. |
508 | /// |
509 | /// If the event is a [`PointerScrollContinuousEvent`], libinput guarantees that a scroll sequence is terminated with a scroll value of 0. |
510 | /// The coordinate system is identical to the cursor movement, i.e. a scroll value of 1 represents the equivalent relative motion of 1. |
511 | fn scroll_value(&self, axis: Axis) -> f64 { |
512 | unsafe { |
513 | ffi::libinput_event_pointer_get_scroll_value( |
514 | self.as_raw_mut(), |
515 | match axis { |
516 | Axis::Vertical => { |
517 | ffi::libinput_pointer_axis_LIBINPUT_POINTER_AXIS_SCROLL_VERTICAL |
518 | } |
519 | Axis::Horizontal => { |
520 | ffi::libinput_pointer_axis_LIBINPUT_POINTER_AXIS_SCROLL_HORIZONTAL |
521 | } |
522 | }, |
523 | ) |
524 | } |
525 | } |
526 | } |
527 | |
528 | #[cfg (feature = "libinput_1_19" )] |
529 | impl PointerScrollEvent for PointerScrollWheelEvent {} |
530 | #[cfg (feature = "libinput_1_19" )] |
531 | impl PointerScrollEvent for PointerScrollFingerEvent {} |
532 | #[cfg (feature = "libinput_1_19" )] |
533 | impl PointerScrollEvent for PointerScrollContinuousEvent {} |
534 | |
535 | #[cfg (feature = "libinput_1_19" )] |
536 | impl PointerScrollWheelEvent { |
537 | /// Return the axis value as a v120-normalized value, that represents the movement in logical mouse wheel clicks, normalized to the -120..+120 range. |
538 | /// |
539 | /// A value that is a fraction of ±120 indicates a wheel movement less than one logical click, |
540 | /// a caller should either scroll by the respective fraction of the normal scroll distance or accumulate |
541 | /// that value until a multiple of 120 is reached. |
542 | /// |
543 | /// For most callers, this is the preferred way of handling high-resolution scroll events. |
544 | /// |
545 | /// The normalized v120 value does not take device-specific physical angles or distances into account, |
546 | /// i.e. a wheel with a click angle of 20 degrees produces only 18 logical clicks per 360 degree rotation, |
547 | /// a wheel with a click angle of 15 degrees produces 24 logical clicks per 360 degree rotation. |
548 | /// Where the physical angle matters, use [`PointerScrollEvent::scroll_value`] instead. |
549 | /// |
550 | /// The magic number 120 originates from the [Windows Vista Mouse Wheel design document](http://download.microsoft.com/download/b/d/1/bd1f7ef4-7d72-419e-bc5c-9f79ad7bb66e/wheel.docx). |
551 | pub fn scroll_value_v120(&self, axis: Axis) -> f64 { |
552 | unsafe { |
553 | ffi::libinput_event_pointer_get_scroll_value_v120( |
554 | self.as_raw_mut(), |
555 | match axis { |
556 | Axis::Vertical => { |
557 | ffi::libinput_pointer_axis_LIBINPUT_POINTER_AXIS_SCROLL_VERTICAL |
558 | } |
559 | Axis::Horizontal => { |
560 | ffi::libinput_pointer_axis_LIBINPUT_POINTER_AXIS_SCROLL_HORIZONTAL |
561 | } |
562 | }, |
563 | ) |
564 | } |
565 | } |
566 | } |
567 | |