]> git.lizzy.rs Git - bspwm.git/commitdiff
Remove settings: '{numlock,capslock}_modifier'
authorBastien Dejean <nihilhill@gmail.com>
Wed, 2 Jan 2013 11:36:54 +0000 (12:36 +0100)
committerBastien Dejean <nihilhill@gmail.com>
Wed, 2 Jan 2013 11:36:54 +0000 (12:36 +0100)
The lock keys (num, caps, scroll) are now handled internally and the
aforementioned settings are obsolete.

15 files changed:
Makefile
README.md
bspwm.1
bspwm.c
bspwm.h
buttons.c [new file with mode: 0644]
buttons.h [new file with mode: 0644]
events.c
events.h
ewmh.c
helpers.c
messages.c
settings.c
settings.h
window.c

index 196871bd605ca4f8b43b4fb792945ecd70af8eba..f7da695ac214af4aca444f405981ea31e0a58436 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -1,7 +1,7 @@
 VERSION = 0.3
 
 CC      = gcc
-LIBS    = -lm -lxcb -lxcb-icccm -lxcb-ewmh -lxcb-xinerama
+LIBS    = -lm -lxcb -lxcb-keysyms -lxcb-icccm -lxcb-ewmh -lxcb-xinerama
 CFLAGS  = -std=c99 -pedantic -Wall -Wextra -DVERSION=\"$(VERSION)\"
 LDFLAGS = $(LIBS)
 
@@ -9,7 +9,7 @@ PREFIX    ?= /usr/local
 BINPREFIX = $(PREFIX)/bin
 MANPREFIX = $(PREFIX)/share/man
 
-WM_SRC = bspwm.c events.c messages.c ewmh.c settings.c helpers.c tree.c types.c rules.c window.c
+WM_SRC = bspwm.c events.c messages.c buttons.c ewmh.c settings.c helpers.c tree.c types.c rules.c window.c
 CL_SRC = bspc.c helpers.c
 
 WM_OBJ = $(WM_SRC:.c=.o)
index c97a0ccd257f0c5a7ac80e55b02ed958345ce998..f0928288a67b52217d805fa8e9a28f4a73d87eea 100644 (file)
--- a/README.md
+++ b/README.md
@@ -269,12 +269,6 @@ Colors are either [X color names](http://en.wikipedia.org/wiki/X11_color_names)
     button_modifier
         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.
 
@@ -318,6 +312,7 @@ Multiple choices:
 - libxcb
 - xcb-util
 - xcb-util-wm
+- xcb-util-keysyms
 
 ## Installation
 
diff --git a/bspwm.1 b/bspwm.1
index b7c4b563a17c073d25c0d64bd10e4192f28a9d29..fd2919d821f5edf946d09f707040284be8a2589c 100644 (file)
--- a/bspwm.1
+++ b/bspwm.1
@@ -316,13 +316,6 @@ property of the root window.
 The modifier mask used for mouse bindings (possible values:
 .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.
-.TP
 .I borderless_monocle
 Whether to remove borders for tiled windows in monocle mode.
 .TP
diff --git a/bspwm.c b/bspwm.c
index 377052efe51c1f2ed7ac640e262d0f8fbc724d02..69177e22c2832fdcd79dc96e3928c026c0162abc 100644 (file)
--- a/bspwm.c
+++ b/bspwm.c
 #include <xcb/xcb.h>
 #include <xcb/xcb_event.h>
 #include <xcb/xcb_ewmh.h>
+#include <xcb/xcb_keysyms.h>
 #include <xcb/xinerama.h>
 #include "types.h"
 #include "settings.h"
+#include "buttons.h"
 #include "messages.h"
 #include "rules.h"
 #include "events.h"
@@ -37,51 +39,26 @@ void cleanup(void)
     while (rule_head != NULL)
         remove_rule(rule_head);
     free(frozen_pointer);
+    xcb_key_symbols_free(symbols);
 }
 
 void register_events(void)
 {
     uint32_t values[] = {ROOT_EVENT_MASK};
-    xcb_generic_error_t *e = xcb_request_check(dpy, xcb_change_window_attributes_checked(dpy, screen->root, XCB_CW_EVENT_MASK, values));
+    xcb_generic_error_t *e = xcb_request_check(dpy, xcb_change_window_attributes_checked(dpy, root, XCB_CW_EVENT_MASK, values));
     if (e != NULL) {
         xcb_disconnect(dpy);
         err("another wm is already running\n");
     }
 }
 
-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)
-{
-    handle_buttons(true);
-}
-
-void ungrab_buttons(void)
-{
-    handle_buttons(false);
-}
-
 void setup(void)
 {
     ewmh_init();
     screen = xcb_setup_roots_iterator(xcb_get_setup(dpy)).data;
     if (!screen)
         err("can't acquire screen\n");
+    root = screen->root;
     register_events();
 
     screen_width = screen->width_in_pixels;
@@ -143,6 +120,7 @@ void setup(void)
     ewmh_update_desktop_names();
     ewmh_update_current_desktop();
     rule_head = rule_tail = NULL;
+    symbols = xcb_key_symbols_alloc(dpy);
     frozen_pointer = make_pointer_state();
     get_pointer_position(&pointer_position);
     last_entered = XCB_NONE;
@@ -212,6 +190,7 @@ int main(int argc, char *argv[])
 
     load_settings();
     run_autostart();
+    get_lock_fields();
     grab_buttons();
     ewmh_update_wm_name();
 
@@ -223,7 +202,7 @@ int main(int argc, char *argv[])
         FD_SET(sock_fd, &descriptors);
         FD_SET(dpy_fd, &descriptors);
 
-        if (select(sel, &descriptors, NULL, NULL, NULL)) {
+        if (select(sel, &descriptors, NULL, NULL, NULL) > 0) {
 
             if (FD_ISSET(sock_fd, &descriptors)) {
                 ret_fd = accept(sock_fd, NULL, 0);
diff --git a/bspwm.h b/bspwm.h
index 2ab0bc2b5228ecda19a8ba9eae84ce8f1e7fe0c0..572fdb3e207083b9d8fb0b1efec8a8f1dcdd2a87 100644 (file)
--- a/bspwm.h
+++ b/bspwm.h
@@ -16,6 +16,7 @@ unsigned int desktop_uid;
 unsigned int client_uid;
 unsigned int rule_uid;
 xcb_screen_t *screen;
+xcb_window_t root;
 uint8_t root_depth;
 FILE *status_fifo;
 
@@ -27,9 +28,11 @@ monitor_t *mon_head;
 monitor_t *mon_tail;
 rule_t *rule_head;
 rule_t *rule_tail;
+
 pointer_state_t *frozen_pointer;
 xcb_point_t pointer_position;
 xcb_window_t last_entered;
+
 int exit_status;
 
 bool visible;
diff --git a/buttons.c b/buttons.c
new file mode 100644 (file)
index 0000000..b3e0120
--- /dev/null
+++ b/buttons.c
@@ -0,0 +1,74 @@
+#include <stdlib.h>
+#include <xcb/xcb_keysyms.h>
+#include "settings.h"
+#include "bspwm.h"
+#include "helpers.h"
+#include "types.h"
+#include "buttons.h"
+
+void grab_buttons(void)
+{
+#define GRAB(b, m)  xcb_grab_button(dpy, false, root, XCB_EVENT_MASK_BUTTON_PRESS, XCB_GRAB_MODE_ASYNC, XCB_GRAB_MODE_ASYNC, XCB_NONE, XCB_NONE, b, m)
+    uint8_t buttons[] = {XCB_BUTTON_INDEX_1, XCB_BUTTON_INDEX_2, XCB_BUTTON_INDEX_3};
+    for (unsigned int i = 0; i < LENGTH(buttons); i++) {
+        uint8_t button = buttons[i];
+        GRAB(button, button_modifier);
+        if (num_lock != XCB_NO_SYMBOL && caps_lock != XCB_NO_SYMBOL && scroll_lock != XCB_NO_SYMBOL)
+            GRAB(button, button_modifier | num_lock | caps_lock | scroll_lock);
+        if (num_lock != XCB_NO_SYMBOL && caps_lock != XCB_NO_SYMBOL)
+            GRAB(button, button_modifier | num_lock | caps_lock);
+        if (caps_lock != XCB_NO_SYMBOL && scroll_lock != XCB_NO_SYMBOL)
+            GRAB(button, button_modifier | caps_lock | scroll_lock);
+        if (num_lock != XCB_NO_SYMBOL && scroll_lock != XCB_NO_SYMBOL)
+            GRAB(button, button_modifier | num_lock | scroll_lock);
+        if (num_lock != XCB_NO_SYMBOL)
+            GRAB(button, button_modifier | num_lock);
+        if (caps_lock != XCB_NO_SYMBOL)
+            GRAB(button, button_modifier | caps_lock);
+        if (scroll_lock != XCB_NO_SYMBOL)
+            GRAB(button, button_modifier | scroll_lock);
+    }
+#undef GRAB
+}
+
+void ungrab_buttons(void)
+{
+    xcb_ungrab_button(dpy, XCB_BUTTON_INDEX_ANY, root, XCB_MOD_MASK_ANY);
+}
+
+void get_lock_fields(void)
+{
+    num_lock = modfield_from_keysym(XK_Num_Lock);
+    caps_lock = modfield_from_keysym(XK_Caps_Lock);
+    scroll_lock = modfield_from_keysym(XK_Scroll_Lock);
+    if (caps_lock == XCB_NO_SYMBOL)
+        caps_lock = XCB_MOD_MASK_LOCK;
+}
+
+int16_t modfield_from_keysym(xcb_keysym_t keysym)
+{
+    uint16_t modfield = 0;
+    xcb_keycode_t *keycodes = NULL, *mod_keycodes = NULL;
+    xcb_get_modifier_mapping_reply_t *reply = NULL;
+    if ((keycodes = xcb_key_symbols_get_keycode(symbols, keysym)) != NULL) {
+        if ((reply = xcb_get_modifier_mapping_reply(dpy, xcb_get_modifier_mapping(dpy), NULL)) != NULL) {
+            if ((mod_keycodes = xcb_get_modifier_mapping_keycodes(reply)) != NULL) {
+                unsigned int num_mod = xcb_get_modifier_mapping_keycodes_length(reply) / reply->keycodes_per_modifier;
+                for (unsigned int i = 0; i < num_mod; i++) {
+                    for (unsigned int j = 0; j < reply->keycodes_per_modifier; j++) {
+                        xcb_keycode_t mk = mod_keycodes[i * reply->keycodes_per_modifier + j];
+                        if (mk == XCB_NO_SYMBOL)
+                            continue;
+                        for (xcb_keycode_t *k = keycodes; *k != XCB_NO_SYMBOL; k++)
+                            if (*k == mk)
+                                modfield |= (1 << i);
+                    }
+                }
+
+            }
+        }
+    }
+    free(keycodes);
+    free(reply);
+    return modfield;
+}
diff --git a/buttons.h b/buttons.h
new file mode 100644 (file)
index 0000000..1477ba0
--- /dev/null
+++ b/buttons.h
@@ -0,0 +1,19 @@
+#ifndef _BUTTONS_H
+#define _BUTTONS_H
+
+#define XK_Num_Lock     0xff7f
+#define XK_Caps_Lock    0xffe5
+#define XK_Scroll_Lock  0xff14
+
+uint16_t num_lock;
+uint16_t caps_lock;
+uint16_t scroll_lock;
+
+xcb_key_symbols_t *symbols;
+
+void grab_buttons(void);
+void ungrab_buttons(void);
+void get_lock_fields(void);
+int16_t modfield_from_keysym(xcb_keysym_t);
+
+#endif
index b79eb616eeb55e8ad5afb9f3145bc8225114906f..00e6b90534c802c48c77526277820de7037bffad 100644 (file)
--- a/events.c
+++ b/events.c
@@ -2,11 +2,13 @@
 #include <stdlib.h>
 #include <string.h>
 #include <xcb/xcb.h>
+#include <xcb/xcb_keysyms.h>
 #include <xcb/xcb_event.h>
 #include <xcb/xcb_icccm.h>
 #include "types.h"
 #include "bspwm.h"
 #include "settings.h"
+#include "buttons.h"
 #include "helpers.h"
 #include "window.h"
 #include "events.h"
@@ -35,6 +37,9 @@ void handle_event(xcb_generic_event_t *evt)
         case XCB_PROPERTY_NOTIFY:
             property_notify(evt);
             break;
+        case XCB_MAPPING_NOTIFY:
+            mapping_notify(evt);
+            break;
         case XCB_ENTER_NOTIFY:
             enter_notify(evt);
             break;
@@ -200,6 +205,17 @@ void property_notify(xcb_generic_event_t *evt)
     }
 }
 
+void mapping_notify(xcb_generic_event_t *evt)
+{
+    xcb_mapping_notify_event_t *e = (xcb_mapping_notify_event_t *) evt;
+    if (e->count > 0) {
+        ungrab_buttons();
+        xcb_refresh_keyboard_mapping(symbols, e);
+        get_lock_fields();
+        grab_buttons();
+    }
+}
+
 void enter_notify(xcb_generic_event_t *evt)
 {
     xcb_enter_notify_event_t *e = (xcb_enter_notify_event_t *) evt;
@@ -298,7 +314,7 @@ void button_press(xcb_generic_event_t *evt)
                             frozen_pointer->corner = TOP_LEFT;
                     }
                 }
-                xcb_grab_pointer(dpy, false, screen->root, XCB_EVENT_MASK_POINTER_MOTION | XCB_EVENT_MASK_BUTTON_RELEASE, XCB_GRAB_MODE_ASYNC, XCB_GRAB_MODE_ASYNC, XCB_NONE, XCB_NONE, XCB_CURRENT_TIME);
+                xcb_grab_pointer(dpy, false, root, XCB_EVENT_MASK_POINTER_MOTION | XCB_EVENT_MASK_BUTTON_RELEASE, XCB_GRAB_MODE_ASYNC, XCB_GRAB_MODE_ASYNC, XCB_NONE, XCB_NONE, XCB_CURRENT_TIME);
                 break;
         }
     }
index 0c47ee10c1a3a4379e9a7bd0f92e89f717f0efb4..bafc33b28698b7ac19f1ab45d5ffc7a0a3c2b094 100644 (file)
--- a/events.h
+++ b/events.h
@@ -11,6 +11,7 @@ void unmap_notify(xcb_generic_event_t *);
 void configure_request(xcb_generic_event_t *);
 void client_message(xcb_generic_event_t *);
 void property_notify(xcb_generic_event_t *);
+void mapping_notify(xcb_generic_event_t *);
 void enter_notify(xcb_generic_event_t *);
 void button_press(xcb_generic_event_t *);
 void motion_notify(xcb_generic_event_t *);
diff --git a/ewmh.c b/ewmh.c
index 3edfba257937eb0d52f1a86a2b2dc708d0db3e9c..c06a39a1841dc99aaa1f916b50c3e677ffc4abc9 100644 (file)
--- a/ewmh.c
+++ b/ewmh.c
@@ -18,7 +18,7 @@ void ewmh_init(void)
 void ewmh_update_wm_name(void)
 {
     if (wm_name != NULL)
-        xcb_ewmh_set_wm_name(ewmh, screen->root, strlen(wm_name), wm_name);
+        xcb_ewmh_set_wm_name(ewmh, root, strlen(wm_name), wm_name);
 }
 
 void ewmh_update_active_window(void)
index 8813e2f0cfd23e244b7a7b5a91f9247115ac99a8..422e7e80d12d38f162f18f72b5ffedf5eb3263b4 100644 (file)
--- a/helpers.c
+++ b/helpers.c
@@ -54,7 +54,7 @@ uint32_t get_color(char *col)
 
 void get_pointer_position(xcb_point_t *pos)
 {
-    xcb_query_pointer_reply_t *qpr = xcb_query_pointer_reply(dpy, xcb_query_pointer(dpy, screen->root), NULL);
+    xcb_query_pointer_reply_t *qpr = xcb_query_pointer_reply(dpy, xcb_query_pointer(dpy, root), NULL);
     if (qpr != NULL) {
         *pos = (xcb_point_t) {qpr->root_x, qpr->root_y};
         free(qpr);
index 41b651d0e8541ee3eab0a7df357e3c5fda5060c6..1c4599fa901dd4f128fe2124646f19258489a02e 100644 (file)
@@ -456,22 +456,6 @@ void set_setting(char *name, char *value, char *rsp)
             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;
@@ -535,10 +519,6 @@ void get_setting(char *name, char* rsp)
         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);
 }
index 4fef401d6b555bfbb7496521585ab3313b6bb377..7bfd28bc914d703da7f93e923c754727d48a7b16 100644 (file)
@@ -56,8 +56,6 @@ void load_settings(void)
 
     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;
index 54d336c5482b8d51a3acd6139b8321d1523a07d6..0dfae202dc9f83149d9901579ef0da3e43708bab 100644 (file)
@@ -6,8 +6,6 @@
 #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"
@@ -68,8 +66,6 @@ bool adaptative_raise;
 
 char wm_name[MAXLEN];
 unsigned int button_modifier;
-unsigned int numlock_modifier;
-unsigned int capslock_modifier;
 
 void load_settings(void);
 void run_autostart(void);
index 67677d8353e78c9cabc819ee3a3f8e718a8385b5..e6c96ffe73a72980a6d2bb69612564deb0648c14 100644 (file)
--- a/window.c
+++ b/window.c
@@ -161,7 +161,7 @@ void manage_window(monitor_t *m, desktop_t *d, xcb_window_t win)
 
 void adopt_orphans(void)
 {
-    xcb_query_tree_reply_t *qtr = xcb_query_tree_reply(dpy, xcb_query_tree(dpy, screen->root), NULL);
+    xcb_query_tree_reply_t *qtr = xcb_query_tree_reply(dpy, xcb_query_tree(dpy, root), NULL);
     if (qtr == NULL)
         return;
     int len = xcb_query_tree_children_length(qtr);
@@ -458,12 +458,12 @@ void window_lower(xcb_window_t win)
 void window_set_visibility(xcb_window_t win, bool visible) {
     uint32_t values_off[] = {ROOT_EVENT_MASK & ~XCB_EVENT_MASK_SUBSTRUCTURE_NOTIFY};
     uint32_t values_on[] = {ROOT_EVENT_MASK};
-    xcb_change_window_attributes(dpy, screen->root, XCB_CW_EVENT_MASK, values_off);
+    xcb_change_window_attributes(dpy, root, XCB_CW_EVENT_MASK, values_off);
     if (visible)
         xcb_map_window(dpy, win);
     else
         xcb_unmap_window(dpy, win);
-    xcb_change_window_attributes(dpy, screen->root, XCB_CW_EVENT_MASK, values_on);
+    xcb_change_window_attributes(dpy, root, XCB_CW_EVENT_MASK, values_on);
 }
 
 void window_hide(xcb_window_t win)