.. _intro_zsh_completion:

Completion
==========

Another great :literal:`zsh` feature is completion.  If you hit :kbd:`Tab`, :literal:`zsh` will complete all kinds of stuff.  Like commands or filenames:

.. code-block:: text
   :caption: Complete commands and filenames
   :name: completion_tab_commands_files

   % comp«Tab»
   % compress _
   
   % ls nic«Tab»
   % ls nicecolors _
   
   % ls /usr/pr«Tab»
   % ls /usr/princeton/_
   
   % ls -l =com«Tab»
   % ls -l =compress _

.. _NO_LIST_BEEP:

.. index:: single: NO_LIST_BEEP

.. _COMPLETE_IN_WORD:

.. index:: single: COMPLETE_IN_WORD

If the completion is ambiguous, the editor will beep.  If you find this annoying, you can set the :literal:`NO_LIST_BEEP` option.  Completion can even be done in the middle of words.  To use this, you will have to set the :literal:`COMPLETE_IN_WORD` option:

.. code-block:: text
   :caption: Complete in middle of word
   :name: completion_complete_in_word

   % setopt completeinword
   % ls /usr/p_on«Tab»
   % ls /usr/prince_on/
   % setopt alwaystoend
   % ls /usr/p_on«Tab»
   % ls /usr/princeton/_

You can list possible completions by pressing :kbd:`Ctrl+D`:

.. code-block:: text
   :caption: List completions with Ctrl+D
   :name: completion_list_ctrl_d

   % ls /vmu«Tab» —beep—
   % ls /vmunix_
   % ls /vmunix«Ctrl+D»
   vmunix                    vmunix.old                
   vmunix.new.kernelmap.old  vmunix.org

.. _AUTO_LIST:

.. index:: single: AUTO_LIST

Or, you could just set the :literal:`AUTO_LIST` option:

.. code-block:: text
   :caption: AUTO_LIST completion listing
   :name: completion_auto_list

   % setopt autolist
   % ls /vmu«Tab» —beep—
   vmunix                    vmunix.old                
   vmunix.new.kernelmap.old  vmunix.org
   % ls /vmunix_

.. _LIST_TYPES:

.. index:: single: LIST_TYPES

.. _LIST_AMBIGUOUS:

.. index:: single: LIST_AMBIGUOUS

If you like to see the types of the files in these lists, like in :literal:`ls -F`, you can set the :literal:`LIST_TYPES` option.  Together with :literal:`AUTO_LIST` you can use :literal:`LIST_AMBIGUOUS`.  This will only list the possibilities if there is no unambiguous part to add:

.. code-block:: text
   :caption: LIST_AMBIGUOUS with Tab
   :name: completion_list_ambiguous

   % setopt listambiguous
   % ls /vmu«Tab» —beep—
   % ls /vmunix_«Tab» —beep—
   vmunix                    vmunix.old                
   vmunix.new.kernelmap.old  vmunix.org

.. _ALWAYS_LAST_PROMPT:

.. index:: single: ALWAYS_LAST_PROMPT

If you don't want several of these listings to scroll the screen so much, the :literal:`ALWAYS_LAST_PROMPT` option is useful.  If set, you can continue to edit the line you were editing, with the completion listing appearing beneath it.

.. _MENU_COMPLETE:

.. index:: single: MENU_COMPLETE

Another interesting option is :literal:`MENU_COMPLETE`.  This affects the way :kbd:`Tab` works.  Let's look at the :literal:`/vmunix` example again:

.. code-block:: text
   :caption: Menu completion with Tab
   :name: completion_menu_complete

   % setopt menucomplete
   % ls /vmu«Tab»
   % ls /vmunix«Tab»
   % ls /vmunix.new.kernelmap.old«Tab»
   % ls /vmunix.old_

Each time you press :kbd:`Tab`, it displays the next possible completion. In this way, you can cycle through the possible completions until you find the one you want.

.. _AUTO_MENU:

.. index:: single: AUTO_MENU

The :literal:`AUTO_MENU` option makes a nice compromise between this method of completion and the regular method.  If you set this option, pressing :kbd:`Tab` once completes the unambiguous part normally, pressing the :kbd:`Tab` key repeatedly after an ambiguous completion will cycle through the possible completions.

.. _REC_EXACT:

.. index:: single: REC_EXACT

Another option you could set is :literal:`REC_EXACT`, which causes exact matches to be accepted, even if there are other possible completions:

.. code-block:: text
   :caption: Accept exact matches
   :name: completion_recexact

   % setopt recexact
   % ls /vmu«Tab» —beep—
   vmunix                    vmunix.old                
   vmunix.new.kernelmap.old  vmunix.org
   % ls /vmunix_«Tab»
   % ls /vmunix _

.. _AUTO_REMOVE_SLASH:

.. index:: single: AUTO_REMOVE_SLASH

To facilitate the typing of pathnames, a slash will be added whenever a directory is completed.  Some computers don't like the spurious slashes at the end of directory names.  In that case, the :literal:`AUTO_REMOVE_SLASH` option comes to rescue.  It will remove these slashes when you type a space or return after them.

The :emphasis:`fignore` variable lists suffixes of files to ignore during completion.

.. code-block:: text
   :caption: Ignore suffixes with fignore
   :name: completion_fignore_suffixes

   % ls foo«Tab» —beep—
   foofile.c  foofile.o
   % fignore=( .o \~ .bak .junk )
   % ls foo«Tab»
   % ls foofile.c _

Since :literal:`foofile.o` has a suffix that is in the :literal:`fignore` list, it was not considered a possible completion of :literal:`foo`.

Username completion is also supported:

.. code-block:: text
   :caption: Complete tilde usernames
   :name: completion_tilde_username

   % ls ~pfal«Tab»
   % ls ~pfalstad/_

and parameter name completion:

.. code-block:: text
   :caption: Parameter name completion
   :name: completion_parameter

   % echo $ORG«Tab»
   % echo $ORGANIZATION _
   % echo ${ORG«Tab»
   % echo ${ORGANIZATION _

.. _AUTO_PARAM_KEYS:

.. index:: single: AUTO_PARAM_KEYS

Note that in the last example a space is added after the completion as usual.  But if you want to add a colon or closing brace, you probably don't want this extra space.  Setting the :literal:`AUTO_PARAM_KEYS` option will automatically remove this space if you type a colon or closing brace after such a completion.

There is also option completion:

.. code-block:: text
   :caption: Option name completion
   :name: completion_setopt

   % setopt nocl«Tab»
   % setopt noclobber _

and binding completion:

.. code-block:: text
   :caption: Completing bindkey arguments
   :name: completion_bindkey

   % bindkey '^X^X' pu«Tab»
   % bindkey '^X^X' push-line _

The :literal:`compctl` command is used to control completion of the arguments of specific commands.  For example, to specify that certain commands take other commands as arguments, you use :literal:`compctl -c`:

.. code-block:: text
   :caption: compctl commands for man
   :name: completion_compctl_commands

   % compctl -c man nohup
   % man upt«Tab»
   % man uptime _

To specify that a command should complete filenames, you should use :literal:`compctl -f`.  This is the default.  It can be combined with :literal:`-c`, as well.

.. code-block:: text
   :caption: compctl commands and files
   :name: completion_compctl_cmd_files

   % compctl -cf echo
   % echo upt«Tab»
   % echo uptime _
   
   % echo fo«Tab»
   % echo foo.c

Similarly, use :literal:`-o` to specify options, :literal:`-v` to specify variables, and :literal:`-b` to specify bindings.

.. code-block:: text
   :caption: compctl options variables bindings
   :name: completion_compctl_ovb

   % compctl -o setopt unsetopt
   % compctl -v typeset vared unset export
   % compctl -b bindkey

You can also use :literal:`-k` to specify a custom list of keywords to use in completion.  After the :literal:`-k` comes either the name of an array or a literal array to take completions from.

.. code-block:: text
   :caption: compctl custom keyword lists
   :name: completion_compctl_keywords

   % ftphosts=(ftp.uu.net wuarchive.wustl.edu)
   % compctl -k ftphosts ftp
   % ftp wu«Tab»
   % ftp wuarchive.wustl.edu _
   
   % compctl -k '(cpirazzi subbarao sukthnkr)' mail finger
   % finger cp«Tab»
   % finger cpirazzi _

To better specify the files to complete for a command, use the :literal:`-g` option which takes any glob pattern as an argument.  Be sure to quote the glob patterns as otherwise they will be expanded when the :literal:`compctl` command is run.

.. code-block:: text
   :caption: compctl globs for TeX tools
   :name: completion_compctl_glob_tex

   % ls
   letter.tex  letter.dvi  letter.aux  letter.log  letter.toc
   % compctl -g '*.tex' latex
   % compctl -g '*.dvi' xdvi dvips
   % latex l«Tab»
   % latex letter.tex _
   % xdvi l«Tab»
   % xdvi letter.dvi _

Glob patterns can include qualifiers within parentheses.  To rmdir only directories and cd to directories and symbolic links pointing to them:

.. code-block:: text
   :caption: compctl directory-only globs
   :name: completion_compctl_directories

   % compctl -g '*(-/)' cd
   % compctl -g '*(/)' rmdir

RCS users like to run commands on files which are not in the current directory, but in the RCS subdirectory where they all get :literal:`,v` suffixes.  They might like to use

.. code-block:: text
   :caption: compctl RCS ,v files
   :name: completion_compctl_rcs

   % compctl -g 'RCS/*(:t:s/\,v//)' co rlog rcs
   % ls RCS
   builtin.c,v  lex.c,v      zle_main.c,v
   % rlog bu«Tab»
   % rlog builtin.c _

The :literal:`:t` modifier keeps only the last part of the pathname and the :literal:`:s/\\,v//` will replace any :literal:`,v` by nothing.

The :literal:`-s` flag is similar to :literal:`-g`, but it uses all expansions, instead of just globbing, like brace expansion, parameter substitution and command substitution.

.. code-block:: text
   :caption: compctl -s substitutions
   :name: completion_compctl_s

   % compctl -s '$(setopt)' unsetopt

will only complete options which are actually set to be arguments to :literal:`unsetopt`.

Sometimes a command takes another command as its argument.  You can tell :literal:`zsh` to complete commands as the first argument to such a command and then use the completion method of the second command.  The :literal:`-l` flag with a null-string argument is used for this.

.. code-block:: text
   :caption: compctl follow command args
   :name: completion_compctl_follow

   % compctl -l '' nohup exec
   % nohup comp«Tab»
   % nohup compress _
   % nohup compress fil«Tab»
   % nohup compress filename _

Sometimes you would like to run really complicated commands to find out what the possible completions are.  To do this, you can specify a shell function to be called that will assign the possible completions to a variable called reply.  Note that this variable must be an array. Here's another (much slower) way to get the completions for :literal:`co` and friends:

.. code-block:: text
   :caption: compctl via reply function
   :name: completion_compctl_function

   % function getrcs {
   > reply=()
   > for i in RCS/*
   >   do
   >   reply=($reply[*] $(basename $i ,v))
   >   done
   > }
   % compctl -K getrcs co rlog rcs

Some command arguments use a prefix that is not a part of the things to complete.  The kill builtin command takes a signal name after a :literal:`-`.  To make such a prefix be ignored in the completion process, you can use the :literal:`-P` flag.

.. code-block:: text
   :caption: compctl kill signal prefix
   :name: completion_compctl_kill_prefix

   % compctl -P - -k signals kill
   % kill -H«Tab»
   % kill -HUP _

TeX is usually run on files ending in :literal:`.tex`, but also sometimes on other files.  It is somewhat annoying to specify that the arguments of TeX should end in :literal:`.tex` and then not be able to complete these other files.  Therefore you can specify things like "Complete to files ending in :literal:`.tex` if available, otherwise complete to any filename.".  This is done with :emphasis:`xor`\ ed completion:

.. code-block:: text
   :caption: Xor completion for tex
   :name: completion_compctl_xor_tex

   % compctl -g '*.tex' + -f tex

The :literal:`+` tells the editor to only take the next thing into account if the current one doesn't generate any matches.  If you have not changed the default completion, the above example is in fact equivalent to

.. code-block:: text
   :caption: Xor with default completion
   :name: completion_compctl_xor_default

   % compctl -g '*.tex' + tex

as a lone :literal:`+` at the end is equivalent to specifying the default completion after the :literal:`+`.  This form of completion is also frequently used if you want to run some command only on a certain type of files, but not necessarily in the current directory.  In this case you will want to complete both files of this type and directories. Depending on your preferences you can use either of

.. code-block:: text
   :caption: Xor files and directories
   :name: completion_compctl_xor_dirs

   % compctl -g '*.ps' + -g '*(-/)' ghostview
   % compctl -g '*.ps *(-/)' ghostview

where the first one will only complete directories (and symbolic links pointing to directories) if no postscript file matches the already typed part of the argument.
