dmenu

my dmenu build
Log | Files | Refs | README | LICENSE

commit 9a5ff4bcc0c4cbe00ee7c4564ea55f1bda9037ca
parent 4e2a2269140d56c398e0726996743798acbae815
Author: ssnf <ssnf@ssnf.xyz>
Date:   Mon, 28 Nov 2022 16:34:36 +0000

prefix completion patch

Diffstat:
Mdmenu.c | 39+++++++++++++++++++--------------------
Apatches/dmenu-prefixcompletion-4.9.diff | 93+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
2 files changed, 112 insertions(+), 20 deletions(-)

diff --git a/dmenu.c b/dmenu.c @@ -254,7 +254,7 @@ match(void) char buf[sizeof text], *s; int i, tokc = 0; size_t len, textsize; - struct item *item, *lprefix, *lsubstr, *prefixend, *substrend; + struct item *item, *lprefix, *prefixend; strcpy(buf, text); /* separate input text into tokens to be matched individually */ @@ -263,8 +263,8 @@ match(void) die("cannot realloc %zu bytes:", tokn * sizeof *tokv); len = tokc ? strlen(tokv[0]) : 0; - matches = lprefix = lsubstr = matchend = prefixend = substrend = NULL; - textsize = strlen(text) + 1; + matches = lprefix = matchend = prefixend = NULL; + textsize = strlen(text); for (item = items; item && item->text; item++) { for (i = 0; i < tokc; i++) if (!fstrstr(item->text, tokv[i])) @@ -276,8 +276,6 @@ match(void) appenditem(item, &matches, &matchend); else if (!fstrncmp(tokv[0], item->text, len)) appenditem(item, &lprefix, &prefixend); - else - appenditem(item, &lsubstr, &substrend); } if (lprefix) { if (matches) { @@ -287,14 +285,6 @@ match(void) matches = lprefix; matchend = prefixend; } - if (lsubstr) { - if (matches) { - matchend->right = lsubstr; - lsubstr->left = matchend; - } else - matches = lsubstr; - matchend = substrend; - } curr = sel = matches; calcoffsets(); } @@ -344,9 +334,11 @@ keypress(XKeyEvent *ev) { char buf[64]; int len; - KeySym ksym = NoSymbol; + struct item* item; + KeySym ksym; Status status; + ksym = NoSymbol; len = XmbLookupString(xic, ev, buf, sizeof buf, &ksym, &status); switch (status) { default: /* XLookupNone, XBufferOverflow */ @@ -533,12 +525,19 @@ insert: } break; case XK_Tab: - if (!sel) - return; - cursor = strnlen(sel->text, sizeof text - 1); - memcpy(text, sel->text, cursor); - text[cursor] = '\0'; - match(); + if (!matches) + break; + strncpy(text, matches->text, sizeof text - 1); + text[sizeof(text) - 1] = '\0'; + len = cursor = strlen(text); /* length of longest common prefix */ + for (item = matches; item && item->text; item = item->right) { + for (cursor = 0 + ;cursor < len && text[cursor] == item->text[cursor] + ;++cursor + ); + len = cursor; + } + memset(text + len, '\0', strlen(text) - len); break; } diff --git a/patches/dmenu-prefixcompletion-4.9.diff b/patches/dmenu-prefixcompletion-4.9.diff @@ -0,0 +1,93 @@ +From 2874b35e41a85731df8c7583f76c71eb249d3dfd Mon Sep 17 00:00:00 2001 +From: Felix Van der Jeugt <felix.vanderjeugt@gmail.com> +Date: Wed, 19 Oct 2016 22:18:21 +0200 +Subject: [PATCH] tabcomplete with longest common prefix + +when hitting tab, the current input will be set to the longest common prefix +of the current selection instead of the first item of the selection +--- + dmenu.c | 32 ++++++++++++++------------------ + 1 file changed, 14 insertions(+), 18 deletions(-) + +diff --git a/dmenu.c b/dmenu.c +index f803149..4bb1c23 100644 +--- a/dmenu.c ++++ b/dmenu.c +@@ -219,7 +219,7 @@ match(void) + char buf[sizeof text], *s; + int i, tokc = 0; + size_t len, textsize; +- struct item *item, *lprefix, *lsubstr, *prefixend, *substrend; ++ struct item *item, *lprefix, *prefixend; + + strcpy(buf, text); + /* separate input text into tokens to be matched individually */ +@@ -228,8 +228,8 @@ match(void) + die("cannot realloc %u bytes:", tokn * sizeof *tokv); + len = tokc ? strlen(tokv[0]) : 0; + +- matches = lprefix = lsubstr = matchend = prefixend = substrend = NULL; +- textsize = strlen(text) + 1; ++ matches = lprefix = matchend = prefixend = NULL; ++ textsize = strlen(text); + for (item = items; item && item->text; item++) { + for (i = 0; i < tokc; i++) + if (!fstrstr(item->text, tokv[i])) +@@ -241,8 +241,6 @@ match(void) + appenditem(item, &matches, &matchend); + else if (!fstrncmp(tokv[0], item->text, len)) + appenditem(item, &lprefix, &prefixend); +- else +- appenditem(item, &lsubstr, &substrend); + } + if (lprefix) { + if (matches) { +@@ -252,14 +250,6 @@ match(void) + matches = lprefix; + matchend = prefixend; + } +- if (lsubstr) { +- if (matches) { +- matchend->right = lsubstr; +- lsubstr->left = matchend; +- } else +- matches = lsubstr; +- matchend = substrend; +- } + curr = sel = matches; + calcoffsets(); + } +@@ -309,6 +299,7 @@ keypress(XKeyEvent *ev) + { + char buf[32]; + int len; ++ struct item * item; + KeySym ksym; + Status status; + +@@ -487,12 +478,17 @@ insert: + } + break; + case XK_Tab: +- if (!sel) +- return; +- strncpy(text, sel->text, sizeof text - 1); ++ if (!matches) break; /* cannot complete no matches */ ++ strncpy(text, matches->text, sizeof text - 1); + text[sizeof text - 1] = '\0'; +- cursor = strlen(text); +- match(); ++ len = cursor = strlen(text); /* length of longest common prefix */ ++ for (item = matches; item && item->text; item = item->right) { ++ cursor = 0; ++ while (cursor < len && text[cursor] == item->text[cursor]) ++ cursor++; ++ len = cursor; ++ } ++ memset(text + len, '\0', strlen(text) - len); + break; + } + +-- +2.20.1 +