.. _intro_zsh_bindings:

Bindings
========

Each of the editor commands we have seen was actually a function bound by default to a certain key.  The real names of the commands are:

.. code-block:: text
   :caption: Default editor key bindings
   :name: bindings_default_bindings

   expand-or-complete   «Tab»
   push-line            «Esc+Q»
   run-help             «Esc+H»
   accept-and-hold      «Esc+A»
   quote-line           «Esc+'»

These bindings are arbitrary; you could change them if you want. For example, to bind :literal:`accept-line` to :kbd:`Ctrl+Z`:

.. code-block:: text
   :caption: bindkey for Ctrl+Z
   :name: bindings_bindkey_ctrl_z

   % bindkey '^Z' accept-line

Another idea would be to bind the delete key to :literal:`delete-char`; this might be convenient if you use :kbd:`Ctrl+H` for backspace.

.. code-block:: text
   :caption: bindkey delete-char
   :name: bindings_bindkey_delete

   % bindkey '^?' delete-char

Or, you could bind :kbd:`Ctrl+X`\ :kbd:`Ctrl+H` to :literal:`run-help`:

.. code-block:: text
   :caption: bindkey Ctrl+X H run-help
   :name: bindings_bindkey_run_help

   % bindkey '^X^H' run-help

Other examples:

.. code-block:: text
   :caption: Miscellaneous bindkey examples
   :name: bindings_bindkey_misc

   % bindkey '^X^Z' universal-argument
   % bindkey ' ' magic-space
   % bindkey -s '^T' 'uptime
   > '
   % bindkey '^Q' push-line-or-edit

:literal:`universal-argument` multiplies the next command by 4. Thus :kbd:`Ctrl+X`\ :kbd:`Ctrl+Z`\ :kbd:`Ctrl+W` might delete the last four words on the line. If you bind space to :literal:`magic-space`, then csh-style history expansion is done on the line whenever you press the space bar.

Something that often happens is that I am typing a multiline command and discover an error in one of the previous lines.  In this case, :literal:`push-line-or-edit` will put the entire multiline construct into the editor buffer.  If there is only a single line, it is equivalent to :literal:`push-line`.

The :literal:`-s` flag to :literal:`bindkey` specifies that you are binding the key to a string, not a command.  Thus :literal:`bindkey -s '^T' 'uptime\\n'` lets you VMS lovers get the load average whenever you press :kbd:`Ctrl+T`.

If you have a NeXT keyboard, the one with the :literal:`|` and :literal:`\\` keys very inconveniently placed, the following bindings may come in handy:

.. code-block:: text
   :caption: NeXT keyboard Alt bindings
   :name: bindings_bindkey_next_keys

   % bindkey -s '\e/' '\\'
   % bindkey -s '\e=' '|'

Now you can type :kbd:`Alt+/` to get a backslash, and :kbd:`Alt+=` to get a vertical bar.  This only works inside :literal:`zsh`, of course; :literal:`bindkey` has no effect on the key mappings inside :literal:`talk` or :literal:`mail`, etc.

.. _NO_FLOW_CONTROL:

.. index:: single: NO_FLOW_CONTROL

Some people like to bind :kbd:`Ctrl+S` and :kbd:`Ctrl+Q` to editor commands. Just binding these has no effect, as the terminal will catch them and use them for flow control.  You could unset them as stop and start characters, but most people like to use these for external commands. The solution is to set the :literal:`NO_FLOW_CONTROL` option.  This will allow you to bind the start and stop characters to editor commands, while retaining their normal use for external commands.
