duality_
duality_

Reputation: 18756

How to reset cursor color in bash

This happens to me on Linux, not on a Mac. When I use tput setaf and then tput sgr0, the cursor still remains in the previously selected colour, until I press return again. I can reset it the same way by just doing echo '', but that isn't ideal as it creates a new line for me. Using printf didn't work either.

How can I reset the cursor color in the shell?

Color change fails Echo kind of helps

Upvotes: 6

Views: 5832

Answers (4)

SpikePy
SpikePy

Reputation: 101

Just use the reset command:

reset

"The reset command under a BSD/Linux/UNIX operating system is used to restore a console to a normal state. This is useful after a program dies leaving a terminal in an abnormal state."

Upvotes: 4

Unai Vivi
Unai Vivi

Reputation: 3101

Short answer

echo -n -e '\e[?0c'

Long answer

As of today, the current version of agetty (contained in util-linux 2.27.1 [util-linux is the linux package providing most core commands, like login, su, mount, more, kill - to name a few] - and you should have it if your linux kernel version is >=4.4) has a different behavior than described in the yet-to-be-updated kernel.org documentation (Software cursor for VGA).

Consider

echo -n -e '\e[?byte1;byte2;byte3c'

byte1:

+---------------+---------------+
|  high nibble  |   low nibble  |
+---+-----------+-----------+---+
|msb|           |           |lsb|
+---+---+---+---+---+---+---+---+
| 7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 |
+---+---+---+---+---+---+---+---+
                  |   |   |   |
                  |   |   |   +-+
                  |   |   |     |   These bits specify the 8
                  |   |   +-----+-> possible blinking HW carets
                  |   |         |   
                  |   +---------+
                  |
                  +---------------> When set, this bit enables SW
                                    caret instead of HW caret

byte2 (SW caret):

                +-----------------> A pretty useless mask applied
                |                   to bits in byte3
+---------------+---------------+
|  high nibble  |   low nibble  |
+---+-----------+-----------+---+
|msb|           |           |lsb|
+---+---+---+---+---+---+---+---+
| 7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 |
+---+---+---+---+---+---+---+---+

byte3 (SW caret):

+---------------+---------------+
|  high nibble  |   low nibble  |
+---+-----------+-----------+---+
|msb|           |           |lsb|
+---+---+---+---+---+---+---+---+
| 7 | 6 | 5 | 4 | 3 | 2 | 1 | 0 |
+---+---+---+---+---+---+---+---+
  |   |   |   |
  |   |   |   +-------------------> Highlighting
  |   |   |
  |   |   +---------------------+
  |   |                         |
  |   +-------------------------+-> Color
  |                             |
  +-----------------------------+

Highlighting: highligths the character beneath the caret (e.g. changing it to white [true shiny white] instead of dark white [the light gray that is commonly the default for TTYs]).

Color: the color of the caret. Note that, compared to the usual order of ANSI color codes we all know and love, bits are reversed, so -for this triplet- the 7th is the Lsb while the 5th is the Msb.

So, while in the 70s ANSI defined the following color codes, setting a de-facto standard adopted universally for TTYs, miscellaneous linux terminals, consoles, and whatnot

000 (0) black
001 (1) red
010 (2) green
011 (3) yellow or dark yellow
100 (4) blue or dark blue
101 (5) magenta, purple or violet
110 (6) cyan or light blue
111 (7) white or dark white (light gray)

in this case we have the opposite

000 (0) black
100 (4) red
010 (2) green
110 (6) yellow or dark yellow
001 (1) blue or dark blue
101 (5) magenta, purple or violet
011 (3) cyan or light blue
111 (7) white or dark white (light gray)

(Octal value parenthesized)

So, here comes the list:

#Hardware carets (blinking and [dark ]white)
echo -n -e '\e[?0c' #default caret
echo -n -e '\e[?1c' #invisible caret
echo -n -e '\e[?2c' #underscore caret
echo -n -e '\e[?3c' #thicker underscore caret
echo -n -e '\e[?4c' #smaller block caret
echo -n -e '\e[?5c' #small block caret
echo -n -e '\e[?6c' #big block caret
echo -n -e '\e[?7c' #biggest block caret
#On my Linux machine, both 6 and 7 are the big rectangular full-size block caret

#Software carets (non-blinking and colored)
echo -n -e '\e[?16;0;0c'  #00001000 0 00000000 black (thus invisible on black background)
echo -n -e '\e[?16;0;128c'#00001000 0 10000000 red
echo -n -e '\e[?16;0;64c' #00001000 0 01000000 green
echo -n -e '\e[?16;0;192c'#00001000 0 11000000 yellow
echo -n -e '\e[?16;0;32c' #00001000 0 00100000 blue
echo -n -e '\e[?16;0;160c'#00001000 0 10100000 magenta
echo -n -e '\e[?16;0;96c' #00001000 0 01100000 cyan
echo -n -e '\e[?16;0;224c'#00001000 0 11100000 dim white
echo -n -e '\e[?16;0;16c' #00001000 0 00010000 black     + highlighting
echo -n -e '\e[?16;0;144c'#00001000 0 10010000 red       + highlighting
echo -n -e '\e[?16;0;80c' #00001000 0 01010000 green     + highlighting
echo -n -e '\e[?16;0;208c'#00001000 0 11010000 yellow    + highlighting
echo -n -e '\e[?16;0;48c' #00001000 0 00110000 blue      + highlighting
echo -n -e '\e[?16;0;176c'#00001000 0 10110000 magenta   + highlighting
echo -n -e '\e[?16;0;112c'#00001000 0 01110000 cyan      + highlighting
echo -n -e '\e[?16;0;240c'#00001000 0 11110000 dim white + highlighting

Upvotes: 5

Thomas Dickey
Thomas Dickey

Reputation: 54495

Whether you can, and how you can change the text-cursor color depends entirely upon the terminal emulator. There is no terminfo/termcap capability which corresponds to this feature.

xterm is one of (a few) which can do this. It is documented as one of the dynamic color features, e.g., from XTerm Control Sequences

OSC Ps ; Pt BEL

Set Text Parameters. For colors and font, if Pt is a "?", the control sequence elicits a response which consists of the control sequence which would set the corresponding value. The dtterm control sequences allow you to determine the icon name and window title.

Ps = 1 2 -> Change text cursor color to Pt.

The xtermset program know hows to set this and similar features. If there is no cursor-color specified, xterm attempts to keep the cursor constantly visible by using the reverse of the cell's foreground and background colors.

Aside from rxvt-unicode (which documents the feature under XTerm Operating System Commands) some other terminal emulators may implement the same thing. However, the usual "MAC" programs (Terminal.app and Iterm2) do not support these control sequences. Iterm2 has it marked as "future release".

Using xtermset, you could set the cursor color to green using

xtermset -cr green

It actually does not do "much": xterm accepts a control sequence which could be put in a script as

printf '\033]12;green\007'

where '033] is OSC (the operating system control prefix) and \007 is one of the suffixes accepted for ending the sequence. A string terminator \033\\ in the printf (escape backslash) would be preferred since it is standard in ECMA-48.

Upvotes: 1

Andrew
Andrew

Reputation: 986

tput sgr0

restore the settings to default colour - and it works fine for me (I don't need another echo).

To solve your situation I suggest to use this code:

tput setaf 2 && echo -en 'Name: ' && tput sgr0 && echo ""

Upvotes: 6

Related Questions