mirror of
https://github.com/libsdl-org/SDL.git
synced 2026-05-30 05:18:13 +08:00
macOS mouse scroll fix (#15404)
* macOS: fix vertical/horizontal scrolling on GCMouse API * macOS: use AppKit events for mouse scrolling as GCMouse scroll events are buggy
This commit is contained in:
@@ -33,6 +33,8 @@
|
|||||||
#define DEBUG_COCOAMOUSE
|
#define DEBUG_COCOAMOUSE
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
//#define USE_GCMOUSE_SCROLL
|
||||||
|
|
||||||
#ifdef DEBUG_COCOAMOUSE
|
#ifdef DEBUG_COCOAMOUSE
|
||||||
#define DLog(fmt, ...) printf("%s: " fmt "\n", SDL_FUNCTION, ##__VA_ARGS__)
|
#define DLog(fmt, ...) printf("%s: " fmt "\n", SDL_FUNCTION, ##__VA_ARGS__)
|
||||||
#else
|
#else
|
||||||
@@ -262,6 +264,9 @@ static id cocoa_mouse_disconnect_observer = nil;
|
|||||||
// Atomic for thread-safe access during high-frequency mouse input
|
// Atomic for thread-safe access during high-frequency mouse input
|
||||||
static SDL_AtomicInt cocoa_gcmouse_relative_mode;
|
static SDL_AtomicInt cocoa_gcmouse_relative_mode;
|
||||||
static bool cocoa_has_gcmouse = false;
|
static bool cocoa_has_gcmouse = false;
|
||||||
|
|
||||||
|
|
||||||
|
#ifdef USE_GCMOUSE_SCROLL
|
||||||
static SDL_MouseWheelDirection cocoa_mouse_scroll_direction = SDL_MOUSEWHEEL_NORMAL;
|
static SDL_MouseWheelDirection cocoa_mouse_scroll_direction = SDL_MOUSEWHEEL_NORMAL;
|
||||||
|
|
||||||
static void Cocoa_UpdateGCMouseScrollDirection(void)
|
static void Cocoa_UpdateGCMouseScrollDirection(void)
|
||||||
@@ -281,6 +286,7 @@ static void Cocoa_UpdateGCMouseScrollDirection(void)
|
|||||||
cocoa_mouse_scroll_direction = SDL_MOUSEWHEEL_NORMAL;
|
cocoa_mouse_scroll_direction = SDL_MOUSEWHEEL_NORMAL;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
static bool Cocoa_SetGCMouseRelativeMode(bool enabled)
|
static bool Cocoa_SetGCMouseRelativeMode(bool enabled)
|
||||||
{
|
{
|
||||||
@@ -348,13 +354,20 @@ static void Cocoa_OnGCMouseConnected(GCMouse *mouse)
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
#ifdef USE_GCMOUSE_SCROLL
|
||||||
|
/*
|
||||||
|
18/04/2026
|
||||||
|
There seems to be a bug in the CGMouse API, at least when using some mouse types.
|
||||||
|
An event is fired only for the first scroll in one direction. Repeated 1-step
|
||||||
|
scrolls in the same direction do not raise an event.
|
||||||
|
Observed on macOS 26.3.1 with 2 different USB mice.
|
||||||
|
*/
|
||||||
mouse.mouseInput.scroll.valueChangedHandler =
|
mouse.mouseInput.scroll.valueChangedHandler =
|
||||||
^(GCControllerDirectionPad *dpad, float xValue, float yValue) {
|
^(GCControllerDirectionPad *dpad, float xValue, float yValue) {
|
||||||
|
DLog("GCMouse scroll: %f, %f", xValue, yValue);
|
||||||
Uint64 timestamp = SDL_GetTicksNS();
|
Uint64 timestamp = SDL_GetTicksNS();
|
||||||
// Raw scroll values: vertical in first axis, horizontal in second.
|
float vertical = yValue;
|
||||||
// Vertical values are inverted compared to SDL conventions.
|
float horizontal = xValue;
|
||||||
float vertical = -xValue;
|
|
||||||
float horizontal = yValue;
|
|
||||||
|
|
||||||
if (cocoa_mouse_scroll_direction == SDL_MOUSEWHEEL_FLIPPED) {
|
if (cocoa_mouse_scroll_direction == SDL_MOUSEWHEEL_FLIPPED) {
|
||||||
vertical = -vertical;
|
vertical = -vertical;
|
||||||
@@ -365,6 +378,7 @@ static void Cocoa_OnGCMouseConnected(GCMouse *mouse)
|
|||||||
cocoa_mouse_scroll_direction);
|
cocoa_mouse_scroll_direction);
|
||||||
};
|
};
|
||||||
Cocoa_UpdateGCMouseScrollDirection();
|
Cocoa_UpdateGCMouseScrollDirection();
|
||||||
|
#endif // USE_GCMOUSE_SCROLL
|
||||||
|
|
||||||
// Use high-priority queue for low-latency input
|
// Use high-priority queue for low-latency input
|
||||||
dispatch_queue_t queue = dispatch_queue_create("org.libsdl.input.mouse",
|
dispatch_queue_t queue = dispatch_queue_create("org.libsdl.input.mouse",
|
||||||
@@ -852,10 +866,12 @@ void Cocoa_HandleMouseEvent(SDL_VideoDevice *_this, NSEvent *event)
|
|||||||
|
|
||||||
void Cocoa_HandleMouseWheel(SDL_Window *window, NSEvent *event)
|
void Cocoa_HandleMouseWheel(SDL_Window *window, NSEvent *event)
|
||||||
{
|
{
|
||||||
|
#ifdef USE_GCMOUSE_SCROLL
|
||||||
// GCMouse handles scroll events directly, skip NSEvent path to avoid duplicates
|
// GCMouse handles scroll events directly, skip NSEvent path to avoid duplicates
|
||||||
if (Cocoa_HasGCMouse()) {
|
if (Cocoa_HasGCMouse()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
SDL_MouseID mouseID = SDL_DEFAULT_MOUSE_ID;
|
SDL_MouseID mouseID = SDL_DEFAULT_MOUSE_ID;
|
||||||
SDL_MouseWheelDirection direction;
|
SDL_MouseWheelDirection direction;
|
||||||
|
|||||||
Reference in New Issue
Block a user