The value that shall be used for the _NET_WM_NAME property of the root window.
button_modifier
- The modifier mask used for mouse bindings (possible values: 'mod1' ... 'mod5').
+ The modifier mask used for mouse bindings (possible values: 'shift', 'control', 'lock', 'mod1' ... 'mod5').
+
+ numlock_modifier
+ The modifier holding Num_Lock (cf. xmodmap).
+
+ capslock_modifier
+ The modifier holding Lock.
borderless_monocle
Whether to remove borders for tiled windows in monocle mode.
.TP
.I button_modifier
The modifier mask used for mouse bindings (possible values:
-.BR mod1 " ... " mod5 ).
+.BR shift ", " control ", " lock ", " mod1 " ... " mod5 ).
+.TP
+.I numlock_modifier
+The modifier holding Num_Lock (cf.
+.BR xmodmap (1).
+.TP
+.I capslock_modifier
+The modifier holding Lock (cf.
.TP
.I borderless_monocle
Whether to remove borders for tiled windows in monocle mode.
}
}
+void handle_buttons(bool grab)
+{
+ uint8_t buts[] = {XCB_BUTTON_INDEX_1, XCB_BUTTON_INDEX_2, XCB_BUTTON_INDEX_3};
+ uint16_t mods[] = {button_modifier, button_modifier | numlock_modifier, button_modifier | capslock_modifier, button_modifier | numlock_modifier | capslock_modifier};
+
+ for (unsigned int i = 0; i < LENGTH(buts); i++) {
+ uint8_t b = buts[i];
+ for (unsigned int j = 0; j < LENGTH(mods); j++) {
+ uint16_t m = mods[j];
+ if (grab)
+ xcb_grab_button(dpy, false, screen->root, XCB_EVENT_MASK_BUTTON_PRESS, XCB_GRAB_MODE_ASYNC, XCB_GRAB_MODE_ASYNC, XCB_NONE, XCB_NONE, b, m);
+ else
+ xcb_ungrab_button(dpy, b, screen->root, m);
+ }
+ }
+}
+
void grab_buttons(void)
{
- xcb_grab_button(dpy, false, screen->root, XCB_EVENT_MASK_BUTTON_PRESS, XCB_GRAB_MODE_ASYNC, XCB_GRAB_MODE_ASYNC, XCB_NONE, XCB_NONE, XCB_BUTTON_INDEX_1, button_modifier);
- xcb_grab_button(dpy, false, screen->root, XCB_EVENT_MASK_BUTTON_PRESS, XCB_GRAB_MODE_ASYNC, XCB_GRAB_MODE_ASYNC, XCB_NONE, XCB_NONE, XCB_BUTTON_INDEX_2, button_modifier);
- xcb_grab_button(dpy, false, screen->root, XCB_EVENT_MASK_BUTTON_PRESS, XCB_GRAB_MODE_ASYNC, XCB_GRAB_MODE_ASYNC, XCB_NONE, XCB_NONE, XCB_BUTTON_INDEX_3, button_modifier);
- xcb_grab_button(dpy, false, screen->root, XCB_EVENT_MASK_BUTTON_PRESS, XCB_GRAB_MODE_ASYNC, XCB_GRAB_MODE_ASYNC, XCB_NONE, XCB_NONE, XCB_BUTTON_INDEX_1, button_modifier | XCB_MOD_MASK_LOCK);
- xcb_grab_button(dpy, false, screen->root, XCB_EVENT_MASK_BUTTON_PRESS, XCB_GRAB_MODE_ASYNC, XCB_GRAB_MODE_ASYNC, XCB_NONE, XCB_NONE, XCB_BUTTON_INDEX_2, button_modifier | XCB_MOD_MASK_LOCK);
- xcb_grab_button(dpy, false, screen->root, XCB_EVENT_MASK_BUTTON_PRESS, XCB_GRAB_MODE_ASYNC, XCB_GRAB_MODE_ASYNC, XCB_NONE, XCB_NONE, XCB_BUTTON_INDEX_3, button_modifier | XCB_MOD_MASK_LOCK);
+ handle_buttons(true);
}
void ungrab_buttons(void)
{
- xcb_ungrab_button(dpy, XCB_BUTTON_INDEX_1, screen->root, button_modifier);
- xcb_ungrab_button(dpy, XCB_BUTTON_INDEX_2, screen->root, button_modifier);
- xcb_ungrab_button(dpy, XCB_BUTTON_INDEX_3, screen->root, button_modifier);
- xcb_ungrab_button(dpy, XCB_BUTTON_INDEX_1, screen->root, button_modifier | XCB_MOD_MASK_LOCK);
- xcb_ungrab_button(dpy, XCB_BUTTON_INDEX_2, screen->root, button_modifier | XCB_MOD_MASK_LOCK);
- xcb_ungrab_button(dpy, XCB_BUTTON_INDEX_3, screen->root, button_modifier | XCB_MOD_MASK_LOCK);
+ handle_buttons(false);
}
void setup(void)
bool running;
void register_events(void);
+void handle_buttons(bool);
void grab_buttons(void);
void ungrab_buttons(void);
void setup(void);
xcb_button_press_event_t *e = (xcb_button_press_event_t *) evt;
xcb_window_t win = e->child;
- PRINTF("button press %u %X\n", e->detail, win);
+ PRINTF("button press %u %u %X\n", e->detail, e->state, win);
window_location_t loc;
if (locate_window(win, &loc)) {
grab_buttons();
}
return;
+ } else if (strcmp(name, "numlock_modifier") == 0) {
+ unsigned int m;
+ if (parse_modifier_mask(value, &m)) {
+ ungrab_buttons();
+ numlock_modifier = m;
+ grab_buttons();
+ }
+ return;
+ } else if (strcmp(name, "capslock_modifier") == 0) {
+ unsigned int m;
+ if (parse_modifier_mask(value, &m)) {
+ ungrab_buttons();
+ capslock_modifier = m;
+ grab_buttons();
+ }
+ return;
} else {
snprintf(rsp, BUFSIZ, "unknown setting: %s", name);
return;
snprintf(rsp, BUFSIZ, "%s", wm_name);
else if (strcmp(name, "button_modifier") == 0)
print_modifier_mask(rsp, button_modifier);
+ else if (strcmp(name, "numlock_modifier") == 0)
+ print_modifier_mask(rsp, numlock_modifier);
+ else if (strcmp(name, "capslock_modifier") == 0)
+ print_modifier_mask(rsp, capslock_modifier);
else
snprintf(rsp, BUFSIZ, "unknown setting: %s", name);
}
bool parse_modifier_mask(char *s, unsigned int *m)
{
- if (strcmp(s, "mod1") == 0) {
+ if (strcmp(s, "shift") == 0) {
+ *m = XCB_MOD_MASK_SHIFT;
+ return true;
+ } else if (strcmp(s, "control") == 0) {
+ *m = XCB_MOD_MASK_CONTROL;
+ return true;
+ } else if (strcmp(s, "lock") == 0) {
+ *m = XCB_MOD_MASK_LOCK;
+ return true;
+ } else if (strcmp(s, "mod1") == 0) {
+ *m = XCB_MOD_MASK_1;
+ return true;
+ } else if (strcmp(s, "mod1") == 0) {
*m = XCB_MOD_MASK_1;
return true;
} else if (strcmp(s, "mod2") == 0) {
void print_modifier_mask(char *s, unsigned int m)
{
switch(m) {
+ case XCB_MOD_MASK_SHIFT:
+ snprintf(s, BUFSIZ, "shift");
+ break;
+ case XCB_MOD_MASK_CONTROL:
+ snprintf(s, BUFSIZ, "control");
+ break;
+ case XCB_MOD_MASK_LOCK:
+ snprintf(s, BUFSIZ, "lock");
+ break;
case XCB_MOD_MASK_1:
snprintf(s, BUFSIZ, "mod1");
break;
strncpy(wm_name, WM_NAME, sizeof(wm_name));
button_modifier = BUTTON_MODIFIER;
+ numlock_modifier = NUMLOCK_MODIFIER;
+ capslock_modifier = CAPSLOCK_MODIFIER;
inner_border_width = INNER_BORDER_WIDTH;
main_border_width = MAIN_BORDER_WIDTH;
#define WM_NAME "bspwm"
#define AUTOSTART_FILE "autostart"
#define BUTTON_MODIFIER XCB_MOD_MASK_4
+#define NUMLOCK_MODIFIER XCB_MOD_MASK_2
+#define CAPSLOCK_MODIFIER XCB_MOD_MASK_LOCK
#define FOCUSED_BORDER_COLOR "#7D7F8A"
#define ACTIVE_BORDER_COLOR "#7D7F8A"
char wm_name[MAXLEN];
unsigned int button_modifier;
+unsigned int numlock_modifier;
+unsigned int capslock_modifier;
void load_settings(void);
void run_autostart(void);