22

I have the following function:

function pause #for prompted pause until ENTER
{


prompt="$3"
    echo -e -n "\E[36m$3" #color output text cyan
    echo -e -n '\E[0m' #ends colored output
    read -p "$*"  #read keys from user until ENTER.
    clear

}

pause "Press enter to continue..."

However, my function refuses to apply the cyan color to the string I pass into the function.

A similar question was asked here, but it seems that I'm doing everything correctly...

4 Answers 4

34

Try this:

RESTORE='\033[0m'

RED='\033[00;31m'
GREEN='\033[00;32m'
YELLOW='\033[00;33m'
BLUE='\033[00;34m'
PURPLE='\033[00;35m'
CYAN='\033[00;36m'
LIGHTGRAY='\033[00;37m'

LRED='\033[01;31m'
LGREEN='\033[01;32m'
LYELLOW='\033[01;33m'
LBLUE='\033[01;34m'
LPURPLE='\033[01;35m'
LCYAN='\033[01;36m'
WHITE='\033[01;37m'

function test_colors(){

  echo -e "${GREEN}Hello ${CYAN}THERE${RESTORE} Restored here ${LCYAN}HELLO again ${RED} Red socks aren't sexy ${BLUE} neither are blue ${RESTORE} "

}

function pause(){
  echo -en "${CYAN}"
  read -p "[Paused]  $*" FOO_discarded
  echo -en "${RESTORE}"
}


test_colors
pause "Hit any key to continue"

And there's more fun with backgrounds

echo -e "\033[01;41;35mTRY THIS\033[0m"
echo -e "\033[02;44;35mAND THIS\033[0m"
echo -e "\033[03;42;31mAND THIS\033[0m"
echo -e "\033[04;44;33mAND THIS\033[0m"
echo -e "\033[05;44;33mAND THIS\033[0m"
Sign up to request clarification or add additional context in comments.

Comments

15

I've slightly changed your code:

#!/bin/bash

function pause() {
    prompt="$1"
    echo -e -n "\033[1;36m$prompt"
    echo -e -n '\033[0m'
    read
    clear
}

pause "Press enter to continue..."

What I've changed:

  1. You were initializing prompt to $3, when the correct argument was $1
  2. The ANSI sequence was incorrect. See: http://tldp.org/HOWTO/Bash-Prompt-HOWTO/x329.html
  3. The call to read was incorrect, you were passing several arguments do to the use of $*. In this particular case you are discarding the input, so it's not even necessary to save the result of read. I suggest you to read the manpage: http://linux.die.net/man/1/bash to see how to exactly use read. If you pass in several arguments, those arguments will be mapped to variable names that will contain the different fields inputted in the line.

2 Comments

Quoting $* causes the result to be seen as a single string. In the OP's read command, all of the arguments passed to the function were output as the prompt. There's nothing in particular wrong with doing it that way. Your point 1 is essentially correct, however, to be consistent with what the OP seems to be doing, it should be $@ instead of $3 (or $1). There's nothing wrong with the OP's ANSI sequence - it works for me.
This works, but I combined the end sequence into the first line as well, as suggested by Dennis.
14

To save others time:

https://gist.github.com/elucify/c7ccfee9f13b42f11f81

No need to $(echo -ne) all over the place, because the variables defined in the gist above already contain the control characters. The leading/trailing \001 & \002 tell bash that the control characters shouldn't take up space, otherwise using these in a $PS1 will confuse readline.

RESTORE=$(echo -en '\001\033[0m\002')
RED=$(echo -en '\001\033[00;31m\002')
GREEN=$(echo -en '\001\033[00;32m\002')
YELLOW=$(echo -en '\001\033[00;33m\002')
BLUE=$(echo -en '\001\033[00;34m\002')
MAGENTA=$(echo -en '\001\033[00;35m\002')
PURPLE=$(echo -en '\001\033[00;35m\002')
CYAN=$(echo -en '\001\033[00;36m\002')
LIGHTGRAY=$(echo -en '\001\033[00;37m\002')
LRED=$(echo -en '\001\033[01;31m\002')
LGREEN=$(echo -en '\001\033[01;32m\002')
LYELLOW=$(echo -en '\001\033[01;33m\002')
LBLUE=$(echo -en '\001\033[01;34m\002')
LMAGENTA=$(echo -en '\001\033[01;35m\002')
LPURPLE=$(echo -en '\001\033[01;35m\002')
LCYAN=$(echo -en '\001\033[01;36m\002')
WHITE=$(echo -en '\001\033[01;37m\002')

# Test
echo ${RED}RED${GREEN}GREEN${YELLOW}YELLOW${BLUE}BLUE${PURPLE}PURPLE${CYAN}CYAN${WHITE}WHITE${RESTORE} 

Comments

2

The problem is that this line:

echo -e -n "\E[36m$3" #color output text cyan

should be:

echo -e -n "\E[36m" #color output text cyan

and you should eliminate this line since you're not using the variable:

prompt="$3"

Also the end sequence should be moved into the read prompt. In fact, the begin sequence can be, too.

The result:

function pause #for prompted pause until ENTER
{
    read -p $'\E[36m'"$*"$'\E[0m'  #read keys from user until ENTER.
    clear
}

pause "Press enter to continue..."

The colors could be put into variables:

cyan=$'\E[36m'
reset=$'\E[0m'
read -p "$cyan$*$reset"

The $'' causes the escape sequence to be interpreted just like echo -e.

2 Comments

The whole point is to echo "Press enter to continue" in cyan, and then wait for enter to be pressed. This doesn't seem to work...
@derp: You're right, the escape codes don't get interpreted. See my edit.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.