Beefy Boxes and Bandwidth Generously Provided by pair Networks
P is for Practical
 
PerlMonks  

Hex to array conversion

by Anonymous Monk
on Oct 08, 2007 at 13:21 UTC ( [id://643453]=perlquestion: print w/replies, xml ) Need Help??

Anonymous Monk has asked for the wisdom of the Perl Monks concerning the following question:

Monks,
I am using GD to create images. I'm wondering how I can convert a hex RGB string (i.e. "#ff00ff") into the corresponding triplet (in this example, "255,0,255"). Any help is appreciated!

Replies are listed 'Best First'.
Re: Hex to array conversion
by ChOas (Curate) on Oct 08, 2007 at 13:49 UTC
    Works too:
    my @rgb = map {hex($_) } unpack 'xa2a2a2', "#FF00FF"; print "(",join(',',@rgb),")\n";

    GreetZ!,
      ChOas

    print "profeth still\n" if /bird|devil/;
      While we're busy doing silly pack/unpack strings:
      $str = '#FE00FD'; $str =~ tr/0-9a-fA-F//cd; # remove non-hex characters my @rgb = unpack 'C*', pack 'H*', $str; # pack hex as 3 bytes, unpack + into list of 3 character codes $" = ","; $\ = "\n"; print "(@rgb)";
      Result:
      (254,0,253)
Re: Hex to array conversion
by liverpole (Monsignor) on Oct 08, 2007 at 13:29 UTC
    You could do it like this:
    #!/usr/bin/perl -w use strict; use warnings; # Main program try_rgb("#ff00ff"); # Subroutines sub try_rgb { my ($rgb) = @_; printf "$rgb => (%d, %d, %d)\n", rgb_to_decimal($rgb); } sub rgb_to_decimal { my ($value) = @_; if ($value =~ /^#(..)(..)(..)/) { my ($r, $g, $b) = ($1, $2, $3); return (hex($r), hex($g), hex($b)); } return 0; }

    Output is:

    #ff00ff => (255, 0, 255)

    s''(q.S:$/9=(T1';s;(..)(..);$..=substr+crypt($1,$2),2,3;eg;print$..$/
Re: Hex to array conversion
by amarquis (Curate) on Oct 08, 2007 at 13:28 UTC

    Looking quickly at CPAN, it seems that you want Number::RGB. Looks like you can create an object using the hex notation and then grab the decimal RGB components.

    Edit: If you'd prefer the do it yourself version, the function you want is hex. You can pop off each two-hex digit pair and then say $red = hex $first_match, etc.

    Edit^2: Apparently Liverpole can code the DiY solution in the time it takes me to think up the DiY solution, hehe.

Re: Hex to array conversion
by dwm042 (Priest) on Oct 08, 2007 at 13:37 UTC
    This little program can do the conversion:

    #!/usr/bin/perl use warnings; use strict; my $rgb = shift; $rgb = oct($rgb); my $first = ( $rgb & 0xff0000 ) >> 16; my $second = ( $rgb & 0x00ff00 ) >> 8; my $third = ( $rgb & 0x0000ff ); print " ( $first , $second , $third )";
    And the output is:

    C:\Code>perl rgbshift.pl 0xff00ff ( 255 , 0 , 255 )
Re: Hex to array conversion
by mwah (Hermit) on Oct 08, 2007 at 14:32 UTC
    AnonymousI'm wondering how I can convert a hex RGB string (i.e. "#ff00ff") into the corresponding triplet

    This sounds not too complicated. In addition to the
    unpack solutions already posted, you could make it short
    with regexes:
    ... my $RGB = '#FF00FF'; @triplet = map hex, $RGB =~ /\w\w/g; ...
    or even
    ... my $RGB = '#FF00FF'; () = $RGB =~ /(\w\w)(?{push @triplet, hex $^N})/g; ...
    depending on your mileage ;-)

    Regards

    mwa
Re: Hex to array conversion
by johngg (Canon) on Oct 08, 2007 at 14:58 UTC
    I came across a warning I hadn't seen before when initialising an array of RGBs when looking at this.

    my @rgbVals = qw{ #ff00ff #2e7fee };

    warned with

    Possible attempt to put comments in qw() list ...

    The category I found to switch the warning off was "syntax" which potentially covers a lot of ground; "comment" or "comments" was not recognised. Here's the code

    use strict; use warnings; my @rgbVals = do { no warnings q{syntax}; qw{ #ff00ff #2e7fee }; }; print map { qq{@{ [ join q{,}, map { hex } m{^.(..)(..)(..)} ] }\n} } @rgbVals;

    I'd be interested in knowing if there was some finer-grained warnings category covering this.

    Cheers,

    JohnGG

    Update: Thanks to toolic, TGI and FunkyMonk for the responses. I did try to find out in warnings but no luck there. I found "syntax" in a table in the Camel book (3rd Edn. pp 863) but didn't see "qw".

      The category is qw.
      use warnings; @foo = qw( #foo bar,baz ); # Throw a warning; { no warnings 'qw'; @foo = qw( #foo bar,baz ); # Don't throw a warning; }


      TGI says moo

      diagnostics will tell you which category a warning belongs to:
      Possible attempt to put comments in qw() list at /temp/pm line 21 (#1) (W qw) qw() lists contain items separated by whitespace; as with l +iteral ...

      The last line quoted above starts (W qw) telling you that this warning belongs to the qw category.

      That is a great question, and I wish I knew the answer.

      You could always do it the hard way:

      my @rgbVals = ('#ff00ff', '#2e7fee');
      The disadvantage of this is that you lose the capability of the qw operator. The advantage is that you do not have to turn off warnings and worry about what you might be missing.
Re: Hex to array conversion
by gam3 (Curate) on Oct 08, 2007 at 14:32 UTC
    similar to the unpack example, but with error checking.
    use strict; sub hex2rgb { my $hex = shift; if (my @data = ($hex =~ /\#((?:[0-9a-fA-F]){2})((?:[0-9a-fA-F]){2} +)((?:[0-9a-fA-F]){2})/)) { return join(',', map({ hex($_); } @data)); } else { die "Bad hex: ", $hex; } } print hex2rgb("#ff00ff"), "\n"; print hex2rgb("#fx00ff"), "\n";
    -- gam3
    A picture is worth a thousand words, but takes 200K.
Re: Hex to array conversion
by Anonymous Monk on Oct 08, 2007 at 23:07 UTC
    m/#([a-fA-F0-9]){3}(?{push @values, [map{hex} ($1,$2,$3)]})/g;
Re: Hex to array conversion
by Anonymous Monk on Oct 08, 2007 at 23:03 UTC
    m/#([a-fA-F0-9]){3}(?{push @values, [$1,$2,$3]})/g;

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: perlquestion [id://643453]
Approved by Corion
Front-paged by Corion
help
Chatterbox?
and the web crawler heard nothing...

How do I use this?Last hourOther CB clients
Other Users?
Others musing on the Monastery: (1)
As of 2024-04-19 18:30 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found