mirror of
https://github.com/labwc/labwc.git
synced 2026-02-06 04:06:33 -05:00
keyboard: allow applying keyboard layout per window
Fixes #1076 It can be enabled with a config like ~/.config/labwc/rc.xml: <keyboard layoutScope="window"> ~/.config/labwc/environment: XKB_DEFAULT_LAYOUT=de,us XKB_DEFAULT_OPTIONS=grp:alt_shift_toggle,grp_led:scroll With a configuration like this each window should now remember the active keyboard layout when switching between windows. By default, the keyboard layout keeps being a global state.
This commit is contained in:
parent
f1c2664ad1
commit
984aeb0b0b
9 changed files with 66 additions and 3 deletions
|
|
@ -283,6 +283,10 @@ windows using the mouse.
|
||||||
When recognizing a new keyboard enable or disable Num Lock.
|
When recognizing a new keyboard enable or disable Num Lock.
|
||||||
Default is on.
|
Default is on.
|
||||||
|
|
||||||
|
*<keyboard layoutScope="">* [global|window]
|
||||||
|
Stores the keyboard layout either globally or per window and restores
|
||||||
|
it when switching back to the window. Default is global.
|
||||||
|
|
||||||
*<keyboard><keybind key="" layoutDependent="">*
|
*<keyboard><keybind key="" layoutDependent="">*
|
||||||
Define a *key* binding in the format *modifier-key*, where supported
|
Define a *key* binding in the format *modifier-key*, where supported
|
||||||
modifiers are:
|
modifiers are:
|
||||||
|
|
|
||||||
|
|
@ -142,6 +142,7 @@
|
||||||
-->
|
-->
|
||||||
<keyboard>
|
<keyboard>
|
||||||
<numlock>on</numlock>
|
<numlock>on</numlock>
|
||||||
|
<layoutScope>global</layoutScope>
|
||||||
<repeatRate>25</repeatRate>
|
<repeatRate>25</repeatRate>
|
||||||
<repeatDelay>600</repeatDelay>
|
<repeatDelay>600</repeatDelay>
|
||||||
<keybind key="A-Tab">
|
<keybind key="A-Tab">
|
||||||
|
|
|
||||||
|
|
@ -63,6 +63,7 @@ struct rcxml {
|
||||||
int repeat_rate;
|
int repeat_rate;
|
||||||
int repeat_delay;
|
int repeat_delay;
|
||||||
bool kb_numlock_enable;
|
bool kb_numlock_enable;
|
||||||
|
bool kb_layout_per_window;
|
||||||
struct wl_list keybinds; /* struct keybind.link */
|
struct wl_list keybinds; /* struct keybind.link */
|
||||||
|
|
||||||
/* mouse */
|
/* mouse */
|
||||||
|
|
|
||||||
|
|
@ -3,6 +3,7 @@
|
||||||
#define LABWC_KEYBOARD_H
|
#define LABWC_KEYBOARD_H
|
||||||
|
|
||||||
#include <stdbool.h>
|
#include <stdbool.h>
|
||||||
|
#include <xkbcommon/xkbcommon.h>
|
||||||
|
|
||||||
struct seat;
|
struct seat;
|
||||||
struct keyboard;
|
struct keyboard;
|
||||||
|
|
@ -13,6 +14,7 @@ void keyboard_finish(struct seat *seat);
|
||||||
|
|
||||||
void keyboard_setup_handlers(struct keyboard *keyboard);
|
void keyboard_setup_handlers(struct keyboard *keyboard);
|
||||||
void keyboard_set_numlock(struct wlr_keyboard *keyboard);
|
void keyboard_set_numlock(struct wlr_keyboard *keyboard);
|
||||||
|
void keyboard_update_layout(struct seat *seat, xkb_layout_index_t layout);
|
||||||
void keyboard_cancel_keybind_repeat(struct keyboard *keyboard);
|
void keyboard_cancel_keybind_repeat(struct keyboard *keyboard);
|
||||||
bool keyboard_any_modifiers_pressed(struct wlr_keyboard *keyboard);
|
bool keyboard_any_modifiers_pressed(struct wlr_keyboard *keyboard);
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -39,7 +39,6 @@
|
||||||
#include <wlr/types/wlr_virtual_pointer_v1.h>
|
#include <wlr/types/wlr_virtual_pointer_v1.h>
|
||||||
#include <wlr/types/wlr_virtual_keyboard_v1.h>
|
#include <wlr/types/wlr_virtual_keyboard_v1.h>
|
||||||
#include <wlr/util/log.h>
|
#include <wlr/util/log.h>
|
||||||
#include <xkbcommon/xkbcommon.h>
|
|
||||||
#include "config/keybind.h"
|
#include "config/keybind.h"
|
||||||
#include "config/rcxml.h"
|
#include "config/rcxml.h"
|
||||||
#include "input/cursor.h"
|
#include "input/cursor.h"
|
||||||
|
|
|
||||||
|
|
@ -7,6 +7,7 @@
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
#include <wayland-util.h>
|
#include <wayland-util.h>
|
||||||
#include <wlr/util/box.h>
|
#include <wlr/util/box.h>
|
||||||
|
#include <xkbcommon/xkbcommon.h>
|
||||||
|
|
||||||
#define LAB_MIN_VIEW_WIDTH 100
|
#define LAB_MIN_VIEW_WIDTH 100
|
||||||
#define LAB_MIN_VIEW_HEIGHT 60
|
#define LAB_MIN_VIEW_HEIGHT 60
|
||||||
|
|
@ -143,6 +144,7 @@ struct view {
|
||||||
bool fullscreen;
|
bool fullscreen;
|
||||||
enum view_edge tiled;
|
enum view_edge tiled;
|
||||||
bool inhibits_keybinds;
|
bool inhibits_keybinds;
|
||||||
|
xkb_layout_index_t keyboard_layout;
|
||||||
|
|
||||||
/* Pointer to an output owned struct region, may be NULL */
|
/* Pointer to an output owned struct region, may be NULL */
|
||||||
struct region *tiled_region;
|
struct region *tiled_region;
|
||||||
|
|
|
||||||
|
|
@ -735,6 +735,12 @@ entry(xmlNode *node, char *nodename, char *content)
|
||||||
rc.repeat_delay = atoi(content);
|
rc.repeat_delay = atoi(content);
|
||||||
} else if (!strcasecmp(nodename, "numlock.keyboard")) {
|
} else if (!strcasecmp(nodename, "numlock.keyboard")) {
|
||||||
set_bool(content, &rc.kb_numlock_enable);
|
set_bool(content, &rc.kb_numlock_enable);
|
||||||
|
} else if (!strcasecmp(nodename, "layoutScope.keyboard")) {
|
||||||
|
/*
|
||||||
|
* This can be changed to an enum later on
|
||||||
|
* if we decide to also support "application".
|
||||||
|
*/
|
||||||
|
rc.kb_layout_per_window = !strcasecmp(content, "window");
|
||||||
} else if (!strcasecmp(nodename, "screenEdgeStrength.resistance")) {
|
} else if (!strcasecmp(nodename, "screenEdgeStrength.resistance")) {
|
||||||
rc.screen_edge_strength = atoi(content);
|
rc.screen_edge_strength = atoi(content);
|
||||||
} else if (!strcasecmp(nodename, "range.snapping")) {
|
} else if (!strcasecmp(nodename, "range.snapping")) {
|
||||||
|
|
@ -953,6 +959,7 @@ rcxml_init(void)
|
||||||
rc.repeat_rate = 25;
|
rc.repeat_rate = 25;
|
||||||
rc.repeat_delay = 600;
|
rc.repeat_delay = 600;
|
||||||
rc.kb_numlock_enable = true;
|
rc.kb_numlock_enable = true;
|
||||||
|
rc.kb_layout_per_window = false;
|
||||||
rc.screen_edge_strength = 20;
|
rc.screen_edge_strength = 20;
|
||||||
|
|
||||||
rc.snap_edge_range = 1;
|
rc.snap_edge_range = 1;
|
||||||
|
|
|
||||||
|
|
@ -84,6 +84,7 @@ keyboard_modifiers_notify(struct wl_listener *listener, void *data)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
wlr_seat_set_keyboard(seat->seat, wlr_keyboard);
|
||||||
wlr_seat_keyboard_notify_modifiers(seat->seat, &wlr_keyboard->modifiers);
|
wlr_seat_keyboard_notify_modifiers(seat->seat, &wlr_keyboard->modifiers);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -485,7 +486,6 @@ keyboard_key_notify(struct wl_listener *listener, void *data)
|
||||||
struct seat *seat = keyboard->base.seat;
|
struct seat *seat = keyboard->base.seat;
|
||||||
struct wlr_keyboard_key_event *event = data;
|
struct wlr_keyboard_key_event *event = data;
|
||||||
struct wlr_seat *wlr_seat = seat->seat;
|
struct wlr_seat *wlr_seat = seat->seat;
|
||||||
struct wlr_keyboard *wlr_keyboard = keyboard->wlr_keyboard;
|
|
||||||
idle_manager_notify_activity(seat->seat);
|
idle_manager_notify_activity(seat->seat);
|
||||||
|
|
||||||
/* any new press/release cancels current keybind repeat */
|
/* any new press/release cancels current keybind repeat */
|
||||||
|
|
@ -497,7 +497,7 @@ keyboard_key_notify(struct wl_listener *listener, void *data)
|
||||||
start_keybind_repeat(seat->server, keyboard, event);
|
start_keybind_repeat(seat->server, keyboard, event);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
wlr_seat_set_keyboard(wlr_seat, wlr_keyboard);
|
wlr_seat_set_keyboard(wlr_seat, keyboard->wlr_keyboard);
|
||||||
wlr_seat_keyboard_notify_key(wlr_seat, event->time_msec,
|
wlr_seat_keyboard_notify_key(wlr_seat, event->time_msec,
|
||||||
event->keycode, event->state);
|
event->keycode, event->state);
|
||||||
}
|
}
|
||||||
|
|
@ -530,6 +530,41 @@ keyboard_set_numlock(struct wlr_keyboard *keyboard)
|
||||||
keyboard->modifiers.latched, locked, keyboard->modifiers.group);
|
keyboard->modifiers.latched, locked, keyboard->modifiers.group);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
keyboard_update_layout(struct seat *seat, xkb_layout_index_t layout)
|
||||||
|
{
|
||||||
|
assert(seat);
|
||||||
|
|
||||||
|
struct input *input;
|
||||||
|
struct keyboard *keyboard;
|
||||||
|
struct wlr_keyboard *kb = NULL;
|
||||||
|
|
||||||
|
/* We are not using wlr_seat_get_keyboard() here because it might be a virtual one */
|
||||||
|
wl_list_for_each(input, &seat->inputs, link) {
|
||||||
|
if (input->wlr_input_device->type != WLR_INPUT_DEVICE_KEYBOARD) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
keyboard = (struct keyboard *)input;
|
||||||
|
if (keyboard->is_virtual) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
kb = keyboard->wlr_keyboard;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if (!kb) {
|
||||||
|
wlr_log(WLR_INFO, "Restoring kb layout failed: no physical keyboard found");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (kb->modifiers.group == layout) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* By updating a member of the keyboard group, all members of the group will get updated */
|
||||||
|
wlr_log(WLR_DEBUG, "Updating group layout to %u", layout);
|
||||||
|
wlr_keyboard_notify_modifiers(kb, kb->modifiers.depressed,
|
||||||
|
kb->modifiers.latched, kb->modifiers.locked, layout);
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
keyboard_init(struct seat *seat)
|
keyboard_init(struct seat *seat)
|
||||||
{
|
{
|
||||||
|
|
|
||||||
12
src/view.c
12
src/view.c
|
|
@ -6,6 +6,7 @@
|
||||||
#include "common/match.h"
|
#include "common/match.h"
|
||||||
#include "common/mem.h"
|
#include "common/mem.h"
|
||||||
#include "common/scene-helpers.h"
|
#include "common/scene-helpers.h"
|
||||||
|
#include "input/keyboard.h"
|
||||||
#include "labwc.h"
|
#include "labwc.h"
|
||||||
#include "menu/menu.h"
|
#include "menu/menu.h"
|
||||||
#include "regions.h"
|
#include "regions.h"
|
||||||
|
|
@ -266,6 +267,17 @@ view_set_activated(struct view *view, bool activated)
|
||||||
wlr_foreign_toplevel_handle_v1_set_activated(
|
wlr_foreign_toplevel_handle_v1_set_activated(
|
||||||
view->toplevel.handle, activated);
|
view->toplevel.handle, activated);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (rc.kb_layout_per_window) {
|
||||||
|
if (!activated) {
|
||||||
|
/* Store configured keyboard layout per view */
|
||||||
|
view->keyboard_layout =
|
||||||
|
view->server->seat.keyboard_group->keyboard.modifiers.group;
|
||||||
|
} else {
|
||||||
|
/* Switch to previously stored keyboard layout */
|
||||||
|
keyboard_update_layout(&view->server->seat, view->keyboard_layout);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue