|
|
vi can assign sequences of commands to a series of keys or control characters so that whenever a mapped key sequence is typed, the command to which it is mapped is carried out. There are two commands to do this: :map, which works in command mode, and :map!, which works in insertion mode.
To assign a command to a sequence of keystrokes, issue the
:map! command in command mode.
For example, to assign the command "ad$ to the
key <Ctrl>C, you would enter the following:
:map ^C "ad$
^C is a <Ctrl>C character. (To enter the <Ctrl>C without letting vi interpret it, type <Ctrl>V<Ctrl>C.) This command cuts all text between the current cursor position and the end of the line, and places it in buffer ``a''. Now, whenever you type <Ctrl>C in command mode, it will carry out the defined series of commands.
To assign a key mapping in insertion mode, go to command mode and
issue the :map! command.
For example, to make the sequence ``EC'' map to ``European
Community'', enter:
:map! EC European Community
To remove a mapping from a key, use the unmap (or
:unmap!) command; for
example:
:unmap ^C
:unmap! EC
When you begin to type a letter that may be part of a mapped command, vi saves up your typed input and checks whether it matches a mapping before it does anything. If the key sequence you type is a mapped command, vi executes it as soon as the command is complete; if not, when it becomes clear that you are not typing a mapped key sequence, vi acts on the keystrokes. (vi waits for a period of time that you can alter by resetting the timeout internal variable. See the vi(1) manual page for further details. The ab command works in a different manner described by ``Defining abbreviations''.)
To stop vi from expanding a mapping, you must escape
the first character of the command before you begin
typing. For example, using the mapping above, to enter the
acronym ``EC'' you must escape the mapped word by entering:
<Ctrl>VEC
(If you had used an abbreviation for
``ma1G'' instead of a mapping, you would have to type the
following
to escape it:
ma1G<Ctrl>V
For example, consider the following bad definition:
:map! n banana
If you were to try this example, the next
time you typed the letter ``n'' vi would
expand it to ``banana''. But it would only get as far as
the third character in ``banana'' before it saw another
``n'' and tried to expand it. The process
produces output like:
bababababababababababababababababa
vi begins to execute the mapping then dies.
Sometimes it is useful to create a mapping or command that
changes mode while it runs. For example, to create a
command-mode mapping that inserts a piece of text under
the cursor without leaving command mode, do this:
:map h iHello there!^[
The ``^['' character means ``escape''. To enter it into a mapping without letting vi act on it as if it is a command, press <Ctrl>V<Esc>.
When you press ``h'' in command mode, vi carries out the actions in the mapping. It executes the command i and switches to insert mode, enters the characters ``Hello there!'', then switches back to command mode on encountering the Esc character in the sequence of keys.
For example, suppose you have stored your name and address
in a file called .address in your home directory.
You can define a
mapping that will automatically insert the contents of .address
at the beginning of a file you are editing. For example, if your
login is roberta, the mapping would be:
:map % ma1G^:0r /u/roberta/.address^M`a
When you type the ``%'' key in
command mode, the first command, ma, marks your current
position in the file with marker ``a''. The next commands,
1G^, go to line one of the file, then to the
beginning of that line. The following command reads
in the file /u/roberta/.address at the current location:
:r /u/roberta/.address^M
The mapping ends with the command `a, which returns to marker ``a''.
Note that ^M is a carriage return character entered into your mapping by pressing <Ctrl>V<Enter>.
Now whenever you type the ``%'' key in command mode, vi executes the command sequence to insert /u/roberta/.address at the top of your file.