keysequence-20250606-0d6af14.diff - sites - public wiki contents of suckless.org
 (HTM) git clone git://git.suckless.org/sites
 (DIR) Log
 (DIR) Files
 (DIR) Refs
       ---
       keysequence-20250606-0d6af14.diff (4102B)
       ---
            1 From 0d6af14efa1250631b081ad9d1f3aa0263221fd8 Mon Sep 17 00:00:00 2001
            2 From: TUVIMEN <hexderm@gmail.com>
            3 Date: Fri, 6 Jun 2025 09:08:40 +0200
            4 Subject: [PATCH] [PATCH] 6.5 keysequence patch
            5 
            6 ---
            7  config.def.h |  1 +
            8  dwm.c        | 86 +++++++++++++++++++++++++++++++++++++++++++++++-----
            9  2 files changed, 80 insertions(+), 7 deletions(-)
           10 
           11 diff --git a/config.def.h b/config.def.h
           12 index 9efa774..6104343 100644
           13 --- a/config.def.h
           14 +++ b/config.def.h
           15 @@ -95,6 +95,7 @@ static const Key keys[] = {
           16          TAGKEYS(                        XK_8,                      7)
           17          TAGKEYS(                        XK_9,                      8)
           18          { MODKEY|ShiftMask,             XK_q,      quit,           {0} },
           19 +        {0}
           20  };
           21  
           22  /* button definitions */
           23 diff --git a/dwm.c b/dwm.c
           24 index f1d86b2..89a4bc5 100644
           25 --- a/dwm.c
           26 +++ b/dwm.c
           27 @@ -28,6 +28,7 @@
           28  #include <stdlib.h>
           29  #include <string.h>
           30  #include <unistd.h>
           31 +#include <time.h>
           32  #include <sys/types.h>
           33  #include <sys/wait.h>
           34  #include <X11/cursorfont.h>
           35 @@ -177,6 +178,7 @@ static void grabbuttons(Client *c, int focused);
           36  static void grabkeys(void);
           37  static void incnmaster(const Arg *arg);
           38  static void keypress(XEvent *e);
           39 +static void keypress_other(const Arg *arg);
           40  static void killclient(const Arg *arg);
           41  static void manage(Window w, XWindowAttributes *wa);
           42  static void mappingnotify(XEvent *e);
           43 @@ -949,6 +951,13 @@ grabbuttons(Client *c, int focused)
           44          }
           45  }
           46  
           47 +static char
           48 +key_not_empty(const Key *key)
           49 +{
           50 +    static const Key empty = {0};
           51 +    return memcmp(key, &empty, sizeof(Key)) != 0;
           52 +}
           53 +
           54  void
           55  grabkeys(void)
           56  {
           57 @@ -965,7 +974,7 @@ grabkeys(void)
           58                  if (!syms)
           59                          return;
           60                  for (k = start; k <= end; k++)
           61 -                        for (i = 0; i < LENGTH(keys); i++)
           62 +                        for (i = 0; key_not_empty(keys+i); i++)
           63                                  /* skip modifier codes, we do that ourselves */
           64                                  if (keys[i].keysym == syms[(k - start) * skip])
           65                                          for (j = 0; j < LENGTH(modifiers); j++)
           66 @@ -996,8 +1005,8 @@ isuniquegeom(XineramaScreenInfo *unique, size_t n, XineramaScreenInfo *info)
           67  }
           68  #endif /* XINERAMA */
           69  
           70 -void
           71 -keypress(XEvent *e)
           72 +static void
           73 +keypress_r(XEvent *e, const Key *keys)
           74  {
           75          unsigned int i;
           76          KeySym keysym;
           77 @@ -1005,11 +1014,74 @@ keypress(XEvent *e)
           78  
           79          ev = &e->xkey;
           80          keysym = XKeycodeToKeysym(dpy, (KeyCode)ev->keycode, 0);
           81 -        for (i = 0; i < LENGTH(keys); i++)
           82 +        for (i = 0; key_not_empty(keys+i); i++)
           83                  if (keysym == keys[i].keysym
           84 -                && CLEANMASK(keys[i].mod) == CLEANMASK(ev->state)
           85 -                && keys[i].func)
           86 -                        keys[i].func(&(keys[i].arg));
           87 +            && CLEANMASK(keys[i].mod) == CLEANMASK(ev->state)
           88 +            && keys[i].func)
           89 +            keys[i].func(&(keys[i].arg));
           90 +}
           91 +
           92 +static char
           93 +grabkeyboard(void) //taken from dmenu
           94 +{
           95 +        struct timespec ts = { .tv_sec = 0, .tv_nsec = 1000000  };
           96 +
           97 +        /* try to grab keyboard, we may have to wait for another process to ungrab */
           98 +        for (int i = 0; i < 1000; i++) {
           99 +                if (XGrabKeyboard(dpy, DefaultRootWindow(dpy), True, GrabModeAsync,
          100 +                    GrabModeAsync, CurrentTime) == GrabSuccess)
          101 +                        return 0;
          102 +                nanosleep(&ts, NULL);
          103 +        }
          104 +    return 1; //failed
          105 +}
          106 +
          107 +static char
          108 +keysym_is_modifier(KeySym s)
          109 +{
          110 +        return (s == XK_Shift_L ||
          111 +        s == XK_Shift_R ||
          112 +        s == XK_Control_L ||
          113 +        s == XK_Control_R ||
          114 +        s == XK_Caps_Lock ||
          115 +        s == XK_Shift_Lock ||
          116 +        s == XK_Meta_L ||
          117 +        s == XK_Meta_R ||
          118 +        s == XK_Alt_L ||
          119 +        s == XK_Alt_R ||
          120 +        s == XK_Super_L ||
          121 +        s == XK_Super_R ||
          122 +        s == XK_Hyper_L ||
          123 +        s == XK_Hyper_R);
          124 +}
          125 +
          126 +void
          127 +keypress_other(const Arg *arg)
          128 +{
          129 +    if (grabkeyboard())
          130 +        return;
          131 +
          132 +    XEvent ev;
          133 +    while (!XNextEvent(dpy, &ev)) {
          134 +        if (ev.type == ButtonPress)
          135 +            break;
          136 +        if (ev.type == KeyPress) {
          137 +            KeySym keysym = XKeycodeToKeysym(dpy, (KeyCode)ev.xkey.keycode, 0);
          138 +            if (keysym_is_modifier(keysym))
          139 +                continue;
          140 +            keypress_r(&ev, (Key*)arg->v);
          141 +            break;
          142 +        }
          143 +    }
          144 +
          145 +    XUngrabKeyboard(dpy, CurrentTime);
          146 +    grabkeys();
          147 +}
          148 +
          149 +void
          150 +keypress(XEvent *e)
          151 +{
          152 +    keypress_r(e,keys);
          153  }
          154  
          155  void
          156 -- 
          157 2.49.0
          158