Merge pull request #35 from nongio/wayland-pointer

Wayland backend pointer events and cursor images
This commit is contained in:
Fred Kiefer 2021-12-27 17:52:47 +01:00 committed by GitHub
commit 9c7c878717
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
8 changed files with 602 additions and 347 deletions

View file

@ -30,6 +30,21 @@
#include "cairo/CairoSurface.h" #include "cairo/CairoSurface.h"
struct pool_buffer
{
int poolfd;
struct wl_shm_pool *pool;
struct wl_buffer *buffer;
cairo_surface_t *surface;
uint32_t width, height;
void *data;
size_t size;
bool busy;
};
struct pool_buffer *
createShmBuffer(int width, int height, struct wl_shm *shm);
@interface WaylandCairoShmSurface : CairoSurface @interface WaylandCairoShmSurface : CairoSurface
{ {
} }

View file

@ -34,6 +34,7 @@
#include <GNUstepGUI/GSDisplayServer.h> #include <GNUstepGUI/GSDisplayServer.h>
#include <wayland-client.h> #include <wayland-client.h>
#include <wayland-cursor.h>
#include <cairo/cairo.h> #include <cairo/cairo.h>
#include <xkbcommon/xkbcommon.h> #include <xkbcommon/xkbcommon.h>
@ -52,8 +53,24 @@ struct pointer
float last_click_x; float last_click_x;
float last_click_y; float last_click_y;
uint32_t button;
NSTimeInterval last_timestamp;
enum wl_pointer_button_state button_state;
uint32_t axis_source;
uint32_t serial; uint32_t serial;
struct window *focus; struct window *focus;
struct window *captured;
};
struct cursor
{
struct wl_cursor *cursor;
struct wl_surface *surface;
struct wl_cursor_image *image;
struct wl_buffer *buffer;
}; };
typedef struct _WaylandConfig typedef struct _WaylandConfig
@ -67,6 +84,7 @@ typedef struct _WaylandConfig
struct wl_keyboard *keyboard; struct wl_keyboard *keyboard;
struct xdg_wm_base *wm_base; struct xdg_wm_base *wm_base;
struct zwlr_layer_shell_v1 *layer_shell; struct zwlr_layer_shell_v1 *layer_shell;
int seat_version;
struct wl_list output_list; struct wl_list output_list;
int output_count; int output_count;
@ -74,7 +92,20 @@ typedef struct _WaylandConfig
int window_count; int window_count;
int last_window_id; int last_window_id;
// last event serial from pointer or keyboard
uint32_t event_serial;
// cursor
struct wl_cursor_theme *cursor_theme;
struct cursor *cursor;
struct wl_surface *cursor_surface;
// pointer
struct pointer pointer; struct pointer pointer;
float mouse_scroll_multiplier;
// keyboard
struct xkb_context *xkb_context; struct xkb_context *xkb_context;
struct struct
{ {
@ -86,9 +117,6 @@ typedef struct _WaylandConfig
} xkb; } xkb;
int modifiers; int modifiers;
int seat_version;
float mouse_scroll_multiplier;
} WaylandConfig; } WaylandConfig;
struct output struct output
@ -120,6 +148,7 @@ struct window
BOOL terminated; BOOL terminated;
BOOL moving; BOOL moving;
BOOL resizing; BOOL resizing;
BOOL ignoreMouse;
float pos_x; float pos_x;
float pos_y; float pos_y;
@ -140,6 +169,8 @@ struct window
CairoSurface *wcs; CairoSurface *wcs;
}; };
struct window *get_window_with_id(WaylandConfig *wlconfig, int winid);
@interface WaylandServer : GSDisplayServer @interface WaylandServer : GSDisplayServer
{ {
WaylandConfig *wlconfig; WaylandConfig *wlconfig;
@ -147,8 +178,10 @@ struct window
BOOL _mouseInitialized; BOOL _mouseInitialized;
} }
@end @end
@interface @interface
WaylandServer (Cursor) WaylandServer (Cursor)
- (void)initializeMouseIfRequired;
@end @end
#endif /* _WaylandServer_h_INCLUDE */ #endif /* _WaylandServer_h_INCLUDE */

View file

@ -44,17 +44,6 @@
#include <fcntl.h> #include <fcntl.h>
#include <sys/mman.h> #include <sys/mman.h>
struct pool_buffer
{
int poolfd;
struct wl_shm_pool *pool;
struct wl_buffer *buffer;
cairo_surface_t *surface;
uint32_t width, height;
void *data;
size_t size;
bool busy;
};
static const enum wl_shm_format wl_fmt = WL_SHM_FORMAT_ARGB8888; static const enum wl_shm_format wl_fmt = WL_SHM_FORMAT_ARGB8888;
static const cairo_format_t cairo_fmt = CAIRO_FORMAT_ARGB32; static const cairo_format_t cairo_fmt = CAIRO_FORMAT_ARGB32;
@ -135,11 +124,11 @@ createPoolFile(off_t size)
return fd; return fd;
} }
static struct pool_buffer * struct pool_buffer *
createBufferForWindow(struct window * window, struct wl_shm *shm) createShmBuffer(int width, int height, struct wl_shm *shm)
{ {
uint32_t stride = cairo_format_stride_for_width(cairo_fmt, window->width); uint32_t stride = cairo_format_stride_for_width(cairo_fmt, width);
size_t size = stride * window->height; size_t size = stride * height;
struct pool_buffer * buf = malloc(sizeof(struct pool_buffer)); struct pool_buffer * buf = malloc(sizeof(struct pool_buffer));
@ -160,22 +149,28 @@ createBufferForWindow(struct window * window, struct wl_shm *shm)
} }
buf->pool = wl_shm_create_pool(shm, buf->poolfd, size); buf->pool = wl_shm_create_pool(shm, buf->poolfd, size);
buf->buffer = wl_shm_pool_create_buffer(buf->pool, 0, window->width, window->height, buf->buffer = wl_shm_pool_create_buffer(buf->pool, 0, width, height,
stride, wl_fmt); stride, wl_fmt);
wl_buffer_add_listener(buf->buffer, &buffer_listener, buf); wl_buffer_add_listener(buf->buffer, &buffer_listener, buf);
} }
else
{
return NULL;
}
buf->data = data; buf->data = data;
buf->size = size; buf->size = size;
buf->width = window->width; buf->width = width;
buf->height = window->height; buf->height = height;
buf->surface = cairo_image_surface_create_for_data(data, cairo_fmt, window->width, window->height, stride); buf->surface = cairo_image_surface_create_for_data(data, cairo_fmt, width, height, stride);
wl_shm_pool_destroy(buf->pool); if(buf->pool)
{
wl_shm_pool_destroy(buf->pool);
}
return buf; return buf;
} }
@implementation WaylandCairoShmSurface @implementation WaylandCairoShmSurface
{ {
struct pool_buffer *pbuffer; struct pool_buffer *pbuffer;
@ -188,7 +183,7 @@ createBufferForWindow(struct window * window, struct wl_shm *shm)
gsDevice = device; gsDevice = device;
pbuffer = createBufferForWindow(window, window->wlconfig->shm); pbuffer = createShmBuffer(window->width, window->height, window->wlconfig->shm);
if (pbuffer == NULL) if (pbuffer == NULL)
{ {

File diff suppressed because it is too large Load diff

View file

@ -105,12 +105,16 @@ keyboard_handle_enter(void *data, struct wl_keyboard *keyboard, uint32_t serial,
struct wl_surface *surface, struct wl_array *keys) struct wl_surface *surface, struct wl_array *keys)
{ {
// NSDebugLog(@"keyboard_handle_enter"); // NSDebugLog(@"keyboard_handle_enter");
WaylandConfig *wlconfig = data;
wlconfig->event_serial = serial;
} }
static void static void
keyboard_handle_leave(void *data, struct wl_keyboard *keyboard, uint32_t serial, keyboard_handle_leave(void *data, struct wl_keyboard *keyboard, uint32_t serial,
struct wl_surface *surface) struct wl_surface *surface)
{ {
WaylandConfig *wlconfig = data;
wlconfig->event_serial = serial;
// NSDebugLog(@"keyboard_handle_leave"); // NSDebugLog(@"keyboard_handle_leave");
} }
@ -122,6 +126,7 @@ keyboard_handle_modifiers(void *data, struct wl_keyboard *keyboard,
{ {
// NSDebugLog(@"keyboard_handle_modifiers"); // NSDebugLog(@"keyboard_handle_modifiers");
WaylandConfig *wlconfig = data; WaylandConfig *wlconfig = data;
wlconfig->event_serial = serial;
xkb_mod_mask_t mask; xkb_mod_mask_t mask;
/* If we're not using a keymap, then we don't handle PC-style modifiers */ /* If we're not using a keymap, then we don't handle PC-style modifiers */
@ -148,6 +153,7 @@ keyboard_handle_key(void *data, struct wl_keyboard *keyboard, uint32_t serial,
{ {
// NSDebugLog(@"keyboard_handle_key: %d", key); // NSDebugLog(@"keyboard_handle_key: %d", key);
WaylandConfig *wlconfig = data; WaylandConfig *wlconfig = data;
wlconfig->event_serial = serial;
uint32_t code, num_syms; uint32_t code, num_syms;
enum wl_keyboard_key_state state = state_w; enum wl_keyboard_key_state state = state_w;
const xkb_keysym_t *syms; const xkb_keysym_t *syms;

View file

@ -401,6 +401,7 @@ WaylandServer (WindowOps)
window->moving = NO; window->moving = NO;
window->resizing = NO; window->resizing = NO;
window->ignoreMouse = NO;
// FIXME is this needed? // FIXME is this needed?
if (window->pos_x < 0) if (window->pos_x < 0)

2
configure vendored
View file

@ -7373,7 +7373,7 @@ fi
CAIRO_LIBS="$CAIRO_LIBS $XFT_LIBS" CAIRO_LIBS="$CAIRO_LIBS $XFT_LIBS"
CAIRO_CFLAGS="$CAIRO_CFLAGS" CAIRO_CFLAGS="$CAIRO_CFLAGS"
LIBS="-lwayland-client -lxkbcommon $LIBS" LIBS="-lwayland-client -lwayland-cursor -lxkbcommon $LIBS"
else else
as_fn_error $? "Invalid Cairo installation" "$LINENO" 5 as_fn_error $? "Invalid Cairo installation" "$LINENO" 5
fi fi

View file

@ -657,7 +657,7 @@ if test x"$BUILD_GRAPHICS" = "xcairo"; then
[AC_MSG_ERROR([**** No xkb_context_new in libxkbcommon. Install correct version of libxkbcommon-dev or equivalent.])]) [AC_MSG_ERROR([**** No xkb_context_new in libxkbcommon. Install correct version of libxkbcommon-dev or equivalent.])])
CAIRO_LIBS="$CAIRO_LIBS $XFT_LIBS" CAIRO_LIBS="$CAIRO_LIBS $XFT_LIBS"
CAIRO_CFLAGS="$CAIRO_CFLAGS" CAIRO_CFLAGS="$CAIRO_CFLAGS"
LIBS="-lwayland-client -lxkbcommon $LIBS" LIBS="-lwayland-client -lwayland-cursor -lxkbcommon $LIBS"
else else
AC_MSG_ERROR([Invalid Cairo installation]) AC_MSG_ERROR([Invalid Cairo installation])
fi fi