mirror of https://github.com/encounter/SDL.git
Implemented SDL_SetWindowMouseRect() on Wayland
This commit is contained in:
parent
18e69827aa
commit
ae67c7d2da
|
@ -1670,11 +1670,12 @@ lock_pointer_to_window(SDL_Window *window,
|
||||||
w->locked_pointer = locked_pointer;
|
w->locked_pointer = locked_pointer;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void pointer_confine_destroy(struct SDL_WaylandInput *input)
|
static void pointer_confine_destroy(SDL_Window *window)
|
||||||
{
|
{
|
||||||
if (input->confined_pointer) {
|
SDL_WindowData *w = window->driverdata;
|
||||||
zwp_confined_pointer_v1_destroy(input->confined_pointer);
|
if (w->confined_pointer) {
|
||||||
input->confined_pointer = NULL;
|
zwp_confined_pointer_v1_destroy(w->confined_pointer);
|
||||||
|
w->confined_pointer = NULL;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1696,7 +1697,8 @@ int Wayland_input_lock_pointer(struct SDL_WaylandInput *input)
|
||||||
|
|
||||||
/* If we have a pointer confine active, we must destroy it here because
|
/* If we have a pointer confine active, we must destroy it here because
|
||||||
* creating a locked pointer otherwise would be a protocol error. */
|
* creating a locked pointer otherwise would be a protocol error. */
|
||||||
pointer_confine_destroy(input);
|
for (window = vd->windows; window; window = window->next)
|
||||||
|
pointer_confine_destroy(window);
|
||||||
|
|
||||||
if (!input->relative_pointer) {
|
if (!input->relative_pointer) {
|
||||||
relative_pointer =
|
relative_pointer =
|
||||||
|
@ -1736,8 +1738,8 @@ int Wayland_input_unlock_pointer(struct SDL_WaylandInput *input)
|
||||||
|
|
||||||
d->relative_mouse_mode = 0;
|
d->relative_mouse_mode = 0;
|
||||||
|
|
||||||
if (input->confined_pointer_window)
|
for (window = vd->windows; window; window = window->next)
|
||||||
Wayland_input_confine_pointer(input->confined_pointer_window, input);
|
Wayland_input_confine_pointer(input, window);
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
@ -1759,11 +1761,12 @@ static const struct zwp_confined_pointer_v1_listener confined_pointer_listener =
|
||||||
confined_pointer_unconfined,
|
confined_pointer_unconfined,
|
||||||
};
|
};
|
||||||
|
|
||||||
int Wayland_input_confine_pointer(SDL_Window *window, struct SDL_WaylandInput *input)
|
int Wayland_input_confine_pointer(struct SDL_WaylandInput *input, SDL_Window *window)
|
||||||
{
|
{
|
||||||
SDL_WindowData *w = window->driverdata;
|
SDL_WindowData *w = window->driverdata;
|
||||||
SDL_VideoData *d = input->display;
|
SDL_VideoData *d = input->display;
|
||||||
struct zwp_confined_pointer_v1 *confined_pointer;
|
struct zwp_confined_pointer_v1 *confined_pointer;
|
||||||
|
struct wl_region *confine_rect;
|
||||||
|
|
||||||
if (!d->pointer_constraints)
|
if (!d->pointer_constraints)
|
||||||
return -1;
|
return -1;
|
||||||
|
@ -1773,34 +1776,45 @@ int Wayland_input_confine_pointer(SDL_Window *window, struct SDL_WaylandInput *i
|
||||||
|
|
||||||
/* A confine may already be active, in which case we should destroy it and
|
/* A confine may already be active, in which case we should destroy it and
|
||||||
* create a new one. */
|
* create a new one. */
|
||||||
if (input->confined_pointer)
|
pointer_confine_destroy(window);
|
||||||
Wayland_input_unconfine_pointer(input);
|
|
||||||
|
|
||||||
input->confined_pointer_window = window;
|
|
||||||
|
|
||||||
/* We cannot create a confine if the pointer is already locked. Defer until
|
/* We cannot create a confine if the pointer is already locked. Defer until
|
||||||
* the pointer is unlocked. */
|
* the pointer is unlocked. */
|
||||||
if (d->relative_mouse_mode)
|
if (d->relative_mouse_mode)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
|
if (SDL_RectEmpty(&window->mouse_rect)) {
|
||||||
|
confine_rect = NULL;
|
||||||
|
} else {
|
||||||
|
confine_rect = wl_compositor_create_region(d->compositor);
|
||||||
|
wl_region_add(confine_rect,
|
||||||
|
window->mouse_rect.x,
|
||||||
|
window->mouse_rect.y,
|
||||||
|
window->mouse_rect.w,
|
||||||
|
window->mouse_rect.h);
|
||||||
|
}
|
||||||
|
|
||||||
confined_pointer =
|
confined_pointer =
|
||||||
zwp_pointer_constraints_v1_confine_pointer(d->pointer_constraints,
|
zwp_pointer_constraints_v1_confine_pointer(d->pointer_constraints,
|
||||||
w->surface,
|
w->surface,
|
||||||
input->pointer,
|
input->pointer,
|
||||||
NULL,
|
confine_rect,
|
||||||
ZWP_POINTER_CONSTRAINTS_V1_LIFETIME_PERSISTENT);
|
ZWP_POINTER_CONSTRAINTS_V1_LIFETIME_PERSISTENT);
|
||||||
zwp_confined_pointer_v1_add_listener(confined_pointer,
|
zwp_confined_pointer_v1_add_listener(confined_pointer,
|
||||||
&confined_pointer_listener,
|
&confined_pointer_listener,
|
||||||
window);
|
window);
|
||||||
|
|
||||||
input->confined_pointer = confined_pointer;
|
if (confine_rect != NULL) {
|
||||||
|
wl_region_destroy(confine_rect);
|
||||||
|
}
|
||||||
|
|
||||||
|
w->confined_pointer = confined_pointer;
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int Wayland_input_unconfine_pointer(struct SDL_WaylandInput *input)
|
int Wayland_input_unconfine_pointer(struct SDL_WaylandInput *input, SDL_Window *window)
|
||||||
{
|
{
|
||||||
pointer_confine_destroy(input);
|
pointer_confine_destroy(window);
|
||||||
input->confined_pointer_window = NULL;
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -50,8 +50,6 @@ struct SDL_WaylandInput {
|
||||||
SDL_WaylandDataDevice *data_device;
|
SDL_WaylandDataDevice *data_device;
|
||||||
SDL_WaylandTextInput *text_input;
|
SDL_WaylandTextInput *text_input;
|
||||||
struct zwp_relative_pointer_v1 *relative_pointer;
|
struct zwp_relative_pointer_v1 *relative_pointer;
|
||||||
struct zwp_confined_pointer_v1 *confined_pointer;
|
|
||||||
SDL_Window *confined_pointer_window;
|
|
||||||
SDL_WindowData *pointer_focus;
|
SDL_WindowData *pointer_focus;
|
||||||
SDL_WindowData *keyboard_focus;
|
SDL_WindowData *keyboard_focus;
|
||||||
uint32_t pointer_enter_serial;
|
uint32_t pointer_enter_serial;
|
||||||
|
@ -98,8 +96,8 @@ extern void Wayland_display_destroy_pointer_constraints(SDL_VideoData *d);
|
||||||
extern int Wayland_input_lock_pointer(struct SDL_WaylandInput *input);
|
extern int Wayland_input_lock_pointer(struct SDL_WaylandInput *input);
|
||||||
extern int Wayland_input_unlock_pointer(struct SDL_WaylandInput *input);
|
extern int Wayland_input_unlock_pointer(struct SDL_WaylandInput *input);
|
||||||
|
|
||||||
extern int Wayland_input_confine_pointer(SDL_Window *window, struct SDL_WaylandInput *input);
|
extern int Wayland_input_confine_pointer(struct SDL_WaylandInput *input, SDL_Window *window);
|
||||||
extern int Wayland_input_unconfine_pointer(struct SDL_WaylandInput *input);
|
extern int Wayland_input_unconfine_pointer(struct SDL_WaylandInput *input, SDL_Window *window);
|
||||||
|
|
||||||
extern void Wayland_display_add_relative_pointer_manager(SDL_VideoData *d, uint32_t id);
|
extern void Wayland_display_add_relative_pointer_manager(SDL_VideoData *d, uint32_t id);
|
||||||
extern void Wayland_display_destroy_relative_pointer_manager(SDL_VideoData *d);
|
extern void Wayland_display_destroy_relative_pointer_manager(SDL_VideoData *d);
|
||||||
|
|
|
@ -247,6 +247,7 @@ Wayland_CreateDevice(int devindex)
|
||||||
device->SetWindowFullscreen = Wayland_SetWindowFullscreen;
|
device->SetWindowFullscreen = Wayland_SetWindowFullscreen;
|
||||||
device->MaximizeWindow = Wayland_MaximizeWindow;
|
device->MaximizeWindow = Wayland_MaximizeWindow;
|
||||||
device->MinimizeWindow = Wayland_MinimizeWindow;
|
device->MinimizeWindow = Wayland_MinimizeWindow;
|
||||||
|
device->SetWindowMouseRect = Wayland_SetWindowMouseRect;
|
||||||
device->SetWindowMouseGrab = Wayland_SetWindowMouseGrab;
|
device->SetWindowMouseGrab = Wayland_SetWindowMouseGrab;
|
||||||
device->SetWindowKeyboardGrab = Wayland_SetWindowKeyboardGrab;
|
device->SetWindowKeyboardGrab = Wayland_SetWindowKeyboardGrab;
|
||||||
device->RestoreWindow = Wayland_RestoreWindow;
|
device->RestoreWindow = Wayland_RestoreWindow;
|
||||||
|
|
|
@ -1153,15 +1153,35 @@ Wayland_MinimizeWindow(_THIS, SDL_Window * window)
|
||||||
WAYLAND_wl_display_flush(viddata->display);
|
WAYLAND_wl_display_flush(viddata->display);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
Wayland_SetWindowMouseRect(_THIS, SDL_Window *window)
|
||||||
|
{
|
||||||
|
SDL_VideoData *data = (SDL_VideoData *) _this->driverdata;
|
||||||
|
|
||||||
|
/* This may look suspiciously like SetWindowGrab, despite SetMouseRect not
|
||||||
|
* implicitly doing a grab. And you're right! Wayland doesn't let us mess
|
||||||
|
* around with mouse focus whatsoever, so it just happens to be that the
|
||||||
|
* work that we can do in these two functions ends up being the same.
|
||||||
|
*
|
||||||
|
* Just know that this call lets you confine with a rect, SetWindowGrab
|
||||||
|
* lets you confine without a rect.
|
||||||
|
*/
|
||||||
|
if (SDL_RectEmpty(&window->mouse_rect) && !(window->flags & SDL_WINDOW_MOUSE_GRABBED)) {
|
||||||
|
Wayland_input_unconfine_pointer(data->input, window);
|
||||||
|
} else {
|
||||||
|
Wayland_input_confine_pointer(data->input, window);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
Wayland_SetWindowMouseGrab(_THIS, SDL_Window *window, SDL_bool grabbed)
|
Wayland_SetWindowMouseGrab(_THIS, SDL_Window *window, SDL_bool grabbed)
|
||||||
{
|
{
|
||||||
SDL_VideoData *data = (SDL_VideoData *) _this->driverdata;
|
SDL_VideoData *data = (SDL_VideoData *) _this->driverdata;
|
||||||
|
|
||||||
if (grabbed) {
|
if (grabbed) {
|
||||||
Wayland_input_confine_pointer(window, data->input);
|
Wayland_input_confine_pointer(data->input, window);
|
||||||
} else {
|
} else if (SDL_RectEmpty(&window->mouse_rect)) {
|
||||||
Wayland_input_unconfine_pointer(data->input);
|
Wayland_input_unconfine_pointer(data->input, window);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -65,6 +65,7 @@ typedef struct {
|
||||||
struct SDL_WaylandInput *keyboard_device;
|
struct SDL_WaylandInput *keyboard_device;
|
||||||
EGLSurface egl_surface;
|
EGLSurface egl_surface;
|
||||||
struct zwp_locked_pointer_v1 *locked_pointer;
|
struct zwp_locked_pointer_v1 *locked_pointer;
|
||||||
|
struct zwp_confined_pointer_v1 *confined_pointer;
|
||||||
struct zxdg_toplevel_decoration_v1 *server_decoration;
|
struct zxdg_toplevel_decoration_v1 *server_decoration;
|
||||||
struct zwp_keyboard_shortcuts_inhibitor_v1 *key_inhibitor;
|
struct zwp_keyboard_shortcuts_inhibitor_v1 *key_inhibitor;
|
||||||
struct zwp_idle_inhibitor_v1 *idle_inhibitor;
|
struct zwp_idle_inhibitor_v1 *idle_inhibitor;
|
||||||
|
@ -93,6 +94,7 @@ extern void Wayland_SetWindowFullscreen(_THIS, SDL_Window * window,
|
||||||
SDL_bool fullscreen);
|
SDL_bool fullscreen);
|
||||||
extern void Wayland_MaximizeWindow(_THIS, SDL_Window * window);
|
extern void Wayland_MaximizeWindow(_THIS, SDL_Window * window);
|
||||||
extern void Wayland_MinimizeWindow(_THIS, SDL_Window * window);
|
extern void Wayland_MinimizeWindow(_THIS, SDL_Window * window);
|
||||||
|
extern void Wayland_SetWindowMouseRect(_THIS, SDL_Window * window);
|
||||||
extern void Wayland_SetWindowMouseGrab(_THIS, SDL_Window * window, SDL_bool grabbed);
|
extern void Wayland_SetWindowMouseGrab(_THIS, SDL_Window * window, SDL_bool grabbed);
|
||||||
extern void Wayland_SetWindowKeyboardGrab(_THIS, SDL_Window *window, SDL_bool grabbed);
|
extern void Wayland_SetWindowKeyboardGrab(_THIS, SDL_Window *window, SDL_bool grabbed);
|
||||||
extern void Wayland_RestoreWindow(_THIS, SDL_Window * window);
|
extern void Wayland_RestoreWindow(_THIS, SDL_Window * window);
|
||||||
|
|
Loading…
Reference in New Issue