leftwm_core/handlers/
mouse_combo_handler.rs

1use crate::display_action::DisplayAction;
2use crate::models::Handle;
3use crate::models::Mode;
4use crate::models::WindowHandle;
5use crate::state::State;
6use crate::utils;
7use crate::utils::modmask_lookup::Button;
8use crate::utils::modmask_lookup::ModMask;
9
10impl<H: Handle> State<H> {
11    /// `mouse_combo_handler` is called when the display server sends
12    /// `DisplayEvent::MouseCombo(modmask, button, handle, x, y)`
13    ///
14    /// Returns `true` if changes need to be rendered.
15    pub fn mouse_combo_handler(
16        &mut self,
17        modmask: &ModMask,
18        button: Button,
19        handle: WindowHandle<H>,
20        x: i32,
21        y: i32,
22    ) -> bool {
23        if let Some(window) = self.windows.iter().find(|w| w.handle == handle) {
24            if !self.disable_tile_drag || window.floating() {
25                let modifier = utils::modmask_lookup::into_modmask(&self.mousekey);
26                let bottom_right = (window.x() + window.width(), window.y() + window.height());
27                // Build the display to say whether we are ready to move/resize.
28                let act = self.build_action(modmask, button, handle, modifier);
29                if let Some(act) = act {
30                    if self.reposition_cursor_on_resize {
31                        if let DisplayAction::ReadyToResizeWindow(_) = act {
32                            let move_act = DisplayAction::MoveMouseOverPoint(bottom_right);
33                            self.actions.push_back(move_act);
34                        }
35                    }
36                    self.actions.push_back(act);
37                    return false;
38                }
39            }
40        } else if self.focus_manager.behaviour.is_clickto()
41            && (button == Button::Main || button == Button::Secondary)
42            && self.screens.iter().any(|s| s.root == handle)
43        {
44            self.focus_workspace_with_point(x, y);
45            return false;
46        }
47        true
48    }
49
50    // private helper function
51    fn build_action(
52        &mut self,
53        mod_mask: &ModMask,
54        button: Button,
55        window: WindowHandle<H>,
56        modifier: ModMask,
57    ) -> Option<DisplayAction<H>> {
58        let is_mouse_key = *mod_mask == modifier || *mod_mask == (modifier | ModMask::Shift);
59        match button {
60            Button::Main if is_mouse_key => {
61                _ = self
62                    .windows
63                    .iter()
64                    .find(|w| w.handle == window && w.can_move())?;
65                self.mode = Mode::ReadyToMove(window);
66                Some(DisplayAction::ReadyToMoveWindow(window))
67            }
68            Button::Secondary if is_mouse_key => {
69                _ = self
70                    .windows
71                    .iter()
72                    .find(|w| w.handle == window && w.can_resize())?;
73                self.mode = Mode::ReadyToResize(window);
74                Some(DisplayAction::ReadyToResizeWindow(window))
75            }
76            Button::Main | Button::Secondary if self.focus_manager.behaviour.is_clickto() => {
77                self.focus_window(&window);
78                Some(DisplayAction::ReplayClick(window, button))
79            }
80            _ => None,
81        }
82    }
83}