From 802f718b908e961085d7d5d572600854481bb9c0 Mon Sep 17 00:00:00 2001
From: Jose Luis Parrilla Fuentes
Date: Sat, 14 Mar 2026 15:33:23 +0100
Subject: [PATCH] linux_x11: fix enter/leave mouse state handling.
Mouse enter/leave window events were not handling.
This caused incorrect mouse state when the pointer left the window.
When the mouse left the window, button state was not updated because
events outside the window are not received.
This results in incorrect readings in dependent code, such as the macroquad
function is_mouse_button_down().
Tested on Linux/X11.
---
src/event.rs | 2 ++
src/native/linux_x11.rs | 25 ++++++++++++++++++-------
2 files changed, 20 insertions(+), 7 deletions(-)
diff --git a/src/event.rs b/src/event.rs
index 7e16d9fb..82e0a925 100644
--- a/src/event.rs
+++ b/src/event.rs
@@ -176,6 +176,8 @@ pub trait EventHandler {
fn mouse_wheel_event(&mut self, _x: f32, _y: f32) {}
fn mouse_button_down_event(&mut self, _button: MouseButton, _x: f32, _y: f32) {}
fn mouse_button_up_event(&mut self, _button: MouseButton, _x: f32, _y: f32) {}
+ fn mouse_leave_event(&mut self) {}
+ fn mouse_enter_event(&mut self, _button: MouseButton ,_x: f32, _y: f32 ) {}
fn char_event(&mut self, _character: char, _keymods: KeyMods, _repeat: bool) {}
diff --git a/src/native/linux_x11.rs b/src/native/linux_x11.rs
index 9e2b0b53..0fea8e26 100644
--- a/src/native/linux_x11.rs
+++ b/src/native/linux_x11.rs
@@ -12,7 +12,7 @@ mod xi_input;
use crate::{
event::EventHandler,
native::{egl, gl, module, NativeDisplayData, Request},
- CursorIcon,
+ CursorIcon, MouseButton,
};
use libx11::*;
@@ -121,17 +121,28 @@ impl X11Display {
event_handler.mouse_button_up_event(btn, x, y);
}
}
- 7 => {
- // Mouse Enter
- }
- 8 => {
- // Mouse Leave
- }
6 => {
let x = event.xmotion.x as libc::c_float;
let y = event.xmotion.y as libc::c_float;
event_handler.mouse_motion_event(x, y);
}
+ 7 => {
+ let x = event.xcrossing.x as libc::c_float;
+ let y = event.xcrossing.y as libc::c_float;
+ let state = event.xcrossing.state as libc::c_long;
+
+ let btn = match () {
+ _ if (state & Button1MotionMask) != 0 => MouseButton::Left,
+ _ if (state & Button2MotionMask) != 0 => MouseButton::Middle,
+ _ if (state & Button3MotionMask) != 0 => MouseButton::Right,
+ _ => MouseButton::Unknown,
+ };
+ event_handler.mouse_enter_event( btn , x, y);
+
+ }
+ 8 => {
+ event_handler.mouse_leave_event();
+ }
9 => {
event_handler.window_restored_event();
}