Zsh Mailing List Archive
Messages sorted by: Reverse Date, Date, Thread, Author

Re: Menu selection



Oliver Kiddle wrote:

> ...
> 
> If I do ls -<tab><tab><ctrl-s>exc, the prompt changes to `failing
> isearch'. It is matching the word `except' and the `c' didn't enable it
> to move on to another entry so it says it is failing but this doesn't
> seem correct because it is still matching the word `except'. It should
> only say failing when there really is nothing found.
> 
> Keeping with ls, if I do a search for `co' and then repeatedly press
> Ctrl-S to cycle between the matching completions, I have to press Ctrl-S
> twice to move off the --color option. Perhaps because `co' matches in
> both the match and description.

These two (and the manual) should be fixed in the new version below.

> The binding of backspace to undo is not ideal when cycling between
> matches because it goes back through the matches before removing
> characters off the end of the search string.

Personally, I prefer it this way, but we can make it optional, of
course, using another widget, as you suggested. I'll have a look.

And next time, I'm going to commit it.


Bye
  Sven

diff -ur -r ../oz/Completion/Base/Core/_main_complete ./Completion/Base/Core/_main_complete
--- ../oz/Completion/Base/Core/_main_complete	Sun Jun  9 16:03:38 2002
+++ ./Completion/Base/Core/_main_complete	Mon Jun 17 23:37:03 2002
@@ -267,6 +267,19 @@
         unset MENUSELECT
       fi
     fi
+    if [[ -n "$MENUSELECT" ]]; then
+      if [[ -n "$_menu_style[(r)interactive*]" ]]; then
+        MENUMODE=interactive
+      elif [[ -n "$_menu_style[(r)search*]" ]]; then
+        if [[ -n "$_menu_style[(r)*backward*]" ]]; then
+          MENUMODE=search-backward
+        else
+          MENUMODE=search-forward
+        fi
+      else
+        unset MENUMODE
+      fi
+    fi
   fi
 elif [[ nm -lt 1 && -n "$_comp_mesg" ]]; then
   compstate[insert]=''
diff -ur -r ../oz/Doc/Zsh/compsys.yo ./Doc/Zsh/compsys.yo
--- ../oz/Doc/Zsh/compsys.yo	Sun Jun  9 16:03:36 2002
+++ ./Doc/Zsh/compsys.yo	Mon Jun 17 23:54:42 2002
@@ -1824,6 +1824,13 @@
 matches is generated em(or) the list of matches does not fit onto the
 screen, both of `tt(yes=)' and `tt(select=)' can be given twice, once
 with a number and once with `tt(long)' or `tt(long-list)'.
+
+Finally, the two special modes of menu selection, namely interactive
+mode and incremental search can be pre-selected with this style. By
+including the word `tt(interactive)' in the value, interactive mode
+will be entered immediately when menu selection is started and the
+string `tt(search)' does the same for incremental search. To select
+backward incremental search, include the string `tt(search-backward)'.
 )
 kindex(muttrc, completion style)
 item(tt(muttrc))(
diff -ur -r ../oz/Doc/Zsh/mod_complist.yo ./Doc/Zsh/mod_complist.yo
--- ../oz/Doc/Zsh/mod_complist.yo	Sun Jun  9 16:03:36 2002
+++ ./Doc/Zsh/mod_complist.yo	Thu Jun 20 22:40:20 2002
@@ -332,6 +332,22 @@
 item(tt(reverse-menu-complete))(
 moves the mark to the previous match
 )
+item(tt(viinsert))(
+this toggles between normal and interactive mode; in interactive mode
+the keys bound to tt(self-insert) and tt(self-insert-unmeta) insert in
+the same way as in normal editing mode but without leaving menu
+selection; instead, the set of matches will be reduced to contain only
+those matches the changed command line by calling completion again;
+the completion widgets make the longest unambiguous string be inserted
+in the command line and tt(undo) and tt(backward-delete-char) go back
+to the previous set of matches
+)
+item(tt(history-incremental-search-forward),
+tt(history-incremental-search-backward))(
+this starts incremental searches in the list of completions displayed;
+in this mode, tt(accept-line) only leaves incremental search, going
+back to the normal menu selection mode
+)
 enditem()
 
 All movement functions wrap around at the edges; any other zle function not
diff -ur -r ../oz/Src/Zle/compcore.c ./Src/Zle/compcore.c
--- ../oz/Src/Zle/compcore.c	Sun Jun  9 16:03:37 2002
+++ ./Src/Zle/compcore.c	Sun Jun  9 16:03:48 2002
@@ -360,7 +360,7 @@
 	haspattern = 1;
     if (iforcemenu) {
 	if (nmatches)
-	    do_ambig_menu();
+            do_ambig_menu();
 	ret = !nmatches;
     } else if (useline < 0)
 	ret = selfinsert(zlenoargs);
diff -ur -r ../oz/Src/Zle/complist.c ./Src/Zle/complist.c
--- ../oz/Src/Zle/complist.c	Sun Jun  9 16:03:37 2002
+++ ./Src/Zle/complist.c	Thu Jun 20 22:35:32 2002
@@ -400,8 +400,12 @@
 
 /* Used in mtab/mgtab, for explanations. */
 
-#define mtexpl ((Cmatch *) 1)
-#define mgexpl ((Cmgroup) 1)
+#define MMARK       ((unsigned long) 1)
+#define mmarked(v)  (((unsigned long) (v)) & MMARK)
+#define mtmark(v)   ((Cmatch *) (((unsigned long) (v)) | MMARK))
+#define mtunmark(v) ((Cmatch *) (((unsigned long) (v)) & ~MMARK))
+#define mgmark(v)   ((Cmgroup)  (((unsigned long) (v)) | MMARK))
+#define mgunmark(v) ((Cmgroup)  (((unsigned long) (v)) & ~MMARK))
 
 /* Information for in-string colours. */
 
@@ -1065,8 +1069,8 @@
 			int mm = (mcols * ml), i;
 
 			for (i = mcols; i--; ) {
-			    mtab[mm + i] = mtexpl;
-			    mgtab[mm + i] = mgexpl;
+			    mtab[mm + i] = mtmark(NULL);
+			    mgtab[mm + i] = mgmark(NULL);
 			}
 		    }
 		    if (stop)
@@ -1381,13 +1385,20 @@
 
     mlastm = m->gnum;
     if (m->disp && (m->flags & CMF_DISPLINE)) {
-	if (mselect >= 0 && !(m->flags & CMF_DUMMY)) {
+	if (mselect >= 0) {
 	    int mm = (mcols * ml), i;
 
-	    for (i = mcols; i--; ) {
-		mtab[mm + i] = mp;
-		mgtab[mm + i] = g;
-	    }
+            if (m->flags & CMF_DUMMY) {
+                for (i = mcols; i--; ) {
+                    mtab[mm + i] = mtmark(mp);
+                    mgtab[mm + i] = mgmark(g);
+                }
+            } else {
+                for (i = mcols; i--; ) {
+                    mtab[mm + i] = mp;
+                    mgtab[mm + i] = g;
+                }
+            }
 	}
 	if (!dolist(ml)) {
 	    mlprinted = printfmt(m->disp, 0, 0, 0) / columns;
@@ -1428,13 +1439,20 @@
 	} else
 	    mx = mc * g->width;
 
-	if (mselect >= 0 && !(m->flags & CMF_DUMMY)) {
+	if (mselect >= 0) {
 	    int mm = mcols * ml, i;
 
-	    for (i = (width ? width : mcols); i--; ) {
-		mtab[mx + mm + i] = mp;
-		mgtab[mx + mm + i] = g;
-	    }
+            if (m->flags & CMF_DUMMY) {
+                for (i = (width ? width : mcols); i--; ) {
+                    mtab[mx + mm + i] = mtmark(mp);
+                    mgtab[mx + mm + i] = mgmark(g);
+                }
+            } else {
+                for (i = (width ? width : mcols); i--; ) {
+                    mtab[mx + mm + i] = mp;
+                    mgtab[mx + mm + i] = g;
+                }
+            }
 	}
 	if (!dolist(ml)) {
 	    mlprinted = niceztrlen(m->disp ? m->disp : m->str) / columns;
@@ -1675,8 +1693,8 @@
 
     tab -= mcol;
 
-    for (p = wish; p >= 0 && (!tab[p] || tab[p] == mtexpl); p--);
-    for (n = wish; n < mcols && (!tab[n] || tab[n] == mtexpl); n++);
+    for (p = wish; p >= 0 && (!tab[p] || mmarked(tab[p])); p--);
+    for (n = wish; n < mcols && (!tab[n] || mmarked(tab[n])); n++);
     if (n == mcols)
 	n = -1;
 
@@ -1711,21 +1729,222 @@
     Cmgroup amatches, pmatches, lastmatches, lastlmatches;
     char *origline;
     int origcs, origll;
+    char *status;
+    int mode;
+};
+
+typedef struct menusearch *Menusearch;
+
+struct menusearch {
+    Menusearch prev;
+    char *str;
+    int line;
+    int col;
+    int back;
+    int state;
+    Cmatch **ptr;
 };
 
+#define MS_OK       0
+#define MS_FAILED   1
+#define MS_WRAPPED  2
+
+#define MAX_STATUS 128
+
+static char *
+setmstatus(char *status, int *csp, int *llp, int *lenp)
+{
+    char *p, *s, *ret = NULL;
+    int pl, sl, max;
+
+    if (csp) {
+        *csp = cs;
+        *llp = ll;
+        *lenp = lastend - wb;
+
+        ret = dupstring((char *) line);
+
+        p = (char *) zhalloc(cs - wb + 1);
+        strncpy(p, (char *) line + wb, cs - wb);
+        p[cs - wb] = '\0';
+        s = (char *) zhalloc(lastend - cs + 1);
+        strncpy(s, (char *) line + cs, lastend - cs);
+        s[lastend - cs] = '\0';
+
+        cs = wb;
+        foredel(lastend - wb);
+        pl = strlen(compprefix);
+        sl = strlen(compsuffix);
+        spaceinline(pl + sl);
+        strncpy(line + wb, compprefix, pl);
+        strncpy(line + wb + pl, compsuffix, sl);
+        cs = wb + pl;
+    } else {
+        p = compprefix;
+        s = compsuffix;
+    }
+    pl = strlen(p);
+    sl = strlen(s);
+    max = (columns < MAX_STATUS ? columns : MAX_STATUS) - 14;
+
+    if (max > 12) {
+        int h = (max - 2) >> 1;
+
+        strcpy(status, "interactive: ");
+        if (pl > h - 3) {
+            strcat(status, "...");
+            strcat(status, p + pl - h - 3);
+        } else
+            strcat(status, p);
+
+        strcat(status, "[]");
+        if (sl > h - 3) {
+            strncat(status, s, h - 3);
+            strcat(status, "...");
+        } else
+            strcat(status, s);
+    }
+    return ret;
+}
+
+static Menusearch msearchstack;
+static char *msearchstr = NULL;
+static int msearchstate;
+
+static void
+msearchpush(Cmatch **p, int back)
+{
+    Menusearch s = (Menusearch) zhalloc(sizeof(struct menusearch));
+
+    s->prev = msearchstack;
+    msearchstack = s;
+    s->str = dupstring(msearchstr);
+    s->line = mline;
+    s->col = mcol;
+    s->back = back;
+    s->state = msearchstate;
+    s->ptr = p;
+}
+
+static Cmatch **
+msearchpop(int *backp)
+{
+    Menusearch s = msearchstack;
+
+    if (s->prev)
+        msearchstack = s->prev;
+
+    msearchstr = s->str;
+    mline = s->line;
+    mcol = s->col;
+    msearchstate = s->state;
+
+    *backp = s->back;
+
+    return s->ptr;
+}
+
+static Cmatch **
+msearch(Cmatch **ptr, int ins, int back, int rep, int *wrapp)
+{
+    char s[2];
+    Cmatch **p, *l = NULL, m;
+    int x = mcol, y = mline;
+    int ex, ey, wrap = 0, owrap = (msearchstate & MS_WRAPPED);
+
+    msearchpush(ptr, back);
+
+    if (ins) {
+        s[0] = c;
+        s[1] = '\0';
+
+        msearchstr = dyncat(msearchstr, s);
+    }
+    if (back) {
+        ex = mcols - 1;
+        ey = -1;
+    } else {
+        ex = 0;
+        ey = listdat.nlines;
+    }
+    p = mtab + (mline * mcols) + mcol;
+    if (rep)
+        l = *p;
+    while (1) {
+        if (!rep && mtunmark(*p) && *p != l) {
+            l = *p;
+            m = *mtunmark(*p);
+
+            if (strstr((m->disp ? m->disp : m->str), msearchstr)) {
+                mcol = x;
+                mline = y;
+
+                return p;
+            }
+        }
+        rep = 0;
+
+        if (back) {
+            p--;
+            if (--x < 0) {
+                x = mcols - 1;
+                y--;
+            }
+        } else {
+            p++;
+            if (++x == mcols) {
+                x = 0;
+                y++;
+            }
+        }
+        if (x == ex && y == ey) {
+            if (wrap) {
+                msearchstate = MS_FAILED | owrap;
+                break;
+            }
+            msearchstate |= MS_WRAPPED;
+
+            if (back) {
+                x = mcols - 1;
+                y = listdat.nlines - 1;
+                p = mtab + (y * mcols) + x;
+            } else {
+                x = y = 0;
+                p = mtab;
+            }
+            ex = mcol;
+            ey = mline;
+            wrap = 1;
+            *wrapp = 1;
+        }
+    }
+    return NULL;
+}
+
+#define MM_INTER   1
+#define MM_FSEARCH 2
+#define MM_BSEARCH 3
+
 static int
 domenuselect(Hookdef dummy, Chdata dat)
 {
     static Chdata fdat = NULL;
+    static char *lastsearch = NULL;
     Cmatch **p;
     Cmgroup *pg;
     Thingy cmd;
     Menustack u = NULL;
     int i = 0, acc = 0, wishcol = 0, setwish = 0, oe = onlyexpl, wasnext = 0;
     int space, lbeg = 0, step = 1, wrap, pl = nlnct, broken = 0, first = 1;
-    int nolist = 0;
+    int nolist = 0, mode = 0, modecs, modell, modelen;
     char *s;
+    char status[MAX_STATUS], *modeline;
 
+    msearchstack = NULL;
+    msearchstr = "";
+    msearchstate = MS_OK;
+
+    status[0] = '\0';
     queue_signals();
     if (fdat || (dummy && (!(s = getsparam("MENUSELECT")) ||
 			   (dat && dat->num < atoi(s))))) {
@@ -1744,6 +1963,21 @@
 	    if ((step += lines - nlnct) < 0)
 		step = 1;
     }
+    if ((s = getsparam("MENUMODE"))) {
+        if (!strcmp(s, "interactive")) {
+            int l = strlen(origline);
+
+            mode = MM_INTER;
+            cs = 0;
+            foredel(ll);
+            spaceinline(l);
+            strncpy((char *) line, origline, l);
+            cs = origcs;
+            setmstatus(status, NULL, NULL, NULL);
+        } else if (strpfx("search", s)) {
+            mode = (strstr(s, "back") ? MM_BSEARCH : MM_FSEARCH);
+        }
+    }
     if ((mstatus = dupstring(getsparam("MENUPROMPT"))) && !*mstatus)
 	mstatus = "%SScrolling active: current selection at %p%s";
     unqueue_signals();
@@ -1770,7 +2004,7 @@
 
 	    for (y = 0; y < mlines; y++) {
 		for (x = mcols; x; x--, p++)
-		    if (*p && *p != mtexpl && **p && mselect == (**p)->gnum)
+		    if (*p && !mmarked(*p) && **p && mselect == (**p)->gnum)
 			break;
 		if (x) {
                     mcol = mcols - x;
@@ -1790,7 +2024,7 @@
 
 	    while (mlbeg) {
 		for (q = p, c = columns; c; q++, c--)
-		    if (*q && *q != mtexpl)
+		    if (*q && !mmarked(*q))
 			break;
 		if (c)
 		    break;
@@ -1821,8 +2055,33 @@
         showinglist = -2;
         if (first && !listshown && isset(LISTBEEP))
             zbeep();
+        if (first) {
+            modeline = dyncat(compprefix, compsuffix);
+            modecs = cs;
+            modell = ll;
+            modelen = minfo.len;
+        }
         first = 0;
+        if (mode == MM_INTER) {
+            statusline = status;
+            statusll = strlen(status);
+        } else if (mode) {
+            int l = sprintf(status, "%s%sisearch%s: ",
+                            ((msearchstate & MS_FAILED) ? "failed " : ""),
+                            ((msearchstate & MS_WRAPPED) ? "wrapped " : ""),
+                            (mode == MM_FSEARCH ? "" : " backward"));
+
+            strncat(status, msearchstr, MAX_STATUS - l - 1);
+
+            statusline = status;
+            statusll = strlen(status);
+        } else {
+            statusline = NULL;
+            statusll = 0;
+        }
         zrefresh();
+        statusline = NULL;
+        statusll = 0;
         inselect = 1;
         if (noselect) {
             broken = 1;
@@ -1859,13 +2118,36 @@
 	    zbeep();
             molbeg = -1;
 	    break;
-	} else if (nolist && cmd != Th(z_undo)) {
+	} else if (nolist && cmd != Th(z_undo) &&
+                   (!mode || cmd != Th(z_backwarddeletechar))) {
 	    ungetkeycmd();
 	    break;
 	} else if (cmd == Th(z_acceptline)) {
+            if (mode == MM_FSEARCH || mode == MM_BSEARCH) {
+                mode = 0;
+                continue;
+            }
 	    acc = 1;
 	    break;
-	} else if (cmd == Th(z_acceptandinfernexthistory)) {
+        } else if (cmd == Th(z_viinsert)) {
+            if (mode == MM_INTER)
+                mode = 0;
+            else {
+                int l = strlen(origline);
+
+                mode = MM_INTER;
+                cs = 0;
+                foredel(ll);
+                spaceinline(l);
+                strncpy((char *) line, origline, l);
+                cs = origcs;
+                setmstatus(status, NULL, NULL, NULL);
+
+                continue;
+            }
+	} else if (cmd == Th(z_acceptandinfernexthistory) ||
+                   (mode == MM_INTER && (cmd == Th(z_selfinsert) ||
+                                         cmd == Th(z_selfinsertunmeta)))) {
 	    Menustack s = (Menustack) zhalloc(sizeof(*s));
 
 	    s->prev = u;
@@ -1888,6 +2170,8 @@
 	    s->origline = origline;
 	    s->origcs = origcs;
 	    s->origll = origll;
+            s->status = dupstring(status);
+            s->mode = mode;
 	    menucmp = menuacc = hasoldlist = 0;
 	    minfo.cur = NULL;
 	    fixsuffix();
@@ -1897,6 +2181,23 @@
 	    invalidate_list();
 	    iforcemenu = 1;
 	    comprecursive = 1;
+            if (cmd != Th(z_acceptandinfernexthistory)) {
+                int l = strlen(origline);
+
+                cs = 0;
+                foredel(ll);
+                spaceinline(l);
+                strncpy((char *) line, origline, l);
+                cs = origcs;
+
+                if (cmd == Th(z_selfinsert))
+                    selfinsert(zlenoargs);
+                else
+                    selfinsertunmeta(zlenoargs);
+
+                iforcemenu = -1;
+            } else
+                mode = 0;
 	    menucomplete(zlenoargs);
 	    iforcemenu = 0;
 
@@ -1920,6 +2221,9 @@
 		}
 		goto getk;
 	    }
+            if (cmd != Th(z_acceptandinfernexthistory))
+                modeline = setmstatus(status, &modecs, &modell, &modelen);
+
 	    clearlist = listshown = 1;
 	    mselect = (*(minfo.cur))->gnum;
 	    setwish = wasnext = 1;
@@ -1931,6 +2235,7 @@
 	    Menustack s = (Menustack) zhalloc(sizeof(*s));
 	    int ol;
 
+            mode = 0;
 	    s->prev = u;
 	    u = s;
 	    s->line = dupstring((char *) line);
@@ -1949,6 +2254,8 @@
 	    s->origline = origline;
 	    s->origcs = origcs;
 	    s->origll = origll;
+            s->status = dupstring(status);
+            s->mode = mode;
 	    accept_last();
 	    handleundo();
 	    comprecursive = 1;
@@ -1977,7 +2284,8 @@
 	    }
 	    setwish = 1;
 	    continue;
-	} else if (cmd == Th(z_undo)) {
+	} else if (cmd == Th(z_undo) ||
+                   (mode == MM_INTER && cmd == Th(z_backwarddeletechar))) {
 	    int l;
 
 	    if (!u)
@@ -2013,12 +2321,17 @@
 	    origline = u->origline;
 	    origcs = u->origcs;
 	    origll = u->origll;
+            strcpy(status, u->status);
+            mode = u->mode;
 
 	    u = u->prev;
 	    clearlist = 1;
 	    setwish = 1;
 	    listdat.valid = 0;
             molbeg = -42;
+
+            if (mode)
+                continue;
 	} else if (cmd == Th(z_redisplay)) {
 	    redisplay(zlenoargs);
             molbeg = -42;
@@ -2034,6 +2347,7 @@
 	    int omline;
 	    Cmatch **op;
 
+            mode = 0;
 	    wrap = 0;
 
 	down:
@@ -2057,7 +2371,7 @@
 		}
 		if (adjust_mcol(wishcol, &p, NULL))
 		    continue;
-	    } while (!*p || *p == mtexpl);
+	    } while (!*p || mmarked(*p));
 
 	    if (wrap == 1)
 		goto right;
@@ -2068,6 +2382,7 @@
 	    int omline;
 	    Cmatch **op;
 
+            mode = 0;
 	    wrap = 0;
 
 	up:
@@ -2091,7 +2406,7 @@
 		}
 		if (adjust_mcol(wishcol, &p, NULL))
 		    continue;
-	    } while (!*p || *p == mtexpl);
+	    } while (!*p || mmarked(*p));
 
 	    if (wrap == 1) {
 		if (mcol == wishcol)
@@ -2106,6 +2421,7 @@
 	    int i = lines - pl - 1, oi = i, ll = 0;
 	    Cmatch **lp = NULL;
 
+            mode = 0;
 	    if (mline == mlines - 1)
 		goto top;
 	    while (i > 0) {
@@ -2119,7 +2435,7 @@
 		}
 		if (adjust_mcol(wishcol, &p, NULL))
 		    continue;
-		if (*p && *p != mtexpl) {
+		if (*p && !mmarked(*p)) {
 		    i--;
 		    lp = p;
 		    ll = mline;
@@ -2133,6 +2449,7 @@
 	    int i = lines - pl - 1, oi = i, ll = 0;
 	    Cmatch **lp = NULL;
 
+            mode = 0;
 	    if (!mline)
 		goto bottom;
 	    while (i > 0) {
@@ -2146,7 +2463,7 @@
 		}
 		if (adjust_mcol(wishcol, &p, NULL))
 		    continue;
-		if (*p || *p != mtexpl) {
+		if (*p || !mmarked(*p)) {
 		    i--;
 		    lp = p;
 		    ll = mline;
@@ -2158,6 +2475,8 @@
 	    int ll;
 	    Cmatch **lp;
 
+            mode = 0;
+
 	top:
 
 	    ll = mline;
@@ -2167,7 +2486,7 @@
 		p -= mcols;
 		if (adjust_mcol(wishcol, &p, NULL))
 		    continue;
-		if (*p && *p != mtexpl) {
+		if (*p && !mmarked(*p)) {
 		    lp = p;
 		    ll = mline;
 		}
@@ -2178,6 +2497,8 @@
 	    int ll;
 	    Cmatch **lp;
 
+            mode = 0;
+
 	bottom:
 
 	    ll = mline;
@@ -2187,7 +2508,7 @@
 		p += mcols;
 		if (adjust_mcol(wishcol, &p, NULL))
 		    continue;
-		if (*p && *p != mtexpl) {
+		if (*p && !mmarked(*p)) {
 		    lp = p;
 		    ll = mline;
 		}
@@ -2198,6 +2519,7 @@
 	    int omcol;
 	    Cmatch **op;
 
+            mode = 0;
 	    wrap = 0;
 
 	right:
@@ -2219,7 +2541,7 @@
 		    mcol++;
 		    p++;
 		}
-	    } while (!*p || *p == mtexpl || (mcol != omcol && *p == *op));
+	    } while (!*p || mmarked(*p) || (mcol != omcol && *p == *op));
 	    wishcol = mcol;
 
 	    if (wrap == 2)
@@ -2228,6 +2550,7 @@
 	    int omcol;
 	    Cmatch **op;
 
+            mode = 0;
 	    wrap = 0;
 
 	left:
@@ -2249,7 +2572,7 @@
 		    mcol--;
 		    p--;
 		}
-	    } while (!*p || *p == mtexpl || (mcol != omcol && *p == *op));
+	    } while (!*p || mmarked(*p) || (mcol != omcol && *p == *op));
 	    wishcol = mcol;
 
 	    if (wrap == 2) {
@@ -2262,9 +2585,10 @@
 		   cmd == Th(z_beginningofline) ||
 		   cmd == Th(z_beginningoflinehist) ||
 		   cmd == Th(z_vibeginningofline)) {
+            mode = 0;
 	    p -= mcol;
 	    mcol = 0;
-	    while (!*p || *p == mtexpl) {
+	    while (!*p || mmarked(*p)) {
 		mcol++;
 		p++;
 	    }
@@ -2273,9 +2597,10 @@
 		   cmd == Th(z_endofline) ||
 		   cmd == Th(z_endoflinehist) ||
 		   cmd == Th(z_viendofline)) {
+            mode = 0;
 	    p += mcols - mcol - 1;
 	    mcol = mcols - 1;
-	    while (!*p || *p == mtexpl) {
+	    while (!*p || mmarked(*p)) {
 		mcol--;
 		p--;
 	    }
@@ -2285,6 +2610,7 @@
 	    Cmgroup g = *pg;
 	    int ol = mline;
 
+            mode = 0;
 	    do {
 		if (mline == mlines - 1) {
 		    p -= mline * mcols;
@@ -2297,11 +2623,12 @@
 		}
 		if (adjust_mcol(wishcol, &p, &pg))
 		    continue;
-	    } while (ol != mline && (*pg == g || !*pg || *pg == mgexpl));
+	    } while (ol != mline && (*pg == g || !*pg || mmarked(*pg)));
 	} else if (cmd == Th(z_vibackwardblankword)) {
 	    Cmgroup g = *pg;
 	    int ol = mline;
 
+            mode = 0;
 	    do {
 		if (!mline) {
 		    mline = mlines - 1;
@@ -2314,7 +2641,7 @@
 		}
 		if (adjust_mcol(wishcol, &p, &pg))
 		    continue;
-	    } while (ol != mline && (*pg == g || !*pg || *pg == mgexpl));
+	    } while (ol != mline && (*pg == g || !*pg || mmarked(*pg)));
 	} else if (cmd == Th(z_completeword) ||
 		   cmd == Th(z_expandorcomplete) ||
 		   cmd == Th(z_expandorcompleteprefix) ||
@@ -2326,21 +2653,99 @@
 		   !strcmp(cmd->nam, "expand-or-complete-prefix") ||
 		   !strcmp(cmd->nam, "menu-complete") ||
 		   !strcmp(cmd->nam, "menu-expand-or-complete")) {
-	    comprecursive = 1;
-	    do_menucmp(0);
-	    mselect = (*(minfo.cur))->gnum;
-	    setwish = 1;
-	    mline = -1;
+            if (mode == MM_INTER) {
+                origline = modeline;
+                origcs = modecs;
+                origll = modell;
+                cs = 0;
+                foredel(ll);
+                spaceinline(origll);
+                strncpy((char *) line, origline, origll);
+                cs = origcs;
+                minfo.len = modelen;
+            } else {
+                mode = 0;
+                comprecursive = 1;
+                do_menucmp(0);
+                mselect = (*(minfo.cur))->gnum;
+                setwish = 1;
+                mline = -1;
+            }
 	    continue;
 	} else if (cmd == Th(z_reversemenucomplete) ||
 		   !strcmp(cmd->nam, "reverse-menu-complete")) {
+            mode = 0;
 	    comprecursive = 1;
 	    reversemenucomplete(zlenoargs);
 	    mselect = (*(minfo.cur))->gnum;
 	    setwish = 1;
 	    mline = -1;
 	    continue;
+        } else if (cmd == Th(z_historyincrementalsearchforward) ||
+                   cmd == Th(z_historyincrementalsearchbackward) ||
+                   ((mode == MM_FSEARCH || mode == MM_BSEARCH) &&
+                    (cmd == Th(z_selfinsert) ||
+                     cmd == Th(z_selfinsertunmeta)))) {
+            Cmatch **np, **op = p;
+            int was = (mode == MM_FSEARCH || mode == MM_BSEARCH);
+            int ins = (cmd == Th(z_selfinsert) || cmd == Th(z_selfinsertunmeta));
+            int back = (cmd == Th(z_historyincrementalsearchbackward));
+            int wrap;
+
+            do {
+                if (was) {
+                    p += wishcol - mcol;
+                    mcol = wishcol;
+                }
+                if (!ins) {
+                    if (was) {
+                        if (!*msearchstr && lastsearch) {
+                            msearchstr = dupstring(lastsearch);
+                            mode = 0;
+                        }
+                    } else {
+                        msearchstr = "";
+                        msearchstack = NULL;
+                    }
+                }
+                if (cmd == Th(z_selfinsertunmeta)) {
+                    c &= 0x7f;
+                    if (c == '\r')
+                        c = '\n';
+                }
+                wrap = 0;
+                np = msearch(p, ins, (ins ? (mode == MM_BSEARCH) : back),
+                             (was && !ins), &wrap);
+
+                if (!ins)
+                    mode = (back ? MM_BSEARCH : MM_FSEARCH);
+
+                if (*msearchstr) {
+                    zsfree(lastsearch);
+                    lastsearch = ztrdup(msearchstr);
+                }
+                if (np) {
+                    wishcol = mcol;
+                    p = np;
+                }
+                adjust_mcol(wishcol, &p, NULL);
+
+            } while ((back || cmd == Th(z_historyincrementalsearchforward)) &&
+                     np && !wrap && was && **p == **op);
+
+        } else if ((mode == MM_FSEARCH || mode == MM_BSEARCH) &&
+                   cmd == Th(z_backwarddeletechar)) {
+            int back;
+            Cmatch **np = msearchpop(&back);
+
+            mode = (back ? MM_BSEARCH : MM_FSEARCH);
+            wishcol = mcol;
+            if (np) {
+                p = np;
+                adjust_mcol(wishcol, &p, NULL);
+            }
 	} else if (cmd == Th(z_undefinedkey)) {
+            mode = 0;
 	    continue;
 	} else {
 	    ungetkeycmd();
diff -ur -r ../oz/Src/Zle/compresult.c ./Src/Zle/compresult.c
--- ../oz/Src/Zle/compresult.c	Sun Jun  9 16:03:37 2002
+++ ./Src/Zle/compresult.c	Sun Jun  9 16:03:49 2002
@@ -744,8 +744,9 @@
      * unambiguous prefix.                                               */
     lastambig = 1;
 
-    if (usemenu || (haspattern && comppatinsert &&
-		    !strcmp(comppatinsert, "menu"))) {
+    if (iforcemenu != -1 &&
+        (usemenu || (haspattern && comppatinsert &&
+                     !strcmp(comppatinsert, "menu")))) {
 	/* We are in a position to start using menu completion due to one  *
 	 * of the menu completion options, or due to the menu-complete-    *
 	 * word command, or due to using GLOB_COMPLETE which does menu-    *
@@ -961,9 +962,10 @@
     cs = minfo.pos;
     foredel(l);
 
-    if (m->flags & CMF_ALL)
+    if (m->flags & CMF_ALL) {
 	do_allmatches(0);
-    else {
+        return;
+    }
 
     /* And then we insert the new string. */
     minfo.len = instmatch(m, &scs);
@@ -1136,7 +1138,6 @@
 	runhookdef(INSERTMATCHHOOK, (void *) &dat);
 	minfo.cur = om;
     }
-    }
 }
 
 /* Do completion, given that we are in the middle of a menu completion.  We *
@@ -1283,6 +1284,9 @@
 {
     Cmatch *mc;
 
+    if (iforcemenu == -1)
+        do_ambiguous();
+
     if (usemenu != 3) {
 	menucmp = 1;
 	menuacc = 0;
@@ -1324,7 +1328,8 @@
     }
 #endif
     mc = (minfo.group)->matches + insmnum;
-    do_single(*mc);
+    if (iforcemenu != -1)
+        do_single(*mc);
     minfo.cur = mc;
 }
 

-- 
Sven Wischnowsky                          wischnow@xxxxxxxxx



Messages sorted by: Reverse Date, Date, Thread, Author