From 0f612080fa3ce790e89871b0783b9512f104c8ca Mon Sep 17 00:00:00 2001 From: Keith Bowes Date: Mon, 21 Feb 2022 13:47:18 -0500 Subject: [PATCH] Backports from tinywl --- meson.build | 1 - waybox/config.c | 17 +++++++++++------ waybox/config.h | 2 ++ waybox/cursor.c | 13 ++++++------- waybox/output.c | 10 +++++++++- waybox/seat.c | 41 ++++++++++++++++++++--------------------- 6 files changed, 48 insertions(+), 36 deletions(-) diff --git a/meson.build b/meson.build index c97bdb7..b65a58c 100644 --- a/meson.build +++ b/meson.build @@ -15,7 +15,6 @@ add_project_arguments( '-Wno-unused-parameter', '-D_DEFAULT_SOURCE', '-D_POSIX_C_SOURCE=200112L', - '-DWL_HIDE_DEPRECATED', # Hide the deprecated parts of the Wayland API '-DWLR_USE_UNSTABLE', '-DPACKAGE_NAME="' + meson.project_name() + '"', '-DPACKAGE_VERSION="' + meson.project_version() + '"', diff --git a/waybox/config.c b/waybox/config.c index 7af4631..c7a9ba8 100644 --- a/waybox/config.c +++ b/waybox/config.c @@ -6,7 +6,7 @@ static char *parse_xpath_expr(char *expr, xmlXPathContextPtr ctxt) { xmlXPathObjectPtr object = xmlXPathEvalExpression((xmlChar *) expr, ctxt); if (object == NULL) { - wlr_log(WLR_INFO, "%s", _("Unable to evaluate expression")); + wlr_log(WLR_INFO, "%s: %s", _("Unable to evaluate expression"), expr); xmlXPathFreeContext(ctxt); return(NULL); } @@ -157,11 +157,16 @@ bool init_config(struct wb_server *server) { } struct wb_config *config = calloc(1, sizeof(struct wb_config)); - config->keyboard_layout.layout = parse_xpath_expr("//ob:keyboard//ob:layout//ob:layout", ctxt); - config->keyboard_layout.model = parse_xpath_expr("//ob:keyboard//ob:layout//ob:model", ctxt); - config->keyboard_layout.options = parse_xpath_expr("//ob:keyboard//ob:layout//ob:options", ctxt); - config->keyboard_layout.rules = parse_xpath_expr("//ob:keyboard//ob:layout//ob:rules", ctxt); - config->keyboard_layout.variant = parse_xpath_expr("//ob:keyboard//ob:layout//ob:variant", ctxt); + config->keyboard_layout.use_config = parse_xpath_expr("//ob:keyboard//ob:keyboardLayout", ctxt) != NULL; + + if (config->keyboard_layout.use_config) + { + config->keyboard_layout.layout = parse_xpath_expr("//ob:keyboard//ob:keyboardLayout//ob:layout", ctxt); + config->keyboard_layout.model = parse_xpath_expr("//ob:keyboard//ob:keyboardLayout//ob:model", ctxt); + config->keyboard_layout.options = parse_xpath_expr("//ob:keyboard//ob:keyboardLayout//ob:options", ctxt); + config->keyboard_layout.rules = parse_xpath_expr("//ob:keyboard//ob:keyboardLayout//ob:rules", ctxt); + config->keyboard_layout.variant = parse_xpath_expr("//ob:keyboard//ob:keyboardLayout//ob:variant", ctxt); + } if (!parse_key_bindings(config, ctxt)) { xmlFreeDoc(doc); return false; diff --git a/waybox/config.h b/waybox/config.h index 7be672c..e90c8f9 100644 --- a/waybox/config.h +++ b/waybox/config.h @@ -21,6 +21,8 @@ struct wb_config { char *options; char *rules; char *variant; + + bool use_config; } keyboard_layout; struct wl_list applications; diff --git a/waybox/cursor.c b/waybox/cursor.c index 0512fee..33bfaeb 100644 --- a/waybox/cursor.c +++ b/waybox/cursor.c @@ -78,17 +78,16 @@ static void process_cursor_motion(struct wb_server *server, uint32_t time) { server->cursor->xcursor_manager, "left_ptr", server->cursor->cursor); } if (surface) { - bool focus_changed = seat->pointer_state.focused_surface != surface; /* * "Enter" the surface if necessary. This lets the client know that the * cursor has entered one of its surfaces. + * + * Note that wlroots will avoid sending duplicate enter/motion events if + * the surface has already has pointer focus or if the client is already + * aware of the coordinates passed. */ wlr_seat_pointer_notify_enter(seat, surface, sx, sy); - if (!focus_changed) { - /* The enter event contains coordinates, so we only need to notify - * on motion if the focus did not change. */ - wlr_seat_pointer_notify_motion(seat, time, sx, sy); - } + wlr_seat_pointer_notify_motion(seat, time, sx, sy); } else { /* Clear pointer focus so future button events and such are not sent to * the last client to have the cursor over it. */ @@ -158,7 +157,7 @@ static void handle_cursor_frame(struct wl_listener *listener, void *data) { static void handle_cursor_request(struct wl_listener *listener, void *data) { struct wb_cursor *cursor = wl_container_of( listener, cursor, request_cursor); - /* This event is rasied by the seat when a client provides a cursor image */ + /* This event is raised by the seat when a client provides a cursor image */ struct wlr_seat_pointer_request_set_cursor_event *event = data; struct wlr_seat_client *focused_client = cursor->server->seat->seat->pointer_state.focused_client; diff --git a/waybox/output.c b/waybox/output.c index 787eb6a..83238e7 100644 --- a/waybox/output.c +++ b/waybox/output.c @@ -198,6 +198,14 @@ void new_output_notify(struct wl_listener *listener, void *data) { output->frame.notify = output_frame_notify; wl_signal_add(&wlr_output->events.frame, &output->frame); + /* Adds this to the output layout. The add_auto function arranges outputs + * from left-to-right in the order they appear. A more sophisticated + * compositor would let the user configure the arrangement of outputs in the + * layout. + * + * The output layout utility automatically adds a wl_output global to the + * display, which Wayland clients can see to find out information about the + * output (such as DPI, scale factor, manufacturer, etc). + */ wlr_output_layout_add_auto(server->output_layout, wlr_output); - wlr_output_create_global(wlr_output); } diff --git a/waybox/seat.c b/waybox/seat.c index 98d2e89..290cff1 100644 --- a/waybox/seat.c +++ b/waybox/seat.c @@ -161,36 +161,35 @@ static void handle_new_keyboard(struct wb_server *server, keyboard->device = device; /* We need to prepare an XKB keymap and assign it to the keyboard. */ - struct xkb_rule_names rules = {0}; - if (server->config && server->config->keyboard_layout.layout) - rules.layout = server->config->keyboard_layout.layout; + struct xkb_rule_names *rules = malloc(sizeof(struct xkb_rule_names)); + if (server->config && server->config->keyboard_layout.use_config) + { + if (server->config->keyboard_layout.layout) + rules->layout = server->config->keyboard_layout.layout; + if (server->config->keyboard_layout.model) + rules->model = server->config->keyboard_layout.model; + if (server->config->keyboard_layout.options) + rules->options = server->config->keyboard_layout.options; + if (server->config->keyboard_layout.rules) + rules->rules = server->config->keyboard_layout.rules; + if (server->config->keyboard_layout.variant) + rules->variant = server->config->keyboard_layout.variant; + } else - rules.layout = getenv("XKB_DEFAULT_LAYOUT"); - if (server->config && server->config->keyboard_layout.model) - rules.model = server->config->keyboard_layout.model; - else - rules.model = getenv("XKB_DEFAULT_MODEL"); - if (server->config && server->config->keyboard_layout.options) - rules.options = server->config->keyboard_layout.options; - else - rules.options = getenv("XKB_DEFAULT_OPTIONS"); - if (server->config && server->config->keyboard_layout.rules) - rules.rules = server->config->keyboard_layout.rules; - else - rules.rules = getenv("XKB_DEFAULT_RULES"); - if (server->config && server->config->keyboard_layout.variant) - rules.variant = server->config->keyboard_layout.variant; - else - rules.variant = getenv("XKB_DEFAULT_VARIANT"); + /* If a NULL xkb_rule_names pointer is passed to + xkb_keymap_new_from_names, libxkbcommon will default to reading + the XKB_* env variables. So there's no need to do it ourselves. */ + rules = NULL; struct xkb_context *context = xkb_context_new(XKB_CONTEXT_NO_FLAGS); - struct xkb_keymap *keymap = xkb_map_new_from_names(context, &rules, + struct xkb_keymap *keymap = xkb_keymap_new_from_names(context, rules, XKB_KEYMAP_COMPILE_NO_FLAGS); if (keymap != NULL) { wlr_keyboard_set_keymap(device->keyboard, keymap); wlr_keyboard_set_repeat_info(device->keyboard, 25, 600); } + free(rules); xkb_keymap_unref(keymap); xkb_context_unref(context);