Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

add color to command output

4 views
Skip to first unread message

peng...@gmail.com

unread,
Nov 18, 2009, 11:04:00 PM11/18/09
to
grep --color=auto

The above command add color to the output. I'm wondering if there is a
general way to apply color to certain strings in the output of any
command.

Seebs

unread,
Nov 18, 2009, 11:18:18 PM11/18/09
to

No, and indeed, that doesn't even work on all systems -- it's a local
feature.

Color's not really portable in shell, since the shell essentially predates
color being available. :)

-s
--
Copyright 2009, all wrongs reversed. Peter Seebach / usenet...@seebs.net
http://www.seebs.net/log/ <-- lawsuits, religion, and funny pictures
http://en.wikipedia.org/wiki/Fair_Game_(Scientology) <-- get educated!

Chris F.A. Johnson

unread,
Nov 19, 2009, 12:07:22 AM11/19/09
to

There is no foolproof method, but almost all terminals these days
follow the ISO 6429 standard (also known as ECMA-48, and formerly
known as ANSI X3.64), and you can use those codes.

## colours
black=0
red=1
green=2
yellow=3
blue=4
magenta=5
cyan=6
white=7

fg=3 ## foreground prefix
bg=4 ## background prefix

printf "\033[$fg$yellow;$bg${black}m%s\033[m\n" "Yellow on black"

--
Chris F.A. Johnson, author <http://shell.cfajohnson,com/>
===================================================================
Shell Scripting Recipes: A Problem-Solution Approach (2005, Apress)
Pro Bash Programming: Scripting the GNU/Linux Shell (2009, Apress)
===== My code in this post, if any, assumes the POSIX locale =====
===== and is released under the GNU General Public Licence =====

Gary Johnson

unread,
Nov 19, 2009, 3:04:54 PM11/19/09
to

Piping the command into "grep --color=auto -C9999 somestring" will work
in many cases.

Some commands format their output differently when it's redirected to a
pipe, however. To use the above to color the output of ls, for example,
you'd need to use "ls -C" to preserve the columnar output.

--
Gary Johnson

Ivan Shmakov

unread,
Nov 19, 2009, 3:56:31 PM11/19/09
to
>>>>> Chris F A Johnson <cfajo...@gmail.com> writes:
>>>>> On 2009-11-19, Peng...@gmail.com wrote:

>> grep --color=auto

>> The above command add color to the output. I'm wondering if there is
>> a general way to apply color to certain strings in the output of any
>> command.

> There is no foolproof method, but almost all terminals these days
> follow the ISO 6429 standard (also known as ECMA-48, and formerly
> known as ANSI X3.64), and you can use those codes.

Ncurses comes with tput(1) bundled. I'm not sure how widely it
is available.

[...]

> printf "\033[$fg$yellow;$bg${black}m%s\033[m\n" "Yellow on black"

#!/bin/bash
clear
cols=$(tput cols)
rows=$(tput lines)
while sleep .1s ; do
printf 'setaf %d\ncup %d %d\n' \
$((1 + $RANDOM % 15)) \
$((1 + $RANDOM % $rows)) \
$((1 + $RANDOM % $cols)) \
| tput -S
printf '*\b'
done

SEE ALSO

tput(1), terminfo(5)

--
FSF associate member #7257

Ivan Shmakov

unread,
Nov 19, 2009, 4:41:52 PM11/19/09
to
>>>>> "IS" == Ivan Shmakov <iv...@main.uusia.org> writes:

[...]

IS> Ncurses comes with tput(1) bundled. I'm not sure how widely it is
IS> available.

[...]

... And tput(1), together with Bash arrays, allows, e. g., the
following display hack to be implemented. (I wished to code it
for a while...)

#!/bin/bash

cleanup () {
trap EXIT
reset
}

trap cleanup EXIT

set_place () {
local i="$1" cols rows
if [ -z "${row[$i]}" -o -z "${col[$i]}" ] ; then
cols=$(tput cols)
rows=$(tput lines)
row[$i]=$((1 + $RANDOM % ($rows - 1)))
col[$i]=$((1 + $RANDOM % ($cols - 1)))
fi
## .
tput cup "${row[$i]}" "${col[$i]}"
}

set_color () {
local i="$1"
if [ -z "${color[$i]}" ] ; then
color[$i]=$((1 + $RANDOM % 15))
fi
## .
tput setaf "${color[$i]}"
}

new_char_p () {
local i="$1" new
if [ -n "${small[$i]}" ] ; then
case "${ttl[$i]}" in
(0) new=' ' ;;
(1) new='.' ;;
(2) new='*' ;;
(*) new='.' ;;
esac
else
case "${ttl[$i]}" in
([0]) new=' ' ;;
([1-2]) new=. ;;
([3-5]) new=o ;;
([6-7]) new=O ;;
([8-9]) new=o ;;
(*) new=. ;;
esac
fi
## .
test "$new" != "${char[$i]}" \
&& char[$i]=$new
}

put_char () {
local i="$1"
printf %s\\b "${char[$i]}"
}

max=17

update_create_new () {
local i
i=0
while [ "$i" -lt "$max" ] ; do
i=$((1 + $i))
if [ -n "${ttl[$i]}" ] ; then
continue
fi
ttl[$i]=$((13 + $RANDOM % 71))
if [ $(($RANDOM % 7)) -lt 5 ] ; then
small[$i]=1
fi
done
}

update_evolve () {
local i
i=0
while [ "$i" -lt "$max" ] ; do
i=$((1 + $i))
if [ -z "${ttl[$i]}" ] ; then
continue
fi
ttl[$i]=$((-1 + ${ttl[$i]}))
if new_char_p "$i" ; then
set_place "$i"
set_color "$i"
put_char "$i"
fi
done
}

update_remove_old () {
local i
i=0
while [ "$i" -lt "$max" ] ; do
i=$((1 + $i))
if [ -z "${ttl[$i]}" ] ; then
continue
fi
if [ "${ttl[$i]}" -le 0 ] ; then
ttl[$i]=
row[$i]=
col[$i]=
color[$i]=
char[$i]=
small[$i]=
fi
done
}

update () {
update_create_new
update_evolve
update_remove_old
}

tput civis
clear
while sleep .1s ; do
update
done

Chris F.A. Johnson

unread,
Nov 19, 2009, 5:06:18 PM11/19/09
to
On 2009-11-19, Ivan Shmakov wrote:
>>>>>> "IS" == Ivan Shmakov <iv...@main.uusia.org> writes:
>
> [...]
>
> IS> Ncurses comes with tput(1) bundled. I'm not sure how widely it is
> IS> available.
>
> [...]
>
> ... And tput(1), together with Bash arrays, allows, e. g., the
> following display hack to be implemented. (I wished to code it
> for a while...)

It doesn't work everywhere. On some systems, the following does
nothing:

> tput setaf "${color[$i]}"

--

Thomas Dickey

unread,
Nov 19, 2009, 8:17:54 PM11/19/09
to
On Nov 19, 5:06 pm, "Chris F.A. Johnson" <cfajohn...@gmail.com> wrote:
> On 2009-11-19, Ivan Shmakov wrote:
...
> > IS>Ncursescomes with tput(1) bundled.  I'm not sure how widely it is

> > IS> available.
...
> >    ... And tput(1), together with Bash arrays, allows, e. g., the
> >    following display hack to be implemented.  (I wished to code it
> >    for a while...)
>
>     It doesn't work everywhere. On some systems, the following does
>     nothing:
>
> >     tput setaf "${color[$i]}"

er - you're responding to his comment in a misleading manner.

It's unlikely that he's using bash on a system where ncurses
and tput wouldn't work as suggested, unless of course he uses
a tput that doesn't come bundled with ncurses.

awai

--
Thomas E. Dickey <dic...@invisible-island.net>
http://invisible-island.net
ftp://invisible-island.net

Chris F.A. Johnson

unread,
Nov 19, 2009, 8:46:14 PM11/19/09
to
On 2009-11-20, Thomas Dickey wrote:

> On Nov 19, 5:06?pm, "Chris F.A. Johnson" <cfajohn...@gmail.com> wrote:
>> On 2009-11-19, Ivan Shmakov wrote:
> ...
>> > IS>Ncursescomes with tput(1) bundled. ?I'm not sure how widely it is
>> > IS> available.
> ...
>> > ? ?... And tput(1), together with Bash arrays, allows, e. g., the
>> > ? ?following display hack to be implemented. ?(I wished to code it
>> > ? ?for a while...)
>>
>> ? ? It doesn't work everywhere. On some systems, the following does
>> ? ? nothing:
>>
>> > ? ? tput setaf "${color[$i]}"

>
> er - you're responding to his comment in a misleading manner.
>
> It's unlikely that he's using bash on a system where ncurses
> and tput wouldn't work as suggested, unless of course he uses
> a tput that doesn't come bundled with ncurses.

I use bash on at least one system where it doesn't work. I have no
idea what, if anything, it was bundled with. I've used many more
such systems in the past.

While there are a few terminals (or emulators) that do not conform
for the most part to the ISO 6429 standard, the vast majority do.
If a terminal doesn't conform, that's a good-enough reason not to
use it. I have found it far closer to universal than either
version of tput.

Ivan Shmakov

unread,
Nov 19, 2009, 10:32:50 PM11/19/09
to
>>>>> "CFAJ" == Chris F A Johnson <cfajo...@gmail.com> writes:
>>>>> "IS" Ivan Shmakov wrote:

IS> Ncurses comes with tput(1) bundled. I'm not sure how widely it is
IS> available.

[...]

CFAJ> It doesn't work everywhere. On some systems, the following does
CFAJ> nothing:

> tput setaf "${color[$i]}"

I've meant ``a fully-working tput(1)'' by ``it'' specifically in
the sentence above.

My Shell experience was limited mostly to GNU/Linux systems, and
would /it/ fail on one under my rule, I'd immediately suspect a
problem with the terminfo(5) database to be reported to the
developers in charge.

Chris F.A. Johnson

unread,
Nov 19, 2009, 10:47:22 PM11/19/09
to

The POSIX standard only requires that tput support three operands,
clear, init and reset. All else is implementation defined, and many
things are not included in all implementations, and therefore not
portable.

Ivan Shmakov

unread,
Nov 20, 2009, 7:16:46 AM11/20/09
to
>>>>> "CFAJ" == Chris F A Johnson <cfajo...@gmail.com> writes:
>>>>> "IS" == Ivan Shmakov wrote:
>>>>> "CFAJ" == Chris F A Johnson <cfajo...@gmail.com> writes:
>>>>> "IS" Ivan Shmakov wrote:

[Whoops, got it sent personally. Sorry for that.]

IS> Ncurses comes with tput(1) bundled. I'm not sure how widely it is
IS> available.

CFAJ> It doesn't work everywhere. On some systems, the following does
CFAJ> nothing:

>>> tput setaf "${color[$i]}"

IS> I've meant ``a fully-working tput(1)'' by ``it'' specifically in
IS> the sentence above.

CFAJ> The POSIX standard only requires that tput support three
CFAJ> operands, clear, init and reset.

Well, then it should've read ``a fully-working, Ncurses-based
tput(1)'' instead, right? (And I'm really puzzled about how I'd
call the tput(1) I'm accustomed to.)

CFAJ> All else is implementation defined, and many things are not
CFAJ> included in all implementations, and therefore not portable.

Given that animating a starfield is such a toy task, the
requirement to install Ncurses, or, why, even a Debian GNU/Linux
with its ``standard'' and ``GNOME'' tasks under, say, QEMU, for
it to work, doesn't seem to me entirely unreasonable.

Fortunately, the portability is rarely an end by itself.

IS> My Shell experience was limited mostly to GNU/Linux systems, and
IS> would /it/ fail on one under my rule, I'd immediately suspect a
IS> problem with the terminfo(5) database to be reported to the
IS> developers in charge.

0 new messages