<NME> pointer.rs
<BEF> use std::{fmt, sync::Mutex};

use wayland_server::{
    backend::{ClientId, ObjectId},
    protocol::{
        wl_pointer::{
            self, Axis as WlAxis, AxisSource as WlAxisSource, ButtonState as WlButtonState, Request,
            WlPointer,
        },
        wl_surface::WlSurface,
    },
    Dispatch, DisplayHandle, Resource,
};

use crate::{
    backend::input::{Axis, AxisSource, ButtonState},
    input::{
        pointer::{
            AxisFrame, ButtonEvent, CursorImageAttributes, CursorImageStatus, MotionEvent, PointerHandle,
            PointerInternal, PointerTarget,
        },
        Seat,
    },
    utils::Serial,
    wayland::compositor,
mod cursor_image;
pub use cursor_image::{CursorImageAttributes, CursorImageStatus, CURSOR_IMAGE_ROLE};

mod axis_frame;
pub use axis_frame::AxisFrame;

struct PointerInternal {
    known_pointers: Vec<WlPointer>,
    focus: Option<(WlSurface, Point<i32, Logical>)>,
    pending_focus: Option<(WlSurface, Point<i32, Logical>)>,
    location: Point<f64, Logical>,
    grab: GrabStatus,
    pressed_buttons: Vec<u32>,
    image_callback: Box<dyn FnMut(CursorImageStatus) + Send + Sync>,
}

// image_callback does not implement debug, so we have to impl Debug manually
impl fmt::Debug for PointerInternal {
    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
        f.debug_struct("PointerInternal")
            .field("known_pointers", &self.known_pointers)
        for ptr in &*inner {
            if ptr.id().same_client_as(&surface.id()) {
                f(ptr.clone())
            }
        }
    }
}
    }
}

impl PointerInternal {
    fn new(image_callback: Box<dyn FnMut(CursorImageStatus) + Send + Sync>) -> Self {
        Self {
            known_pointers: Vec::new(),
        for_each_focused_pointers(seat, self, |ptr| {
            ptr.enter(event.serial.into(), self, event.location.x, event.location.y);
            if ptr.version() >= 5 {
                ptr.frame();
            }
        })
        }
    }

    fn set_grab<G: PointerGrab + 'static>(
        &mut self,
        dh: &mut DisplayHandle<'_>,
        serial: Serial,
        })
    }
    fn motion(&self, seat: &Seat<D>, _data: &mut D, event: &MotionEvent) {
        for_each_focused_pointers(seat, self, |ptr| {
            ptr.motion(event.time, event.location.x, event.location.y);
            if ptr.version() >= 5 {
                ptr.frame();
            }
        })
    }
    fn button(&self, seat: &Seat<D>, _data: &mut D, event: &ButtonEvent) {
        for_each_focused_pointers(seat, self, |ptr| {
            ptr.button(event.serial.into(), event.time, event.button, event.state.into());
            if ptr.version() >= 5 {
                ptr.frame();
            }
        })
    }
    fn axis(&self, seat: &Seat<D>, _data: &mut D, details: AxisFrame) {
        for_each_focused_pointers(seat, self, |ptr| {
            // axis
            if details.axis.0 != 0.0 {
                ptr.axis(details.time, WlAxis::HorizontalScroll, details.axis.0);
            }
            if details.axis.1 != 0.0 {
                ptr.axis(details.time, WlAxis::VerticalScroll, details.axis.1);
            }
            if ptr.version() >= 5 {
                // axis source
                if let Some(source) = details.source {
                    // WheelTilt was not supported before version 6
                    // The best we can do is replace it with Wheel
                    let source = if ptr.version() < 6 {
                        match source {
                            AxisSource::WheelTilt => AxisSource::Wheel,
                            other => other,
                        }
                    } else {
                        source
                    }
                    .into();
                    ptr.axis_source(source);
                }
                // axis discrete
                if details.discrete.0 != 0 {
                    ptr.axis_discrete(WlAxis::HorizontalScroll, details.discrete.0);
                }
                if details.discrete.1 != 0 {
                    ptr.axis_discrete(WlAxis::VerticalScroll, details.discrete.1);
                }
                // stop
                if details.stop.0 {
                    ptr.axis_stop(details.time, WlAxis::HorizontalScroll);
                }
                if details.stop.1 {
                    ptr.axis_stop(details.time, WlAxis::VerticalScroll);
                }
                // frame
                ptr.frame();
            }
        })
    }
}

/// User data for pointer
pub struct PointerUserData<D: SeatHandler> {
    pub(crate) handle: Option<PointerHandle<D>>,
}

impl<D: SeatHandler> fmt::Debug for PointerUserData<D>
where
    <D as SeatHandler>::PointerFocus: fmt::Debug,
{
    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
        f.debug_struct("PointerUserData")
            .field("handle", &self.handle)
            .finish()
    }
}

impl<D> Dispatch<WlPointer, PointerUserData<D>, D> for SeatState<D>
where
    D: Dispatch<WlPointer, PointerUserData<D>>,
    D: SeatHandler,
    <D as SeatHandler>::PointerFocus: WaylandFocus,
    D: 'static,
{
    fn request(
        state: &mut D,
        _client: &wayland_server::Client,

    fn with_grab<F>(&mut self, dh: &mut DisplayHandle<'_>, f: F)
    where
        F: FnOnce(&mut DisplayHandle<'_>, PointerInnerHandle<'_>, &mut dyn PointerGrab),
    {
        let mut grab = ::std::mem::replace(&mut self.grab, GrabStatus::Borrowed);
        match grab {
            Request::SetCursor {
                surface,
                hotspot_x,
                hotspot_y,
                ..
            } => {
                if let Some(ref handle) = data.handle {
                    let seat = {
                        let seat_state = state.seat_state();
                        seat_state
                            .seats
                            .iter()
                            .find(|seat| seat.get_pointer().map(|h| &h == handle).unwrap_or(false))
                            .cloned()
                    };

                    let guard = handle.inner.lock().unwrap();
                    // only allow setting the cursor icon if the current pointer focus
                    // is of the same client
                    let PointerInternal { ref focus, .. } = *guard;
                    if let Some((ref focus, _)) = *focus {
                        if focus.same_client_as(&pointer.id()) {
                            match surface {
                                Some(surface) => {
                                    // tolerate re-using the same surface
                                    if compositor::give_role(&surface, CURSOR_IMAGE_ROLE).is_err()
                                        && compositor::get_role(&surface) != Some(CURSOR_IMAGE_ROLE)
                                    {
                                        pointer.post_error(
                                            wl_pointer::Error::Role,
                                            "Given wl_surface has another role.",
                                        );
/// When sending events using this handle, they will be intercepted by a pointer
/// grab if any is active. See the [`PointerGrab`] trait for details.
#[derive(Debug)]
pub struct PointerHandle {
    inner: Arc<Mutex<PointerInternal>>,
}

impl Clone for PointerHandle {
    fn clone(&self) -> Self {
        Self {
            inner: self.inner.clone(),
                                            .unwrap()
    }
}

impl PointerHandle {
    pub(crate) fn new<F>(cb: F) -> PointerHandle
    where
        F: FnMut(CursorImageStatus) + Send + Sync + 'static,
    {
                                }
                                None => {
                                    if let Some(seat) = seat {
                                        state.cursor_image(&seat, CursorImageStatus::Hidden);
                                    }
                                }
                            }
                        }
                    }
                }
    /// Change the current grab on this pointer to the provided grab
    ///
    /// Overwrites any current grab.
    pub fn set_grab<G: PointerGrab + 'static>(
        &self,
        dh: &mut DisplayHandle<'_>,
        grab: G,

    fn destroyed(_state: &mut D, _: ClientId, object_id: ObjectId, data: &PointerUserData<D>) {
        if let Some(ref handle) = data.handle {
            handle
                .known_pointers
                .lock()
                .unwrap()
                .retain(|p| p.id() != object_id);
        }
    }
}

impl From<Axis> for WlAxis {
    fn from(axis: Axis) -> WlAxis {
        match axis {
            Axis::Horizontal => WlAxis::HorizontalScroll,
            Axis::Vertical => WlAxis::VerticalScroll,
        }
    }
}

#[derive(Debug, thiserror::Error)]
#[error("Unknown Axis {0:?}")]
pub struct UnknownAxis(WlAxis);

impl TryFrom<WlAxis> for Axis {
    type Error = UnknownAxis;
    fn try_from(value: WlAxis) -> Result<Self, Self::Error> {
        match value {
            WlAxis::HorizontalScroll => Ok(Axis::Horizontal),
            WlAxis::VerticalScroll => Ok(Axis::Vertical),
            x => Err(UnknownAxis(x)),
        }
    }
}

impl From<AxisSource> for WlAxisSource {
    fn from(axis: AxisSource) -> WlAxisSource {
        match axis {
            AxisSource::Wheel => WlAxisSource::Wheel,
            AxisSource::Finger => WlAxisSource::Finger,
            AxisSource::Continuous => WlAxisSource::Continuous,
            AxisSource::WheelTilt => WlAxisSource::WheelTilt,
    ///
    /// This will internally take care of notifying the appropriate client objects
    /// of enter/motion/leave events.
    pub fn motion(
        &self,
        dh: &mut DisplayHandle<'_>,
        location: Point<f64, Logical>,
        focus: Option<(WlSurface, Point<i32, Logical>)>,
        serial: Serial,
        time: u32,
    ) {
        let mut inner = self.inner.lock().unwrap();
        inner.pending_focus = focus.clone();
        inner.with_grab(dh, move |dh, mut handle, grab| {
            grab.motion(dh, &mut handle, location, focus, serial, time);
        });
    }

}
    ///
    /// This will internally send the appropriate button event to the client
    /// objects matching with the currently focused surface.
    pub fn button(
        &self,
        dh: &mut DisplayHandle<'_>,
        button: u32,
        state: ButtonState,
        serial: Serial,
        time: u32,
    ) {
        let mut inner = self.inner.lock().unwrap();
        match state {
            ButtonState::Pressed => {
                inner.pressed_buttons.push(button);
            }
            ButtonState::Released => {
                inner.pressed_buttons.retain(|b| *b != button);
            }
            _ => unreachable!(),
        }
        inner.with_grab(dh, |dh, mut handle, grab| {
            grab.button(dh, &mut handle, button, state, serial, time);
        });
    }

    // /// Start an axis frame
    // ///
    // /// A single frame will group multiple scroll events as if they happened in the same instance.
    // pub fn axis(&self, details: AxisFrame) {
    //     self.inner.borrow_mut().with_grab(|mut handle, grab| {
    //         grab.axis(&mut handle, details);
    //     });
    // }

    /// Access the current location of this pointer in the global space
    pub fn current_location(&self) -> Point<f64, Logical> {
/// This inner handle is accessed from inside a pointer grab logic, and directly
/// sends event to the client
#[derive(Debug)]
pub struct PointerInnerHandle<'a> {
    inner: &'a mut PointerInternal,
}

impl<'a> PointerInnerHandle<'a> {
    /// Change the current grab on this pointer to the provided grab
    ///
    /// Overwrites any current grab.
    pub fn set_grab<G: PointerGrab + 'static>(
        &mut self,
        dh: &mut DisplayHandle<'_>,
        serial: Serial,

/// User data for pointer
#[derive(Debug)]
pub struct PointerUserData {
    pub(crate) handle: Option<PointerHandle>,
}

impl DelegateDispatchBase<WlPointer> for SeatState {
    type UserData = PointerUserData;
}

impl<D> DelegateDispatch<WlPointer, D> for SeatState
where
    D: Dispatch<WlPointer, UserData = PointerUserData>,
    D: SeatHandler,
    D: 'static,
{
    fn request(
        _state: &mut D,

<MSG> seat: Implement &mut T passing for grabs


<DFF> @@ -26,21 +26,21 @@ pub use grab::{GrabStartData, PointerGrab};
 mod cursor_image;
 pub use cursor_image::{CursorImageAttributes, CursorImageStatus, CURSOR_IMAGE_ROLE};
 
-mod axis_frame;
-pub use axis_frame::AxisFrame;
+mod events;
+pub use events::{AxisFrame, ButtonEvent, MotionEvent};
 
-struct PointerInternal {
+struct PointerInternal<T> {
     known_pointers: Vec<WlPointer>,
     focus: Option<(WlSurface, Point<i32, Logical>)>,
     pending_focus: Option<(WlSurface, Point<i32, Logical>)>,
     location: Point<f64, Logical>,
-    grab: GrabStatus,
+    grab: GrabStatus<T>,
     pressed_buttons: Vec<u32>,
     image_callback: Box<dyn FnMut(CursorImageStatus) + Send + Sync>,
 }
 
 // image_callback does not implement debug, so we have to impl Debug manually
-impl fmt::Debug for PointerInternal {
+impl<T> fmt::Debug for PointerInternal<T> {
     fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
         f.debug_struct("PointerInternal")
             .field("known_pointers", &self.known_pointers)
@@ -54,7 +54,7 @@ impl fmt::Debug for PointerInternal {
     }
 }
 
-impl PointerInternal {
+impl<T> PointerInternal<T> {
     fn new(image_callback: Box<dyn FnMut(CursorImageStatus) + Send + Sync>) -> Self {
         Self {
             known_pointers: Vec::new(),
@@ -67,7 +67,7 @@ impl PointerInternal {
         }
     }
 
-    fn set_grab<G: PointerGrab + 'static>(
+    fn set_grab<G: PointerGrab<T> + 'static>(
         &mut self,
         dh: &mut DisplayHandle<'_>,
         serial: Serial,
@@ -164,7 +164,7 @@ impl PointerInternal {
 
     fn with_grab<F>(&mut self, dh: &mut DisplayHandle<'_>, f: F)
     where
-        F: FnOnce(&mut DisplayHandle<'_>, PointerInnerHandle<'_>, &mut dyn PointerGrab),
+        F: FnOnce(&mut DisplayHandle<'_>, PointerInnerHandle<'_, T>, &mut dyn PointerGrab<T>),
     {
         let mut grab = ::std::mem::replace(&mut self.grab, GrabStatus::Borrowed);
         match grab {
@@ -203,11 +203,11 @@ impl PointerInternal {
 /// When sending events using this handle, they will be intercepted by a pointer
 /// grab if any is active. See the [`PointerGrab`] trait for details.
 #[derive(Debug)]
-pub struct PointerHandle {
-    inner: Arc<Mutex<PointerInternal>>,
+pub struct PointerHandle<T> {
+    inner: Arc<Mutex<PointerInternal<T>>>,
 }
 
-impl Clone for PointerHandle {
+impl<T> Clone for PointerHandle<T> {
     fn clone(&self) -> Self {
         Self {
             inner: self.inner.clone(),
@@ -215,8 +215,8 @@ impl Clone for PointerHandle {
     }
 }
 
-impl PointerHandle {
-    pub(crate) fn new<F>(cb: F) -> PointerHandle
+impl<T> PointerHandle<T> {
+    pub(crate) fn new<F>(cb: F) -> PointerHandle<T>
     where
         F: FnMut(CursorImageStatus) + Send + Sync + 'static,
     {
@@ -233,7 +233,7 @@ impl PointerHandle {
     /// Change the current grab on this pointer to the provided grab
     ///
     /// Overwrites any current grab.
-    pub fn set_grab<G: PointerGrab + 'static>(
+    pub fn set_grab<G: PointerGrab<T> + 'static>(
         &self,
         dh: &mut DisplayHandle<'_>,
         grab: G,
@@ -283,18 +283,11 @@ impl PointerHandle {
     ///
     /// This will internally take care of notifying the appropriate client objects
     /// of enter/motion/leave events.
-    pub fn motion(
-        &self,
-        dh: &mut DisplayHandle<'_>,
-        location: Point<f64, Logical>,
-        focus: Option<(WlSurface, Point<i32, Logical>)>,
-        serial: Serial,
-        time: u32,
-    ) {
+    pub fn motion(&self, data: &mut T, dh: &mut DisplayHandle<'_>, event: &MotionEvent) {
         let mut inner = self.inner.lock().unwrap();
-        inner.pending_focus = focus.clone();
+        inner.pending_focus = event.focus.clone();
         inner.with_grab(dh, move |dh, mut handle, grab| {
-            grab.motion(dh, &mut handle, location, focus, serial, time);
+            grab.motion(data, dh, &mut handle, event);
         });
     }
 
@@ -302,37 +295,30 @@ impl PointerHandle {
     ///
     /// This will internally send the appropriate button event to the client
     /// objects matching with the currently focused surface.
-    pub fn button(
-        &self,
-        dh: &mut DisplayHandle<'_>,
-        button: u32,
-        state: ButtonState,
-        serial: Serial,
-        time: u32,
-    ) {
+    pub fn button(&self, data: &mut T, dh: &mut DisplayHandle<'_>, event: &ButtonEvent) {
         let mut inner = self.inner.lock().unwrap();
-        match state {
+        match event.state {
             ButtonState::Pressed => {
-                inner.pressed_buttons.push(button);
+                inner.pressed_buttons.push(event.button);
             }
             ButtonState::Released => {
-                inner.pressed_buttons.retain(|b| *b != button);
+                inner.pressed_buttons.retain(|b| *b != event.button);
             }
             _ => unreachable!(),
         }
         inner.with_grab(dh, |dh, mut handle, grab| {
-            grab.button(dh, &mut handle, button, state, serial, time);
+            grab.button(data, dh, &mut handle, event);
         });
     }
 
-    // /// Start an axis frame
-    // ///
-    // /// A single frame will group multiple scroll events as if they happened in the same instance.
-    // pub fn axis(&self, details: AxisFrame) {
-    //     self.inner.borrow_mut().with_grab(|mut handle, grab| {
-    //         grab.axis(&mut handle, details);
-    //     });
-    // }
+    /// Start an axis frame
+    ///
+    /// A single frame will group multiple scroll events as if they happened in the same instance.
+    pub fn axis(&self, data: &mut T, dh: &mut DisplayHandle<'_>, details: AxisFrame) {
+        self.inner.lock().unwrap().with_grab(dh, |dh, mut handle, grab| {
+            grab.axis(data, dh, &mut handle, details);
+        });
+    }
 
     /// Access the current location of this pointer in the global space
     pub fn current_location(&self) -> Point<f64, Logical> {
@@ -343,15 +329,15 @@ impl PointerHandle {
 /// This inner handle is accessed from inside a pointer grab logic, and directly
 /// sends event to the client
 #[derive(Debug)]
-pub struct PointerInnerHandle<'a> {
-    inner: &'a mut PointerInternal,
+pub struct PointerInnerHandle<'a, T> {
+    inner: &'a mut PointerInternal<T>,
 }
 
-impl<'a> PointerInnerHandle<'a> {
+impl<'a, T> PointerInnerHandle<'a, T> {
     /// Change the current grab on this pointer to the provided grab
     ///
     /// Overwrites any current grab.
-    pub fn set_grab<G: PointerGrab + 'static>(
+    pub fn set_grab<G: PointerGrab<T> + 'static>(
         &mut self,
         dh: &mut DisplayHandle<'_>,
         serial: Serial,
@@ -473,19 +459,20 @@ impl<'a> PointerInnerHandle<'a> {
 
 /// User data for pointer
 #[derive(Debug)]
-pub struct PointerUserData {
-    pub(crate) handle: Option<PointerHandle>,
+pub struct PointerUserData<T> {
+    pub(crate) handle: Option<PointerHandle<T>>,
 }
 
-impl DelegateDispatchBase<WlPointer> for SeatState {
-    type UserData = PointerUserData;
+impl<T: 'static> DelegateDispatchBase<WlPointer> for SeatState<T> {
+    type UserData = PointerUserData<T>;
 }
 
-impl<D> DelegateDispatch<WlPointer, D> for SeatState
+impl<T, D> DelegateDispatch<WlPointer, D> for SeatState<T>
 where
-    D: Dispatch<WlPointer, UserData = PointerUserData>,
-    D: SeatHandler,
+    D: Dispatch<WlPointer, UserData = PointerUserData<T>>,
+    D: SeatHandler<T>,
     D: 'static,
+    T: 'static,
 {
     fn request(
         _state: &mut D,

seat: Implement &mut T passing for grabs