Um- minor correction- I slightly misspoke-- I was confusing this with another module I have. This example _only_ matches the URL, CAPTION, and NAME fields from the hash. Sorry for any confusion.
John On Tuesday 17 September 2002 03:27 am, Brat Wizard spewed into the ether: > I've been meaning for a long time to release some code samples-- here is > one I especially like for making menus and navbars in html-- same code will > work for either. > > A caveat: I use several custom modules which hides some stuff- most notably > the Page object, which is basically a hash of hashes that contain the > menu-item data, as well as an array of pages (items in a Page object) which > keeps the correct page-order. The general structure of a page-item is like > this: > > name => undef, # name of page item (eg. 'contact') > admin => 0, # 1=Admin-Only > caption => undef, # page caption (eg. "Contact Us") > url => undef, # what to do if clicked eg: http://someurl > type => 'user', # User or Prot (Prot=protected & can't > edit) origin => 'user', # User or Int (Int=internal) > active => 0, # mark inactive by default > > And not all of these items are relevant to this routine. So, that said, > this snippet of code-- which is meant more for its idea value than its > particular usefulness as written-- (it works well in my apps but you won't > have all the supporting stuff to make it work out of the box). This bit of > code will allow you to very easily specify an html menu/navbar structure > and have the selected item behave differently, and to specify the menu > separator (if any). It easily lends itself to horizontal and vertical menus > and its html-like (xml-ish) syntax is like so (a simplified vertical > example): > > <table><tr><td> > <my:menu selected="$$args{cmd}"> > <sel><b><a href="__URL__">__CAPTION__</a></b><br></sel> > <norm><a href="__URL__">__CAPTION__</a><br></norm> > </my:menu> > </td></tr></table> > > This produces a very attractive (albeit simple) vertical menu. What's > important is to notice the <sel>, <norm>, and (if present), <sep> tags (and > they need to be closed). ANY legal html/javascript code (or anything else > for that matter that can be expressed as a string) can be put between the > tags. For example, in more complicated menus, I often use javascript to do > button rollover effects and the like. > > The function presented below will take everything (in uppercase) surrounded > by two underscores (ie. '__FIELD__') and attempt to match it to its > corresponding (lower-case) field in the page-item object (or your own > substituted hash structure). > > If the <sep> tag is present, it will be used between the menu/navbar items > and will separate the items however you say. I often just use something > like <sep>|</sep> (vertical bar) or <sep> </sep> (a couple of > spaces), but it can be anything html. > > To make this work, you have to be using the XMLSubsMatch setting in the > .htaccess or apache config file (wherever you set your other ASP config > vars). Mine looks like this: > > PerlSetVar XMLSubsMatch my:\w+ > > This causes anything beginning with 'my:' in my .html/.asp files to be > interpreted (or attempted anyway) as a sub-routine reference. The args > supplied inside the opening tag itself are passed to the subroutine as > '$args' (or whatever you want to call it-- the first argument passed). The > text (if any) between the tags is passed as the second ($body). Such that: > > <my:parseme somefield="someval"> > Whatever you want to pass as the body goes here > </my:parseme> > > This is all documented better on the main ASP site. > > One thing to note that is NOT mentioned on the ASP site-- apparently the > parsing algorithm doesn't know how to handle values that are NOT enclosed > in quotes. Html does not require quotes as long as the value contains no > spaces and only alphanumeric characters. You can't do that here. The other > thing to point out is that any perl variables (eg. $myvar) are NOT escaped > in the usual apache::asp way, (<%=$myvar%>) but instead are just simply > passed between the quotes. Personally I think this is an inconsistancy, and > one that should be dealt with so that clueless users who write html pages > using custom tags don't accidently expose the workings of apache::asp. An > alternative might be to allow a secondary syntax that could only be used as > subroutine references-- eg. [% stuff %]. I can understand the depth of the > syntax and coding problems surrounding this issue-- especially when the > subject of nesting comes up... I'm not complaining, just tossing in my 2 > cents and wishing there was a way to keep the functional aspect without > exposing ASP to the clueless user (or malicious web hacker for that > matter). > > Anyway, fwiw, here is the routine below. You can see an example of it in > operation at: stores.wizard.org/wizorg, stores.wizard.org/wizcomp, and > stores.wizard.org/dots (I'm not sure that Dot has her store completely set > up and ready to go but you can see the menu anyway). > > I hope this helps someone! :) > > John Whitten > [EMAIL PROTECTED] > Wizard.Org, Inc. > > > ##------------------------------------------------------------------------- >--- sub my::navbar { my::menu(@_) } > sub my::menu { > my ($args, $body) = @_; > my $norm = qq{<a href="__URL__">__CAPTION__</a><br>}; > my $sel = qq{<b><a href="__URL__">__CAPTION__</a></b><br>}; > my $sep = ''; > my $themeurl = "$URL{theme}/$Store->{theme}/images"; > > if ($body =~ /<norm>/i) { > $body =~ /<norm>(.*?)<\/norm>/i; # normal cell > $norm = $1; > } > if ($body =~ /<sel>/i) { > $body =~ /<sel>(.*?)<\/sel>/i; # selected cell > $sel = $1; > } > if ($body =~ /<sep>/i) { > $body =~ /<sep>(.*?)<\/sep>/i; # divider cell > $sep = $1; > } > > $$args{selected} = lc($$args{selected}); > my $start = 0; > foreach (@{$Store->{pages}}) { > my $page = $Store->{pagedata}->findPage($_); > next if (isPermitted() == 0 && $page->val('admin') == 1); > my $name = $page->val('name'); > > my $caption = $page->val('caption') || $name; > my $url = $page->val('url'); > my $selected = ($name eq $$args{selected})?1:0; > > $url = $page->val('url'); > $url = "/$storeid/$name" if ($url eq ''); > > print "$sep\n" if ($sep ne '' && $start++ > 0); > my $str = ($selected == 1)?$sel:$norm; > $str =~ s/__NAME__/$name/gie; > $str =~ s/__URL__/$url/gie; > $str =~ s/__CAPTION__/$caption/gie; > print "$str\n"; > } > } -- -------------------------------------------------------------------------------- Check out http://www.Wizard.Org for great deals on Electronic Parts *NEW* Computer Parts & Accessories - Drives - LCD - Systems - Linux -------------------------------------------------------------------------------- ** Affordable Online Store w/Merchant Card Processing & Paypal ** Write to us: [EMAIL PROTECTED] -- Get your Store Online Today! -------------------------------------------------------------------------------- --------------------------------------------------------------------- To unsubscribe, e-mail: [EMAIL PROTECTED] For additional commands, e-mail: [EMAIL PROTECTED]