Beefy Boxes and Bandwidth Generously Provided by pair Networks
Do you know where your variables are?
 
PerlMonks  

Drop-down list Option Value

by Happyjack (Novice)
on Feb 02, 2003 at 06:20 UTC ( [id://231950]=perlquestion: print w/replies, xml ) Need Help??

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

I'm a true novice in CGI so please bare with me.

I'm trying to customize my very first script for a simple form. Without getting into all the form objects, I am having some difficulty with only one.

I have a list box containing various animals. In the form, I have values such as:
<option value="fish1.jpg">Fresh water fish</option>

The problem is that I need to display "Fresh water fish" when I execute the script, but what I get is the value property "fish1.jpg". The line of script is:

I Love $in{'pet'} where 'pet' is the <Select name> for the list.

How can I change the script to use the list item description instead of the value attribute?

Thanks so much for the help!

Replies are listed 'Best First'.
Re: Drop-down list Option Value
by thezip (Vicar) on Feb 02, 2003 at 07:10 UTC
    Is this helpful?
    #!/perl/bin/perl use strict; use warnings; use Data::Dumper; # Fish configurator my %fish = ( "Fresh water fish" => "fish1.jpg", "Salt water fish" => "fish2.jpg", "One fish" => "seuss1.jpg", "Two fish" => "seuss2.jpg", "Thanks for all the fish" => "adams.jpg", ); print qq(<form> <select name="fish"> ); # Print each fish's <option> line for my $pet (sort keys %fish) { # Note that $pet is the hash key # ... and $fish{$pet} refers to the value print sprintf qq(<option value="%s">%s</option>\n), $fish{$pet}, $pet; } print qq(</select> </form>); __OUTPUT__ <form> <select name="fish"> <option value="fish1.jpg">Fresh water fish</option> <option value="seuss1.jpg">One fish</option> <option value="fish2.jpg">Salt water fish</option> <option value="adams.jpg">Thanks for all the fish</option> <option value="seuss2.jpg">Two fish</option> </select> </form>
    Where do you want *them* to go today?
      Sure it's helpful, but how about simply running your 'fish configurator' through CGI::popup_menu?
      use strict; use warnings; use CGI::Pretty qw(:standard); my %fish = ( "Fresh water fish" => "fish1.jpg", "Salt water fish" => "fish2.jpg", "One fish" => "seuss1.jpg", "Two fish" => "seuss2.jpg", "Thanks for all the fish" => "adams.jpg", ); print start_form, popup_menu( -name => 'fish', -values => [map {$fish{$_}} sort keys %fish], -labels => \%fish, ), end_form, ;
      UPDATE:
      Thanks for watching my back, Coruscate, i was caught up by the -values key -- kept thinking that it needed the hash values, not the hash keys ... oops. Thanks again. :)

      jeffa

      L-LL-L--L-LL-L--L-LL-L--
      -R--R-RR-R--R-RR-R--R-RR
      B--B--B--B--B--B--B--B--
      H---H---H---H---H---H---
      (the triplet paradiddle with high-hat)
      

        jeffa++ for using CGI and presenting the right way to go about it. Just to point out however, jeffa's actual code will not work as you might hope. It took me a second to see why he was using map{} to pass the values. Then I realized that the hash was reversed in the way CGI likes to receive it. So the map works correctly. But unfortunately, CGI is not smart enough to take \%fish for the labels and flip the hash around to get the values right.

        There are two ways (that I know of) to go about fixing this. I will post both solutions. (As well, I'm hoping jeffa would plan on calling header() before start_html() :) ) First method of getting it done: attach a map{} to the passing of -labels as well. So you get the following:

        #!/usr/bin/perl -w use strict; use warnings; use CGI::Pretty qw(:standard); my %fish = ( "Fresh water fish" => "fish1.jpg", "Salt water fish" => "fish2.jpg", "One fish" => "seuss1.jpg", "Two fish" => "seuss2.jpg", "Thanks for all the fish" => "adams.jpg", ); print header(), start_form(), popup_menu( -name => 'fish', -values => [map { $fish{$_} } sort keys %fish], -labels => {map { $fish{$_}, $_ } sort keys %fish} ), end_form();

        The second way to get it done will make things much easier and will make it a little more readable. Simply flip the keys and values in the hash around and then the calls to popup_menu() will be quite simple:

        #!/usr/bin/perl -w use strict; use warnings; use CGI::Pretty qw(:standard); my %fish = ( 'fish1.jpg' => 'Fresh water fish', 'fish2.jpg' => 'Salt water fish', 'seuss1.jpg' => 'One fish', 'seuss2.jpg' => 'Two fish', 'adams.jpg' => 'Thanks for all the fish' ); print header(), start_form(), popup_menu( -name => 'fish', -values => [sort keys %fish], -labels => \%fish ), end_form();

        And from the above two snippets, there should really only be one difference: the first one will sort based on the user-viewed values (ie: 'Thanks for all the fish'), whereas the second snippet sorts based on the actual field values (ie: 'adams.jpg').


              C:\>shutdown -s
              >> Could not shut down computer:
              >> Microsoft is logged in remotely.
            

Re: Drop-down list Option Value
by ibanix (Hermit) on Feb 02, 2003 at 06:58 UTC
    If your content isn't going to change much, why not setup a hash to map the values to the names?

    %list_items = ( 'fish1.jpg' => 'Fresh water fish', 'fish2.jpg' => 'Salt water fish', 'fish3.jpg' => 'Mudskippers', );
    Of course, you'd probally prefer to store the value/name pairs in a file and read them in. I'm sorry that I can't answer the question in a CGI way. I've been using ASP with PerlScript for my web-app needs and I like it very much -- so much that I haven't learned CGI!

    Cheers,
    ibanix

    $ echo '$0 & $0 &' > foo; chmod a+x foo; foo;
Re: Drop-down list Option Value
by tachyon (Chancellor) on Feb 02, 2003 at 11:50 UTC
    use strict; use warnings; my %fish = ( "Fresh water fish" => "fish1.jpg", "Salt water fish" => "fish2.jpg", "One fish" => "seuss1.jpg", "Two fish" => "seuss2.jpg", "Thanks for all the fish" => "adams.jpg", ); print option_list(\%fish); sub option_list { my $options = shift; return "<select>\n" . (join '', map{ qq!<option value="$options->{$_}">$_</option>\n! } +keys %$options ) . "</select>\n"; }

    cheers

    tachyon

    s&&rsenoyhcatreve&&&s&n.+t&"$'$`$\"$\&"&ee&&y&srve&&d&&print

Re: Drop-down list Option Value
by Happyjack (Novice) on Feb 02, 2003 at 16:04 UTC

    Okay. I guess I blew my explanation. Here are snippets of code from my HTML document and my CGI.

    HTML Code

    <p>.....Yada, Yada, Yada... <select name="pet" size="1" onChange="showimage()"> <option selected value="pets.gif">Your Favorite Pet</option> <option value="afghanhd.jpg">Big dogs</option> <option value="austter.jpg">Little dogs</option> <option value="ragdoll2.jpg">Cats</option> <option value="fish1.jpg">Fresh water fish</option> <option value="gerbil.jpg">Gerbils</option> <option value="morganhorse.jpg">Horses</option> <option value="parrot.jpg">Parrots</option> <option value="macaw.jpg">Macaws</option> <option value="toucan.jpg">Toucans</option> <option value="snap.jpg">Turtles</option> <option value="iguana.jpg">Iguanas</option> <option value="sinaloan.jpg">Snakes</option> </select> </p>

    CGI Code

    #!/usr/bin/perl -w require "cgi-lib.pl"; &ReadParse; #color.cgi #Warn browser that HTML is coming print &PrintHeader; print <<"eohtml"; <html><head><title>Thanks for responding</title></head> <body bgcolor = "#FFFFFF"><H1>Thank You</H1> <p>What a coincidence, $in{'firstname'} $in{'lastname'}!!</p> <p>My favorite color is $in{'color'} <strong>AND</strong> I Love $in{' +pet'}.</p> </body></html> eohtml #End of Program

    OUTPUT

    Thank You

    What a coincidence, Jack Gray!!
    My favorite color is yellow AND I Love fish1.jpg.

    Desired Output

    Thank You

    What a coincidence, Jack Gray!!
    My favorite color is yellow AND I Love Fresh water fish.

    I don't want the drop-down list box in my CGI output, only the description from the HTML option statement.

    Again, thanks for all the great responses and I apologize for not fully explaining the assignment.

      In your HTML code you have

      <option value="fish1.jp­g">Fresh water fish</option>

      Only the contents of the value attribute are sent to your CGI script by the browser. So if you want your script to display "Fresh water fish", then you either need to put that into the value attribute or have some sort of a lookup table/file where you can match fish1.jpg to "Fresh water fish"

      On an unrelated note, I am not very sure what cgi-lib.pl is, but you should consider using a standard module for parsing the submitted form data such as CGI. Here's the relavent section of Ovid's web tutorial that talks about why you should use CGi.pm


      Just a tongue-tied, twisted, earth-bound misfit. -- Pink Floyd

        Pink Floyd,
        Just a aheads up regarding cgi-lib. The cgi-lib.pl library has become the de facto standard library for creating Common Gateway Interface (CGI) scripts in the Perl language. You can find information on this at Berkeley. I still need to dig into the difference between the two.

      Easiest way to do that is just use a hash mapping the whatever.gif|jpg to the text values. You use hashes in your program already so I guess you don't need an explanation of how to use them. :)

      Note: untested code follows:

      #!/usr/bin/perl -w require "cgi-lib.pl"; &ReadParse; my %hashOfAnimals = ( "pets.gif" => "Your Favorite Pet", "afghanhd.jpg" => "Big dogs", "austter.jpg" => "Little dogs", "ragdoll2.jpg" => "Cats", "fish1.jpg" => "Fresh water fish", "gerbil.jpg" => "Gerbils", "morganhorse.jpg" => "Horses", "parrot.jpg" => "Parrots", "macaw.jpg" => "Macaws", "toucan.jpg" => "Toucans", "snap.jpg" => "Turtles", "iguana.jpg" => "Iguanas", "sinaloan.jpg" => "Snakes" ); #color.cgi #Warn browser that HTML is coming print &PrintHeader; print <<"eohtml"; <html><head><title>Thanks for responding</title></head> <body bgcolor = "#FFFFFF"><H1>Thank You</H1> <p>What a coincidence, $in{'firstname'} $in{'lastname'}!!</p> <p>My favorite color is $in{'color'} <strong>AND</strong> I Love $hash +OfAnimals{$in{'pet'}}.</p> </body></html> eohtml #End of Program


      Updated: Forgot if key has . in it, key needs to be quoted. Doh!

      antirice    
      The first rule of Perl club is - use Perl
      The
      ith rule of Perl club is - follow rule i - 1 for i > 1

        Antirice,
        Thanks for your help. The code required only one simple change; it requires that the jgp/gif option values be enclosed in quotation marks (as well as the descriptions). With thism change, the code worked perfectly.

        Now I would like to expand this cgi code to display the selected image from the HTML file. This may, in fact, be much more advanced than I am right now. However, it's all a learning experience. Any suggestions in displaying the selected image?

        THX!!!

Re: Drop-down list Option Value
by jonadab (Parson) on Feb 03, 2003 at 15:49 UTC
    I'm a true novice in CGI so please bare with me.

    Whom are we going to moon?

    Ahem. Others have given you examples, but I think I can clarify the why of it a bit more...

    A web form does not send the whole web page back to the script. That would be unnecessary, would waste bandwidth (and slow things down), and would create problems if a page has multiple forms (as is common; in some database-oriented CGI applications, a table may have a form on each line, with the ID of that record embedded in a hidden field, so that if the user clicks the "Edit" button on that line, he goes to a form for editing that record). In that case, how would the script know which form the user submitted?

    So, to simplify matters, the web browser sends only the important information -- the name/value pairs from the form. In the case of select/option, the name comes from the select element and the value comes from the chosen option element. That's what value="foo" is for -- it sets the value that is sent back to the script. Whatever you put in there will be the value your script gets if the user chooses that option.

    So, that's one reason it's convenient to have your script print the form itself; then it knows if a new option is added, or an option is reworded, or something. Your script might look like this (simplified) example...

    %pet = ( fish.jpg => 'Fresh Fish', fido.jpg => 'Domestic Dog', ); if (getinput()) { print_header(); print "<body><p>I like $pet{$input{pet}}</p></body>"; print_footer(); } else { # no input; print the blank form... print_header(); print "<body><form method=\"post\" action=\"$ENV{REQUEST_URI}\"> Pet: <select name="pet">\n"; foreach $p (%pets) { print "<option value=\"$p\">$pet{$p}</option>\n"; } print "</select> <input type=\"submit\" value=\"submit\"> </form></body>"; print_footer(); }

    The other option is to change your HTML form so that 'Fresh Water Fish' (or whatever) is the value.

     --jonadab

Log In?
Username:
Password:

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

How do I use this?Last hourOther CB clients
Other Users?
Others scrutinizing the Monastery: (2)
As of 2024-04-20 03:52 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found