How many colours are supported and how to change the foreground and background colour depends on the terminal.
The terminfo
database is usually there to help you come up with the right sequence.
Most colour terminals support the ANSI colour escape sequences to change the foreground and background colours 0 to 7.
That's:
- set foreground colour $n:
printf "\33[3${n}m"
- set background colour $n:
printf "\33[4${n}m"
Some (rare) terminals (like emu
) use different sequences for those ANSI colours.
Some (rare) terminals like the QNX console have different escape sequences and different colours.
Some (rare) work with colour pairs. You define a colour pair for background and foreground, and then have an escape sequence to select the pair you want to use.
Now, xterm and most modern Free Software terminal emulators extend the basic 8 ANSI colours, to up to 16 (where 8 to 15 are brighter versions of the ANSI colours 0 to 7), 88 or 256 colours for some.
Some terminals like rxvt
only support 8 colours, but use the brighter colours if bold is also on (for the foreground) or blink (for the background). \033[34;1m
will give a brighter blue than \033[34m
.
The most portable way to use colours is to use the terminfo database.
It can be via the tput
command. tcsh
and zsh
also have an echoti
builtin for that.
Provided the terminfo database is correct and the value of $TERM
correctly reflects the terminal you're using:
tput colors
Will give you the number of colours supported by your terminal.
Nowadays, except for the rare exceptions mentionned above, you can assume that your terminal will support ANSI colours. The terminfo capabilities for the ANSI background and foreground colours are setab
and setaf
. If the terminal supports more than 8 colours, you can still use that capability to query them.
tput setaf 233
If the terminal supports 256 colors should output the correct escape sequence for that colour 233.
For xterm
, setaf
outputs \033[30m..\033[37m
for colours 0 to 7, \033[90m..\033[97m
for colours 8 to 15 and \033[38;5;16m..\033[38;5;255m
for colours 16 to 255.
\033[38;5;0m..\033[38;5;15m
will also work but are 4 bytes longer than their more portable equivalent for colours 0 to 15.
So, to test all the colours supported by the terminal. If it supports ansi colours:
i=0; n=$(tput colors); while [ "$i" -lt "$n" ]; do
tput setaf "$i"; printf %04d "$i"
i=$((i + 1))
done
If it supports other colours:
i=0; n=$(tput colors); while [ "$i" -lt "$n" ]; do
tput setf "$i"; printf %04d "$i"
i=$((i + 1))
done
If it works with colour pairs (like hpterm-color):
i=0; n=$(tput pairs); while [ "$i" -lt "$n" ]; do
tput scp "$i"; printf %04d "$i"
i=$((i + 1))
done
Now, to redefine a colour or colour-pair, that also varies between terminals.
There's a initc
terminfo capability to redefine a given colour for those terminals that can do it. And initp
to redefine a pair.
For instance to redefine the colour 1 as bright white:
tput initc 1 1000 1000 1000
With xterm
, that sends the sequence: \033]4;1;rgb:FF/FF/FF\033\
.
To redefine the colour pair 1 to white on black on terminals that work with pairs:
tput initp 1 1000 1000 1000 0 0 0
echo $TERM
for starters...xterm-256color
gnome-terminal