Beefy Boxes and Bandwidth Generously Provided by pair Networks
The stupid question is the question not asked

Selectively coloring a menu's item members

by hacker (Priest)
on Aug 31, 2007 at 23:49 UTC ( #636447=perlquestion: print w/replies, xml ) Need Help??
hacker has asked for the wisdom of the Perl Monks concerning the following question:

I'm trying to color a menu of items on an webpage, based on the item currently selected. I know the item chosen, based on $cgi->param('a'), so that part isn't a problem.

I've abstracted the logic into a small, standalone script that looks like this:

my @menu_options = ('home', 'donate', 'news', 'docs', 'download', 'gal +lery', 'samples', 'users', 'developers', 'about'); my $items = @menu_options; my $count = 1; print qq{ <div class="sh"> <span class="doNotDisplay">Navigation:</span> }; my $style = ''; foreach my $menu_item (@menu_options) { $style = qq{style="background-color: #9943ac;"} if ($action eq $menu_item && $action =~ /docs/); $style = qq{style="background-color: #d8402b;"} if ($action eq $menu_item && $action =~ /download/); $style = qq{style="background-color: #ab0;"} if ($action eq $menu_item && $action =~ /users/); $style = qq{style="background-color: #6fab87;"} if ($action eq $menu_item && $action =~ /developers/); print qq{\t\t<a href="/$menu_item" $style>$menu_item</a>}; print " |" if ($count < $items); print "\n"; $count++; } print "\t</div>\n";

In my actual code, I have a dispatch table that looks like this:

my %dispatch = ( (map { $_ => \&default } qw( home donate news docs download gallery docs users developers about )), samples => sub { \&samples($dbh) }, );

I'm trying to selectively color the background of the item selected. What am I missing in my sample code above?

I'm only trying to colorize 4 of the 10 menu options, and only one should be colorized at a time. They're in my dispatch table in the production code (not an array like the sample test above; I created that to try to isolate the problem).

Is there a better way to do this?

Replies are listed 'Best First'.
Re: Selectively coloring a menu's item members
by GrandFather (Sage) on Sep 01, 2007 at 00:01 UTC

    General rule: declare variables in the smallest scope possible. In this case:

    #my $style = ''; # Removed global foreach my $menu_item (@menu_options) { my $style = '';

    avoids your problem which is due to using a global (to the loop) variable instead of a temporary variable.

    DWIM is Perl's answer to Gödel
Re: Selectively coloring a menu's item members
by beretboy (Chaplain) on Sep 01, 2007 at 13:04 UTC
    Please, please, please use HTML::Template. It will make CGI programming orders of magnitude easier. I second everything said above about using css identifiers.

    "Sanity is the playground of the unimaginative" -Unknown
Re: Selectively coloring a menu's item members
by snopal (Pilgrim) on Sep 01, 2007 at 00:00 UTC

    A link is not an area. It does not have a background-color component. You need to use some form of bordering, perhaps with DIV tags.

    == Desire is one product of absence. -- Stephen Opal ==

        To get the behavior expressed in the parent, I've always found it necessary to declare some container object to express an area of color background.

        That does not mean that I wouldn't entertain an example from you or another contributor that satisfies the parent's design strictly by controlling the background color style property.

        Essentially, one can do almost anything with any tag by redefining its style properties, but then it becomes possible the element ceases to be understandable HTML.

        == Desire is one product of absence. -- Stephen Opal ==
Re: Selectively coloring a menu's item members
by hacker (Priest) on Sep 03, 2007 at 01:40 UTC

    The code works so far, but I've discovered a problem..

    If you select docs on the test website, you'll see that the menu properly tabs itself and colorizes itself based on the item you select.

    The other 3 tabs that colorize this way are 'download', 'users' and 'developers'. Those work as well.

    The problem I've noticed, happens when you select a second-level citizen from the secondary menu. For example, if you click on docs and then click on faq from there, the relationship to 'docs' is no longer maintained, and you lose the purple "tab" that goes to 'docs'.

    The first-level menu is generated dynamically, using an array and checking $action (coming out of my dispatch table) against the items in that array, and applying the appropriate css style inline for that element only.

    This is how the first-level citizens works right now, and you can see that it does indeed work.

    What I'm trying to figure out, is how to create/maintain a relationship between the second-level citizens and their parent dispatch actions.

    This means the child=>parent relationship looks like this:

    home: donate: news: docs......: [faq] [lists] [tour] [documentation] download..: [windows] [macosx] [linux] [source] bugs: gallery: samples: users.....: [irc] [links] developers: [snapshots] [source] [tools] about:

    What is the easiest/most flexible way of creating these menus in a way that maintains these relationships and allows me to keep the parent menu's tab colored, when I'm selecting children items of that parent?

Log In?

What's my password?
Create A New User
Node Status?
node history
Node Type: perlquestion [id://636447]
Approved by Anno
and all is quiet...

How do I use this? | Other CB clients
Other Users?
Others taking refuge in the Monastery: (4)
As of 2017-03-26 13:18 GMT
Find Nodes?
    Voting Booth?
    Should Pluto Get Its Planethood Back?

    Results (315 votes). Check out past polls.