mirror of https://github.com/tLDP/LDP
557 lines
17 KiB
Plaintext
557 lines
17 KiB
Plaintext
<!doctype linuxdoc system>
|
|
<!-- $Id$ -->
|
|
|
|
<article>
|
|
|
|
<title>How to change the title of an xterm</title>
|
|
<author>Ric Lister, <tt>ric@giccs.georgetown.edu</tt></author>
|
|
<date>v2.0, 27 October 1999</date>
|
|
|
|
<abstract>
|
|
This document explains how to use escape sequences to
|
|
dynamically change window and icon titles of an xterm. Examples are
|
|
given for several shells, and the appendix gives escape sequences
|
|
for some other terminal types.
|
|
</abstract>
|
|
|
|
|
|
<toc>
|
|
|
|
|
|
<sect>Where to find this document
|
|
|
|
<p>
|
|
This document is now part of the
|
|
<url name="Linux HOWTO Index" url="http://sunsite.unc.edu/LDP/HOWTO/">
|
|
and can be found at
|
|
<url url="http://sunsite.unc.edu/LDP/HOWTO/mini/Xterm-Title.html">.
|
|
|
|
<p>
|
|
The latest version can always be found in several formats at
|
|
<url url="http://www.giccs.georgetown.edu/~ric/howto/Xterm-Title/">.
|
|
|
|
<p>
|
|
This document supercedes the original howto written
|
|
by Winfried Trümper.
|
|
|
|
|
|
<sect>Static titles
|
|
|
|
<p>
|
|
A static title may be set for any of the terminals <tt>xterm</tt>,
|
|
<tt>color-xterm</tt> or <tt>rxvt</tt>, by using the <tt>-T</tt> and
|
|
<tt>-n</tt> switches:
|
|
<tscreen>
|
|
xterm -T "My XTerm's Title" -n "My XTerm's Icon Title"
|
|
</tscreen>
|
|
|
|
|
|
<sect>Dynamic titles
|
|
|
|
<p>
|
|
Many people find it useful to set the title of a terminal to reflect
|
|
dynamic information, such as the name of the host the user is logged
|
|
into, the current working directory, etc.
|
|
|
|
|
|
<sect1>xterm escape sequences
|
|
|
|
<p>
|
|
Window and icon titles may be changed in a running xterm
|
|
by using XTerm escape sequences. The following sequences
|
|
are useful in this respect:
|
|
<itemize>
|
|
<item><tt>ESC]0;<bf>string</bf>BEL</tt> -- Set icon name and window title
|
|
to <bf>string</bf>
|
|
<item><tt>ESC]1;<bf>string</bf>BEL</tt> -- Set icon name to <bf>string</bf>
|
|
<item><tt>ESC]2;<bf>string</bf>BEL</tt> -- Set window title to
|
|
<bf>string</bf>
|
|
</itemize>
|
|
where <tt>ESC</tt> is the <bf>escape</bf> character (\033), and <tt>BEL</tt> is
|
|
the <bf>bell</bf> character (\007).
|
|
|
|
<p>
|
|
Printing one of these sequences within the xterm will cause the
|
|
window or icon title to be changed.
|
|
|
|
<p>
|
|
<bf>Note</bf>: these sequences apply to most xterm derivatives,
|
|
such as <tt>nxterm</tt>, <tt>color-xterm</tt> and <tt>rxvt</tt>. Other
|
|
terminal types often use different escapes; see the
|
|
appendix for examples. For the full list of
|
|
xterm escape sequences see the file
|
|
<url name="ctlseq2.txt"
|
|
url="http://www.giccs.georgetown.edu/~ric/howto/Xterm-Title/ctlseq2.txt">,
|
|
which comes with the xterm distribution, or
|
|
<url url="http://www.giccs.georgetown.edu/~ric/howto/Xterm-Title/xterm.seq"
|
|
name="xterm.seq">, which comes with the
|
|
<url url="http://www.rxvt.org/" name="rxvt"> distribution.
|
|
|
|
|
|
<sect1>Printing the escape sequences
|
|
|
|
<p>
|
|
For information that is constant throughout the lifetime of
|
|
this shell, such as host and username, it will suffice to
|
|
simply echo the escape string in the shell rc file:
|
|
<tscreen><verb>
|
|
echo -n "\033]0;${USER}@${HOST}\007"
|
|
</verb></tscreen>
|
|
should produce a title like <tt>username@hostname</tt>, assuming
|
|
the shell variables <tt>$USER</tt> and <tt>$HOST</tt> are set correctly.
|
|
The required options for <tt>echo</tt> may vary by shell (see examples
|
|
below).
|
|
|
|
<p>
|
|
For information that may change during the shell's lifetime, such
|
|
as current working directory, these escapes really need to be
|
|
applied every time the prompt changes.
|
|
This way the string is updated with every command you issue and can keep
|
|
track of information such as current working directory, username, hostname,
|
|
etc. Some shells provide special functions for this purpose, some don't
|
|
and we have to insert the title sequences directly into the prompt
|
|
string. This is illustrated in the next section.
|
|
|
|
|
|
<sect>Examples for different shells
|
|
|
|
<p>
|
|
Below we provide an set of examples for some of the more common shells.
|
|
We start with <tt>zsh</tt> as it provides several facilities that
|
|
make our job much easier. We will then progress through increasingly
|
|
difficult examples.
|
|
|
|
<p>
|
|
In all the examples we test the environment variable <tt>$TERM</tt>
|
|
to make sure we only apply the escapes to xterms. We test for
|
|
<tt>$TERM=xterm*</tt>; the wildcard is because some variants (such as
|
|
rxvt) can set <tt>$TERM=xterm-color</tt>.
|
|
|
|
<p>
|
|
We should make an extra comment about C shell derivatives, such as
|
|
<tt>tcsh</tt> and <tt>csh</tt>. In C shells, undefined variables are
|
|
fatal errors. Therefore, before testing the variable <tt>$TERM</tt>, it
|
|
is necessary to test for its existence so as not to break non-interactive
|
|
shells. To achieve this you must wrap the examples below in something
|
|
like:
|
|
<tscreen><verb>
|
|
if ($?TERM) then
|
|
...
|
|
endif
|
|
</verb></tscreen>
|
|
(In our opinion this is just one of many reasons not to use C shells. See
|
|
<it><url name="Csh Programming Considered Harmful"
|
|
url="http://language.perl.com/versus/csh.whynot"></it> for a useful
|
|
discussion).
|
|
|
|
<p>
|
|
The examples below should be used by inserting them into the appropriate
|
|
shell initialisation file; i.e. one that is sourced by interactive shells
|
|
on startup. In most cases this is called something like
|
|
<tt>.<it>shell</it>rc</tt> (e.g. <tt>.zshrc</tt>, <tt>.tcshrc</tt>, etc).
|
|
|
|
|
|
|
|
<sect1>zsh
|
|
|
|
<p>
|
|
<tt>zsh</tt> provides some functions and expansions, which we will use:
|
|
<tscreen><verb>
|
|
precmd () a function which is executed just before each prompt
|
|
chpwd () a function which is executed whenever the directory is changed
|
|
\e escape sequence for escape (ESC)
|
|
\a escape sequence for bell (BEL)
|
|
%n expands to $USERNAME
|
|
%m expands to hostname up to first '.'
|
|
%~ expands to directory, replacing $HOME with '~'
|
|
</verb></tscreen>
|
|
There are many more expansions available: see the <tt>zshmisc</tt> man page.
|
|
|
|
<p>
|
|
Thus, the following will set the xterm title to
|
|
"<tt><it>username</it>@<it>hostname</it>: <it>directory</it></tt>":
|
|
<tscreen><verb>
|
|
case $TERM in
|
|
xterm*)
|
|
precmd () {print -Pn "\e]0;%n@%m: %~\a"}
|
|
;;
|
|
esac
|
|
</verb></tscreen>
|
|
This could also be achieved by using <tt>chpwd()</tt> instead
|
|
of <tt>precmd()</tt>. The <tt>print</tt> builtin works like
|
|
<tt>echo</tt>, but gives us access to the <tt>%</tt> prompt escapes.
|
|
|
|
|
|
<sect1>tcsh
|
|
|
|
<p>
|
|
<tt>tcsh</tt> has some functions and expansions similar to those of
|
|
<tt>zsh</tt>:
|
|
<tscreen><verb>
|
|
precmd () a function which is executed just before each prompt
|
|
cwdcmd () a function which is executed whenever the directory is changed
|
|
%n expands to username
|
|
%m expands to hostname
|
|
%~ expands to directory, replacing $HOME with '~'
|
|
%# expands to '>' for normal users, '#' for root users
|
|
%{...%} includes a string as a literal escape sequence
|
|
</verb></tscreen>
|
|
|
|
<p>
|
|
Unfortunately, there is no equivalent to <tt>zsh</tt>'s <tt>print</tt>
|
|
command allowing us to use prompt escapes in the title string,
|
|
so the best we can do is to use shell variables (in <tt>~/.tcshrc</tt>):
|
|
<tscreen><verb>
|
|
switch ($TERM)
|
|
case "xterm*":
|
|
alias precmd 'echo -n "\033]0;${HOST}:$cwd\007"'
|
|
breaksw
|
|
endsw
|
|
</verb></tscreen>
|
|
However, this gives the directory's full path instead of using <tt>~</tt>.
|
|
Instead you can insert the string in the prompt:
|
|
<tscreen><verb>
|
|
switch ($TERM)
|
|
case "xterm*":
|
|
set prompt="%{\033]0;%n@%m:%~\007%}tcsh%# "
|
|
breaksw
|
|
default:
|
|
set prompt="tcsh%# "
|
|
breaksw
|
|
endsw
|
|
</verb></tscreen>
|
|
which sets a prompt of "<tt>tcsh% </tt>", and an xterm title and icon
|
|
of "<tt><it>username</it>@<it>hostname</it>: <it>directory</it></tt>". Note that
|
|
the "<tt>%{...%}</tt>" must be placed around escape sequences (and cannot
|
|
be the last item in the prompt: see the <tt>tcsh</tt> man page for details).
|
|
|
|
|
|
<sect1>bash
|
|
|
|
<p>
|
|
<tt>bash</tt> supplies a variable <tt>$PROMPT_COMMAND</tt> which contains a
|
|
command to execute before the prompt. This example sets the title to
|
|
<tt>username@hostname: directory</tt>:
|
|
<tscreen><verb>
|
|
PROMPT_COMMAND='echo -ne "\033]0;${USER}@${HOSTNAME}: ${PWD}\007"'
|
|
</verb></tscreen>
|
|
where <tt>\033</tt> is the character code for <tt>ESC</tt>,
|
|
and <tt>\007</tt> for <tt>BEL</tt>.
|
|
|
|
<p>
|
|
Note that the quoting is important here: variables are expanded in
|
|
<tt>"..."</tt>, and not expanded in <tt>'...'</tt>. So
|
|
<tt>$PROMPT_COMMAND</tt> is set to an unexpanded value, but the
|
|
variables inside <tt>"..."</tt> are expanded when
|
|
<tt>$PROMPT_COMMAND</tt> is used.
|
|
|
|
<p>
|
|
However, <tt>$PWD</tt> produces the full directory path. If we want to
|
|
use the <tt>~</tt> shorthand we need to embed the escape string in the
|
|
prompt, which allows us to take advantage of the following prompt expansions
|
|
provided by the shell:
|
|
<tscreen><verb>
|
|
\u expands to $USERNAME
|
|
\h expands to hostname up to first '.'
|
|
\w expands to directory, replacing $HOME with '~'
|
|
\$ expands to '$' for normal users, '#' for root
|
|
\[...\] embeds a sequence of non-printing characters
|
|
</verb></tscreen>
|
|
|
|
<p>
|
|
Thus, the following produces a prompt of <tt>bash$ </tt>, and an xterm
|
|
title of <tt>username@hostname: directory</tt>:
|
|
<tscreen><verb>
|
|
case $TERM in
|
|
xterm*)
|
|
PS1="\[\033]0;\u@\h: \w\007\]bash\\$ "
|
|
;;
|
|
*)
|
|
PS1="bash\\$ "
|
|
;;
|
|
esac
|
|
</verb></tscreen>
|
|
Note the use of <tt>\[...\]</tt>, which tells <tt>bash</tt> to ignore
|
|
the non-printing control characters when calculating the width
|
|
of the prompt. Otherwise line editing commands get confused while
|
|
placing the cursor.
|
|
|
|
|
|
<sect1>ksh
|
|
|
|
<p>
|
|
<tt>ksh</tt> provides little in the way of functions and expansions, so
|
|
we have to insert the escape string in the prompt to have it updated
|
|
dynamically. This example produces a title of
|
|
<tt>username@hostname: directory</tt> and a prompt of <tt>ksh$ </tt>.
|
|
<tscreen><verb>
|
|
case $TERM in
|
|
xterm*)
|
|
HOST=`hostname`
|
|
PS1='^[]0;${USER}@${HOST}: ${PWD}^Gksh$ '
|
|
;;
|
|
*)
|
|
PS1='ksh$ '
|
|
;;
|
|
esac
|
|
</verb></tscreen>
|
|
However, <tt>$PWD</tt> produces the full directory path. We can remove the
|
|
prefix of <tt>$HOME/</tt> from the directory using the <tt>${...##...}</tt>
|
|
construct. We can also use <tt>${...%%...}</tt> to truncate the hostname:
|
|
<tscreen><verb>
|
|
HOST=`hostname`
|
|
HOST=${HOST%%.*}
|
|
PS1='^[]0;${USER}@${HOST}: ${PWD##${HOME}/}^Gksh$ '
|
|
</verb></tscreen>
|
|
Note that the <tt>^[</tt> and <tt>^G</tt> in the prompt string are single
|
|
characters for <tt>ESC</tt> and <tt>BEL</tt> (can be entered in emacs
|
|
using <tt>C-q ESC</tt> and <tt>C-q C-g</tt>).
|
|
|
|
|
|
<sect1>csh
|
|
|
|
<p>
|
|
This is very difficult indeed in <tt>csh</tt>, and we end up doing something
|
|
like the following:
|
|
<tscreen><verb>
|
|
switch ($TERM)
|
|
case "xterm*":
|
|
set host=`hostname`
|
|
alias cd 'cd \!*; echo -n "^[]0;${user}@${host}: ${cwd}^Gcsh% "'
|
|
breaksw
|
|
default:
|
|
set prompt='csh% '
|
|
breaksw
|
|
endsw
|
|
</verb></tscreen>
|
|
where we have had to alias the <tt>cd</tt> command to do the work of
|
|
sending the escape sequence. Note that the <tt>^[</tt> and <tt>^G</tt> in
|
|
the string are single characters for <tt>ESC</tt> and <tt>BEL</tt>
|
|
(can be entered in emacs using <tt>C-q ESC</tt> and <tt>C-q C-g</tt>).
|
|
|
|
<p>
|
|
Notes: on some systems <tt>hostname -s</tt> may be used to get
|
|
a short, rather than fully-qualified, hostname. Some users with
|
|
symlinked directories may find <tt>`pwd`</tt> (backquotes to run the
|
|
<tt>pwd</tt> command) gives a more accurate path than <tt>$cwd</tt>.
|
|
|
|
|
|
|
|
<sect>Printing the current job name
|
|
|
|
<p>
|
|
Often a user will start a long-lived foreground job such as <tt>top</tt>,
|
|
an editor, an email client, etc, and wishes the name of the job
|
|
to be shown in the title. This is a more thorny problem and is
|
|
only achieved easily in <tt>zsh</tt>.
|
|
|
|
<sect1>zsh
|
|
|
|
<p>
|
|
<tt>zsh</tt> provides an ideal builtin function for this purpose:
|
|
<tscreen><verb>
|
|
preexec() a function which is just before a command is executed
|
|
$*,$1,... arguments passed to preexec()
|
|
</verb></tscreen>
|
|
Thus, we can insert the job name in the title as follows:
|
|
<tscreen><verb>
|
|
case $TERM in
|
|
xterm*)
|
|
preexec () {
|
|
print -Pn "\e]0;$*\a"
|
|
}
|
|
;;
|
|
esac
|
|
</verb></tscreen>
|
|
Note: the <tt>preexec()</tt> function appeared around version 3.1.2
|
|
of <tt>zsh</tt>, so you may have to upgrade from an earlier version.
|
|
|
|
|
|
<sect1>Other shells
|
|
|
|
<p>
|
|
This is not easy in other shells which lack an equivalent of the
|
|
<tt>preexec()</tt> function. If anyone has examples please email
|
|
them to the author.
|
|
|
|
|
|
<sect>Appendix: escapes for other terminal types
|
|
|
|
<p>
|
|
Many modern terminals are descended from <tt>xterm</tt> or <tt>rxvt</tt>
|
|
and support the escape sequences we have used so far. Some proprietary
|
|
terminals shipped with various flavours of unix use their own
|
|
escape sequences.
|
|
|
|
|
|
<sect1>IBM <tt>aixterm</tt>
|
|
|
|
<p>
|
|
<tt>aixterm</tt> recognises the <tt>xterm escape</tt> sequences.
|
|
|
|
|
|
<sect1>SGI <tt>wsh</tt>, <tt>xwsh</tt> and <tt>winterm</tt>
|
|
|
|
<p>
|
|
These terminals set <tt>$TERM=iris-ansi</tt> and use the following escapes:
|
|
<itemize>
|
|
<item><tt>ESCP1.y<it>string</it>ESC\ Set window title to <it>string</it></tt>
|
|
<item><tt>ESCP3.y<it>string</it>ESC\ Set icon title to <it>string</it></tt>
|
|
</itemize>
|
|
For the full list of <tt>xwsh</tt> escapes see the <tt>xwsh(1G)</tt> man page.
|
|
|
|
<p>
|
|
The Irix terminals also support the <tt>xterm</tt> escapes to individually
|
|
set window title and icon title, but not the escape to set both.
|
|
|
|
|
|
<sect1>Sun <tt>cmdtool</tt> and <tt>shelltool</tt>
|
|
|
|
<p>
|
|
<tt>cmdtool</tt> and <tt>shelltool</tt> both set <tt>$TERM=sun-cmd</tt>
|
|
and use the following escapes:
|
|
<itemize>
|
|
<item><tt>ESC]l<it>string</it>ESC\ Set window title to <it>string</it></tt>
|
|
<item><tt>ESC]L<it>string</it>ESC\ Set icon title to <it>string</it></tt>
|
|
</itemize>
|
|
These are truly awful programs: use something else.
|
|
|
|
|
|
<sect1>CDE <tt>dtterm</tt>
|
|
|
|
<p>
|
|
<tt>dtterm</tt> sets <tt>$TERM=dtterm</tt>, and appears to recognise both the
|
|
standard <tt>xterm</tt> escape sequences and the Sun <tt>cmdtool</tt>
|
|
sequences (tested on Solaris 2.5.1, Digital Unix 4.0, HP-UX 10.20).
|
|
|
|
|
|
<sect1>HPterm
|
|
|
|
<p>
|
|
<tt>hpterm</tt> sets <tt>$TERM=hpterm</tt> and uses the following escapes:
|
|
<itemize>
|
|
<item><tt>ESC&f0k<it>length</it>D<it>string</it> Set window title to <it>string</it> of length <it>length</it></tt>
|
|
<item><tt>ESC&f-1k<it>length</it>D<it>string</it> Set icon title to <it>string</it> of length <it>length</it></tt>
|
|
</itemize>
|
|
|
|
<p>
|
|
A basic C program to calculate the length and echo the string looks like this:
|
|
<tscreen><verb>
|
|
#include <string.h>
|
|
int main(int argc, char *argv[])
|
|
{
|
|
printf("\033&f0k%dD%s", strlen(argv[1]), argv[1]);
|
|
printf("\033&f-1k%dD%s", strlen(argv[1]), argv[1]);
|
|
return(0);
|
|
}
|
|
</verb></tscreen>
|
|
|
|
<p>
|
|
We may write a similar shell-script, using the <tt>${#string}</tt>
|
|
(<tt>zsh</tt>, <tt>bash</tt>, <tt>ksh</tt>) or <tt>${%string}</tt>
|
|
(<tt>tcsh)</tt> expansion to find the string length. The following
|
|
is for <tt>zsh</tt>:
|
|
<tscreen><verb>
|
|
case $TERM in
|
|
hpterm)
|
|
str="\e]0;%n@%m: %~\a"
|
|
precmd () {print -Pn "\e&f0k${#str}D${str}"}
|
|
precmd () {print -Pn "\e&f-1k${#str}D${str}"}
|
|
;;
|
|
esac
|
|
</verb></tscreen>
|
|
|
|
|
|
|
|
|
|
<sect>Appendix: examples in other languages
|
|
|
|
<p>
|
|
It may be useful to write a small program to print an argument to
|
|
the title using the <tt>xterm</tt> escapes. Some examples are provided
|
|
below.
|
|
|
|
|
|
<sect1>C
|
|
|
|
<p>
|
|
<tscreen><verb>
|
|
#include <stdio.h>
|
|
|
|
int main (int argc, char *argv[]) {
|
|
printf("%c]0;%s%c", '\033', argv[1], '\007');
|
|
return(0);
|
|
}
|
|
</verb></tscreen>
|
|
|
|
|
|
<sect1>Perl
|
|
|
|
<p>
|
|
<tscreen><verb>
|
|
#!/usr/bin/perl
|
|
print "\033]0;@ARGV\007";
|
|
</verb></tscreen>
|
|
|
|
|
|
|
|
<sect>Credits
|
|
|
|
<p>
|
|
Thanks to the following people who have provided advice, errata, and
|
|
examples for this document.
|
|
|
|
<p>
|
|
Paul D. Smith <tt><psmith@BayNetworks.COM></tt> and
|
|
Christophe Martin <tt><cmartin@ipnl.in2p3.fr></tt>
|
|
both pointed out that I had the quotes the wrong way round in the
|
|
<tt>bash</tt> <tt>$PROMPT_COMMAND</tt>. Getting them right
|
|
means variables <it>are</it> expanded dynamically.
|
|
|
|
<p>
|
|
Paul D. Smith <tt><psmith@BayNetworks.COM></tt>
|
|
suggested the use of <tt>\[...\]</tt> in the <tt>bash</tt>
|
|
prompt for embedding non-printing characters.
|
|
|
|
<p>
|
|
Christophe Martin <tt><cmartin@ipnl.in2p3.fr></tt>
|
|
provided the solution for <tt>ksh</tt>.
|
|
|
|
<p>
|
|
Keith Turner <tt><keith@silvaco.com></tt>
|
|
supplied the escape sequences for Sun <tt>cmdtool</tt> and
|
|
<tt>shelltool</tt>.
|
|
|
|
<p>
|
|
Jean-Albert Ferrez <tt><ferrez@dma.epfl.ch></tt>
|
|
pointed out some inconsistencies in the use of "<tt>PWD</tt>"
|
|
and "<tt>$PWD</tt>", and in the use of "<tt>\</tt>" vs "<tt>\\</tt>".
|
|
|
|
<p>
|
|
Bob Ellison <tt><papillo@hpellis.fc.hp.com></tt> and
|
|
Jim Searle <tt><jims@broadcom.com></tt> tested <tt>dtterm</tt>
|
|
on HP-UX.
|
|
|
|
<p>
|
|
Teng-Fong Seak <tt><seak@drfc.cad.cea.fr></tt> suggested the
|
|
<tt>-s</tt> option for <tt>hostname</tt>, use of <tt>`pwd`</tt>, and
|
|
use of <tt>echo</tt> under <tt>csh</tt>.
|
|
|
|
<p>
|
|
Trilia <tt><trilia@nmia.com></tt> suggested examples
|
|
in other languages.
|
|
|
|
<p>
|
|
Brian Miller <tt><bmiller@telstra.com.au></tt> supplied the
|
|
escape sequences and examples for <tt>hpterm</tt>.
|
|
|
|
<p>
|
|
Lenny Mastrototaro <tt><lenny@click3x.com></tt> explained
|
|
the Irix terminals' use of xterm escape sequences.
|
|
|
|
<p>
|
|
Paolo Supino <tt><paolo@init.co.il></tt> suggested the use
|
|
of <tt>\\$</tt> in the <tt>bash</tt> prompt.
|
|
|
|
</article>
|