[SOLVED] Easier way to color text in Perl like BASH?
ProgrammingThis forum is for all programming questions.
The question does not have to be directly related to Linux and any language is fair game.
Notices
Welcome to LinuxQuestions.org, a friendly and active Linux Community.
You are currently viewing LQ as a guest. By joining our community you will have the ability to post topics, receive our newsletter, use the advanced search, subscribe to threads and access many other special features. Registration is quick, simple and absolutely free. Join our community today!
Note that registered members see fewer ads, and ContentLink is completely disabled once you log in.
If you have any problems with the registration process or your account login, please contact us. If you need to reset your password, click here.
Having a problem logging in? Please visit this page to clear all LQ-related cookies.
Get a virtual cloud desktop with the Linux distro that you want in less than five minutes with Shells! With over 10 pre-installed distros to choose from, the worry-free installation life is here! Whether you are a digital nomad or just looking for flexibility, Shells can put your Linux machine on the device that you want to use.
Exclusive for LQ members, get up to 45% off per month. Click here for more info.
I've been trying to figure out a way to more easily color text in Perl like I do on Bash on a Linux box. In bash, what I'll do is set color variables up to equal the escape sequence, then echo out with escape seqeunces to print it exactly how I want it. Typically I'll want a character or a word in a different color, not the whole line. For example
Code:
echo -n -e "My face is turning ${RED}red${UNCOLOR} like a lobster."
In Perl with the term::ANSIColor module, it seems to just do a line. Am I being dense? Is there a way that I can do it like I do it in BASH that's fairly easy to read after the fact? Any suggestions?
I've been trying to figure out a way to more easily color text in Perl like I do on Bash on a Linux box. In bash, what I'll do is set color variables up to equal the escape sequence, then echo out with escape seqeunces to print it exactly how I want it. Typically I'll want a character or a word in a different color, not the whole line. For example
Code:
echo -n -e "My face is turning ${RED}red${UNCOLOR} like a lobster."
In Perl with the term::ANSIColor module, it seems to just do a line. Am I being dense? Is there a way that I can do it like I do it in BASH that's fairly easy to read after the fact? Any suggestions?
Thanks for the suggestion. This will work, but looks very messy. For example -
Code:
#!/usr/bin/perl -w
use Term::ANSIColor qw(:constants);
$Term::ANSIColor::AUTORESET = 1;
print "Do you wish to operate in ";
print BOLD GREEN "(s)";
print "cript mode or in ";
print BOLD RED "(l)";
print "ive mode ? \n";
That's very hard to read from a maintainability standpoint. In BASH, it be
Code:
echo -ne "Do you wish to operate in ${GREEN}(s)${UNCOLOR}ript or ${RED}(l)${UNCOLOR}ive mode ? \n"
That to me is more readable and what I'm trying to emulate, if possible.
Thanks for the suggestion. This will work, but looks very messy. For example -
Code:
#!/usr/bin/perl -w
use Term::ANSIColor qw(:constants);
$Term::ANSIColor::AUTORESET = 1;
print "Do you wish to operate in ";
print BOLD GREEN "(s)";
print "cript mode or in ";
print BOLD RED "(l)";
print "ive mode ? \n";
That's very hard to read from a maintainability standpoint. In BASH, it be
Code:
echo -ne "Do you wish to operate in ${GREEN}(s)${UNCOLOR}ript or ${RED}(l)${UNCOLOR}ive mode ? \n"
That to me is more readable and what I'm trying to emulate, if possible.
Devon
You can have a number of 'print' statements on in one line.
You can invent your own simplistic color management language, like
Code:
"The next hello will be red __RED__hello, but goodbye to come will be __BLUE__goodbye"
, trivially parse it and convert into what Term::ANSIColor understands.
You can probably even overload 'print' in order to do the above parsing.
Or you can use a subset of standard language, say, HTML (it allows coloration), any standard HTML parser and, again, convert the parser output into what Term::ANSIColor understands.
I went a different route and the problem is solved, but it produced a different error. Here's how I did it -
I made a subroutine that takes parameters in pairs; the color you want printed and the statement you want printed. The call of the subroutine makes it read very close to the way it did in BASH for me.
Code:
&colorprint("NO","The lobster was ","RED","red");
Here's the problem; The statement inside the subroutine of
Code:
print $COLOR "$STATEMENT";
Makes it thinks $COLOR is a filehandle, and gives an error stating that RED is not a file handle. However -
Code:
print RED "$STATEMENT";
works fine, and prints as expected. I did an ugly work around of lots of elsif's searching for all the possible color names, but I'd prefer for it to evaluate $COLOR and consider it a color selection instead of a file handle. My guess is this is a presidence problem of how it evaluates the statement from right to left, but I have no idea how to fix it? I'm way too new to perl still.
Why not just create your own print function which translates embedded color tags to escape sequences, using regular expression substitutions, and ultimately prints the converted string?
Untested:
Code:
#! /bin/perl -w
use strict;
sub colorPrint($);
colorPrint( "This is \${red}red\${unred}\n" );
colorPrint( "This is \${green}green\${ungreen}\n" );
colorPrint( "This is \${blue}blue\${unblue}\n" );
exit 0;
sub colorPrint($){
# Escape sequences not real, just invented for demonstration
my %colorTags = (
'${red}' => "esc[#",
'${unred}' => "esc]#",
'${green}' => "esc[\$",
'${ungreen}'=> "esc]\$",
'${blue}' => "esc[%",
'${unblue}'=> "esc]%"
);
my $stringToPrint = shift;
foreach my $color ( keys %colorTags ){
my $escapeSeq = $colorTags{ $color };
$color = quotemeta( $color );
$stringToPrint =~ s/$color/$escapeSeq/g;
}
print $stringToPrint;
}
Thank you for the excellent suggestion, rod. I had tried something similiar to your suggestion, yet I could not figure out the escape sequences to put in place to make the colors work. All's it did was print the 'garbage' characters to the screen. With the TERM:ANSIcolors module there, it kind of lead me to believe that it didn't exist, and that printf didn't have the ability to interpret escape seqeunces like BASH does with a %b or echo does inline with -e to process escape codes. If I could get just "print $COLOR "$STATEMENT" to process $COLOR as a color name and not see it as a file handle, I'd be happy.
I got it gentlemen. I should have just looked at the TERM:ANSIColor module in the first place. The fomulation of the escape code I had earlier was my problem. I now have -
Code:
$RED="\e[31m";
$GREEN="\e[32m";
etc. and doing a
Code:
print "My lobster is ${RED}red${NO} in color.";
works as I want it to. BASH is different. It uses -
LinuxQuestions.org is looking for people interested in writing
Editorials, Articles, Reviews, and more. If you'd like to contribute
content, let us know.