From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 3930 invoked from network); 4 Feb 2000 15:04:13 -0000 Received: from sunsite.auc.dk (130.225.51.30) by ns1.primenet.com.au with SMTP; 4 Feb 2000 15:04:13 -0000 Received: (qmail 12510 invoked by alias); 4 Feb 2000 15:04:07 -0000 Mailing-List: contact zsh-workers-help@sunsite.auc.dk; run by ezmlm Precedence: bulk X-No-Archive: yes X-Seq: 9569 Received: (qmail 12502 invoked from network); 4 Feb 2000 15:04:06 -0000 Date: Fri, 4 Feb 2000 16:04:04 +0100 (MET) Message-Id: <200002041504.QAA28963@beta.informatik.hu-berlin.de> From: Sven Wischnowsky To: zsh-workers@sunsite.auc.dk Subject: PATCH: a new completer The hunks in compcore.c fix some problems in the suffix-matching code. The new completer is `_prefix'. It allows one to try completion with ignoring the suffix of the word the cursor is on. I.e. if you have `zsfrob' with the cursor after the `zs' and try completion with _prefix in your completer list, it will try to complete `zs' and leave the suffix alone. What types of completion are to be tried can be set with a locally used completer style. If that is not set it uses the global list currently used -- see the manual for examples. Bye Sven diff -ru ../z.old/Completion/Core/_main_complete Completion/Core/_main_complete --- ../z.old/Completion/Core/_main_complete Fri Feb 4 13:32:30 2000 +++ Completion/Core/_main_complete Fri Feb 4 15:35:42 2000 @@ -20,6 +20,7 @@ unsetopt markdirs globsubst shwordsplit nounset ksharrays local comp post ret=1 _compskip _prio_num=1 format _comp_ignore \ + _completers _completers_left \ context state line opt_args val_args curcontext="$curcontext" \ _last_nmatches=-1 _last_menu_style _def_menu_style _menu_style sel \ _saved_exact="${compstate[exact]}" \ @@ -63,11 +64,15 @@ # And now just call the completer functions defined. +_completers=( "$@" ) +_completers_left=( "$@" ) + for comp; do if "$comp"; then ret=0 break; fi + shift 1 _completers_left done if (( $compstate[nmatches] )); then diff -ru ../z.old/Completion/Core/_prefix Completion/Core/_prefix --- ../z.old/Completion/Core/_prefix Fri Feb 4 15:35:08 2000 +++ Completion/Core/_prefix Fri Feb 4 15:58:36 2000 @@ -0,0 +1,23 @@ +#autoload + +# Try to ignore the suffix. A bit like e-o-c-prefix. + +[[ -n "$SUFFIX" ]] || return 1 + +local curcontext="${curcontext/:[^:]#:/:prefix:}" comp i + +zstyle -a ":completion:${curcontext}:" completer comp || + comp=( "${(@)_completers[1,-${#_completers_left}-1][(R)_prefix,-1]}" ) + +if zstyle -t ":completion:${curcontext}:" add-space; then + ISUFFIX=" $SUFFIX" +else + ISUFFIX="$SUFFIX" +fi +SUFFIX='' + +for i in "$comp[@]"; do + [[ "$i" != _prefix ]] && "$i" && return 0 +done + +return 1 diff -ru ../z.old/Doc/Zsh/compsys.yo Doc/Zsh/compsys.yo --- ../z.old/Doc/Zsh/compsys.yo Fri Feb 4 13:32:10 2000 +++ Doc/Zsh/compsys.yo Fri Feb 4 15:57:54 2000 @@ -681,6 +681,10 @@ same as the string on the line, this match will immediately be accepted. ) +item(tt(add-space))( +This style is used by the tt(_prefix) completer to decide if a space +should be inserted before the suffix. +) item(tt(arguments))( The value of this style is given to the tt(ps) command by functions that call it when generating process identifiers as matches. @@ -1583,16 +1587,6 @@ ifzman(the section `Completion System Configuration' above)\ ifnzman(noderef(Completion System Configuration)). ) -findex(_menu) -item(tt(_menu))( -This completer is a simple example function implemented to show how -menucompletion can be done in shell code. It should be used as the -first completer and has the effect of making the code perform -menucompletion. Note that this is independent of the setting of the -tt(MENU_COMPLETE) option and does not work with the other -menucompletion widgets such as tt(reverse-menu-complete), or -tt(accept-and-menu-complete). -) findex(_oldlist) item(tt(_oldlist))( This completer controls how the standard completion widgets behave @@ -1603,6 +1597,46 @@ tt(menu), see ifzman(the section `Completion System Configuration' above)\ ifnzman(noderef(Completion System Configuration)). +) +findex(_prefix) +item(tt(_prefix))( +This completer can be used to try completion with the suffix after the +cursor ignored. I.e. the suffix will not be considered to be part of +the word to complete and hence does not need to be matched. It uses +the tt(completer) style to decide which other completers to call to +try to generate matches. If this style is unset, the completers +currently used by the whole completion are used -- except, of course, +the tt(_prefix) completer itself. Also, if this completer appears more +than once in the list of completers to use only those completers not +already tried by the last invocation of tt(_prefix) will be called. + +For example, consider this global tt(completer) style: + +example(zstyle ':completion:::::' completer _complete _prefix _correct _prefix) + +This makes the tt(_prefix) completer try normal completion with the +suffix ignored. If that doesn't generate any matches and neither does +the call to the tt(_correct) completer after it, then tt(_prefix) will +be called a second time and will now only try correction with the +suffix ignored. If you want to use tt(_prefix) as the last resort and +want it to try only normal completion, you need to do: + +example(zstyle ':completion:::::' completer _complete ... _prefix +zstyle ':completion::prefix:::' completer _complete) + +The tt(add-space) style is used, too. If it is set to `true' then +tt(_prefix) will insert a space between the matches generated (if any) +and the suffix. +) +findex(_menu) +item(tt(_menu))( +This completer is a simple example function implemented to show how +menucompletion can be done in shell code. It should be used as the +first completer and has the effect of making the code perform +menucompletion. Note that this is independent of the setting of the +tt(MENU_COMPLETE) option and does not work with the other +menucompletion widgets such as tt(reverse-menu-complete), or +tt(accept-and-menu-complete). ) enditem() diff -ru ../z.old/Src/Zle/compcore.c Src/Zle/compcore.c --- ../z.old/Src/Zle/compcore.c Fri Feb 4 13:32:01 2000 +++ Src/Zle/compcore.c Fri Feb 4 15:25:40 2000 @@ -1974,21 +1974,12 @@ salen += (qisl = strlen(qisuf)); if (salen) { - char *asuf = (char *) zhalloc(salen); Cline pp, p, s, sl = NULL; - - - if (psl) - memcpy(asuf, psuf, psl); - if (isl) - memcpy(asuf + psl, isuf, isl); - if (qisl) - memcpy(asuf + psl + isl, qisuf, qisl); for (pp = NULL, p = line; p->next; pp = p, p = p->next); - if (salen > qisl) { - s = bld_parts(asuf, salen - qisl, salen - qisl, &sl); + if (psl) { + s = bld_parts(psuf, psl, psl, &sl); if (sline) { Cline sp; @@ -1998,6 +1989,7 @@ for (sp = sline; sp->next; sp = sp->next); sp->next = s; s = sline; + sline = NULL; } if (!(p->flags & (CLF_SUF | CLF_MID)) && !p->llen && !p->wlen && !p->olen) { @@ -2009,7 +2001,7 @@ s->prefix = p->prefix; p->prefix = NULL; } - s->flags |= (p->flags & CLF_MATCHED); + s->flags |= (p->flags & CLF_MATCHED) | CLF_MID; free_cline(p); if (pp) pp->next = s; @@ -2018,8 +2010,29 @@ } else p->next = s; } + if (isl) { + Cline tsl; + + s = bld_parts(isuf, isl, isl, &tsl); + + if (sl) + sl->next = s; + else if (sline) { + Cline sp; + + sline = cp_cline(sline, 1); + + for (sp = sline; sp->next; sp = sp->next); + sp->next = s; + p->next = sline; + sline = NULL; + } else + p->next = s; + + sl = tsl; + } if (qisl) { - Cline qsl = bld_parts(asuf + psl + isl, qisl, qisl, NULL); + Cline qsl = bld_parts(qisuf, qisl, qisl, NULL); qsl->flags |= CLF_SUF; qsl->suffix = qsl->prefix; @@ -2129,7 +2142,7 @@ } else for (p = lp = cp_cline(pline, 1); lp->next; lp = lp->next); - if (lp->prefix && !(line->flags & (CLF_SUF | CLF_MID)) && + if (lp->prefix && !(line->flags & CLF_SUF) && !lp->llen && !lp->wlen && !lp->olen) { Cline lpp; -- Sven Wischnowsky wischnow@informatik.hu-berlin.de