Forums / Developer / Simple Code for Generating Multi-Level Divs for Menus

Simple Code for Generating Multi-Level Divs for Menus

Author Message

Alex Jones

Monday 01 December 2003 7:46:46 am

I have been working on the code that generates our navigation menu system as it is rather large at the moment. I had been using the Tree Menu code as an example, but I think I have found a better method. I am posting the code below to see if anyone can poke holes in it, especially in regards to efficieincy. I know the code generates the proper front-end code as I have thoroughly tested that part.

If this looks like a solid piece of work, I will post a contribution with a proper write-up after any important changes are made.

The code below is meant to generate DIVs which contain links. The DIVs would be controlled by JavaScript and CSS which I have not included at this point, though I will in the final contribution. I have tried to provide appropriate comments, but am more than happy to answer any questions you may have. To see an example of the menu system (though, it uses the old code at the moment) you can see a static version at http://www.agrussell.com

[Code]------------------------------

{* Loop through folders to a depth of four levels *}
{let NavList=fetch( content, list, hash(depth, 4, parent_node_id, 2, class_filter_type, "include", class_filter_array, array(1)))}
{section name=Nav loop=$NavList}
{* This switch statement allows me to use a different class for the first level of menus versus all of the others. It also allows me to use a different naming structure for the first level compared to the other levels. I use different naming conventions as my root node (2) has a really long name that I don't want inserted multiple times within my HTML. Adding additional cases will provide more flexibility should you wish to differntiate between levels in the hierarchy. *}
{switch match=$:item.depth}
{case match=2}<div id="menu-{$Nav:item.name|wash(nospace)}" class="Menu"> {* I use a wash operater dubbed 'nospace' to strip out spaces for use in the ID *}
{/case}
{case}<div id="menu-{$Nav:item.parent.name|wash(nospace)}{$Nav:item.name|wash(nospace)}" class="SubMenu">
{/case}
{/switch}
{* Loops through Folders, articles and some custom classes, sort them by name for display. *}
{section name=NavChild loop=fetch( 'content', 'list', hash(parent_node_id, $Nav:item.node_id, class_filter_type, "include", class_filter_array, array(1,2,10,11,46), "sort_by", array("name", true())))}
{* I have added a checkbox to my folder class which allows me to toggle whether the navigation menus should display the contents within the navigation menu system. This provides a lot of flexibility as I do not want all sub-folders to be treated the same. *}

{* If the folder's contents should be displayed, print out a link which any required JavaScript statements - this would vary depending on the menu code. *}
{section show=eq($:item.object.data_map.navdisplay.data_int,1)}
{* Within the link I detect whether or not the depth is greater than 2. This detection allows me to call the name that matches the ID set in the switch statement above. *}
<a href={concat("/",$:item.url_alias)|ezroot)|ezroot} onmouseover="menu.show('{section show=$:item.depth|gt(2)}{$:item.parent.name|wash(nospace)}{/section}{$:item.name|wash(nospace)}', '{section show=$Nav:item.depth|gt(2)}{$Nav:item.parent.name|wash(nospace)}{/section}{$:item.parent.name|wash(nospace)}', this, 125, 0)" onmouseout="menu.hide('{$:item.parent.name|wash(nospace)}{$:item.name|wash(nospace)}')">{$:item.name|wash} &raquo;</a>{section-else}

{* Otherwise print out a plain link. *}
<a href={concat("/",$:item.url_alias)|ezroot)|ezroot}>{$:item.name|wash}</a>{/section}
{/section}

</div>

{/section}
{/section}
{/let}

[/Code]------------------------------

Thanks!

Alex

Alex
[ bald_technologist on the IRC channel (irc.freenode.net): #eZpublish ]

<i>When in doubt, clear the cache.</i>

Alex Jones

Monday 01 December 2003 7:55:21 am

One Quick note, if you are looking at the source code of the site I posted, all of the menu DIVs are at the bottom of the code.

Alex

Alex
[ bald_technologist on the IRC channel (irc.freenode.net): #eZpublish ]

<i>When in doubt, clear the cache.</i>

jamie harbison

Thursday 03 June 2004 10:48:46 pm

Nice work!!

This is looking really cool, and more or less what i'm looking to implement>>>have you done any further development on the code?

Mark Marsiglio

Thursday 02 December 2004 5:34:58 pm

Alex,

Did you ever get a chance to finish out this menu? I did not see the javascript code or CSS anywhere else, but I am not sure if I am missing it.

It sure would be helpful for the project i am working on right now if it is available...if not the code you provided already will be a good start.

Thanks
Mark

http://www.thinkcreative.com
Turning Ideas Into Strategic Solutions

Alex Jones

Friday 03 December 2004 7:35:56 am

I'm afraid I haven't provided a contribution for this, for several reasons, the foremost of which is time. Sorry. :( I would recommend you adapt the code I provided above to fit the structure of your chosen menu code. If you haven't decided what to use to control the drop downs, here are a couple of recommendations:

<b>Son of Suckerfish Dropdown Menus</b>
Accessible, and only needs 12 lines of JavaScript.I haven't used them yet, but have heard great things.
Site: http://www.htmldog.com/articles/suckerfish/dropdowns/
Example 1: http://www.htmldog.com/articles/suckerfish/dropdowns/example/
Example 2: http://www.htmldog.com/articles/suckerfish/dropdowns/example/vertical.html

<b>TwinHelix FreeStyle Menus</b>
This is a newer version of the script I use on www.agrussell.com. Note, if you want to use it without providing a visible link to the TwinHelix site, you need to make a donation. Personally, I think it is well worth it, as the developer was very responsive and has produced some great code.

What I like about this script over Suckerfish is the delay before a menu disappears. The Suckerfish menus seem a bit too abrupt as they disappear the instant the cursor isn't over them.
Site: http://www.twinhelix.com/dhtml/fsmenu/
Example: http://www.twinhelix.com/dhtml/fsmenu/demo/

Hope that helps. One day, I'll try to put a contribution together.

Alex
[ bald_technologist on the IRC channel (irc.freenode.net): #eZpublish ]

<i>When in doubt, clear the cache.</i>

Xavier Dutoit

Saturday 04 December 2004 1:10:54 am

I don't think the div are the right thing to do to represent a menu. After all, a menu is a multilevel list of links, isn't it ?

I've used this code http://www.csscreator.com/menu/multimenu.php and it works fine. You just need to use css for xhtml compatible browsers and a 10 lines javascript program deals with ie.

For the template code, I simply used three imbricated section loop.

X+

http://www.sydesy.com

Lazaro Ferreira

Saturday 04 December 2004 4:26:14 am

Hi Xavier,

Can you post a sample of your template code to feed the JS popmenu ?

Another question have you tried EZP 3.5 popmenu ?

What do you think about it ?

Lazaro
http://www.mzbusiness.com

Marco Zinn

Saturday 04 December 2004 6:54:11 am

Hi Folks,
just another link:
Eric Meyer (CSS-Guru) shows off a very nice "pure CSS" menu here:
http://www.meyerweb.com/eric/css/edge/menus/demo.html
I was very impressed by this. It's using nested lists (ULs and LIs) with CSS 2.

This means, that the "pure CSS" version does not work (menu's don't popup) in IE's . This is a design-design of Eric, as he wanted to show off a pure CSS solution without the usuall JS stuff.

This might be usefull for site, which can rely on the users having Gecko-Powered browser (like Firefox) or as a starting point for a CSS+JS menu based on lists rather than divs.

Marco
http://www.hyperroad-design.com

Alex Jones

Saturday 04 December 2004 7:37:23 am

Xavier, you are quite right, <i>DIV</i>s are not the way to go. Since I built agrussell.com, I have switched to using nested lists, and highly recommend others do the same. Ultimately though, the concept is the same.

Marco, I am a big fan of Eric Meyer, and actually thought about those menus, but ultimately, I don't think they are ready for production use, quite specifically because they don't work in IE. :( That is one of the reasons I pointed out the Suckerfish menus, as the JavaScript that is included (all 12 lines of it) makes it work in IE, DOM-compatible browsers do not use the JS at all. So, the suckerfish menus are a half way between menu systems that are driven by JavaScript, and those that are driven purely by CSS.

As I mentioned above, I have one issue with the SuckerFish, and Eric Meyer's menu systems: menus disappear the instant the cursor moves away from them. I don't think this is very user friendly, and ultimately can prove very frustrating once a site needs multi-level menus. A user may accidentally move the cursor and have to go find the same spot again, three sub-menus down. If this happens more than once, they will get quite annoyed - well, at least I do.

So, while I am a huge fan of CSS and promote its use everywhere that I can, I don't think it is the best solution for menus. Pure JavaScript menus are not the answer either. It is important to use the technologies for their respective strengths and purposes. In my opinion, the ideal system is a combination of JavaScript to control how the menus work, with CSS to control how the menu style and location.

Sorry to go off on a tangent there, but I think it is applicable to the subject at hand. If not, let me know. :)

Alex
[ bald_technologist on the IRC channel (irc.freenode.net): #eZpublish ]

<i>When in doubt, clear the cache.</i>

eZ debug

Timing: Jan 18 2025 10:22:38
Script start
Timing: Jan 18 2025 10:22:38
Module start 'content'
Timing: Jan 18 2025 10:22:39
Module end 'content'
Timing: Jan 18 2025 10:22:39
Script end

Main resources:

Total runtime0.9997 sec
Peak memory usage4,096.0000 KB
Database Queries220

Timing points:

CheckpointStart (sec)Duration (sec)Memory at start (KB)Memory used (KB)
Script start 0.00000.0058 588.9766180.8125
Module start 'content' 0.00580.8470 769.7891799.0156
Module end 'content' 0.85280.1468 1,568.8047348.4297
Script end 0.9996  1,917.2344 

Time accumulators:

 Accumulator Duration (sec) Duration (%) Count Average (sec)
Ini load
Load cache0.00400.4001210.0002
Check MTime0.00150.1536210.0001
Mysql Total
Database connection0.00070.067910.0007
Mysqli_queries0.896089.62472200.0041
Looping result0.00260.26092180.0000
Template Total0.962596.320.4813
Template load0.00230.231820.0012
Template processing0.960296.049220.4801
Template load and register function0.00010.010510.0001
states
state_id_array0.00150.154310.0015
state_identifier_array0.00110.112520.0006
Override
Cache load0.00210.2097910.0000
Sytem overhead
Fetch class attribute can translate value0.00220.215370.0003
Fetch class attribute name0.00120.1187130.0001
XML
Image XML parsing0.00250.246170.0004
class_abstraction
Instantiating content class attribute0.00000.0032160.0000
General
dbfile0.00510.5111440.0001
String conversion0.00000.000530.0000
Note: percentages do not add up to 100% because some accumulators overlap

CSS/JS files loaded with "ezjscPacker" during request:

CacheTypePacklevelSourceFiles
CSS0extension/community/design/community/stylesheets/ext/jquery.autocomplete.css
extension/community_design/design/suncana/stylesheets/scrollbars.css
extension/community_design/design/suncana/stylesheets/tabs.css
extension/community_design/design/suncana/stylesheets/roadmap.css
extension/community_design/design/suncana/stylesheets/content.css
extension/community_design/design/suncana/stylesheets/star-rating.css
extension/community_design/design/suncana/stylesheets/syntax_and_custom_tags.css
extension/community_design/design/suncana/stylesheets/buttons.css
extension/community_design/design/suncana/stylesheets/tweetbox.css
extension/community_design/design/suncana/stylesheets/jquery.fancybox-1.3.4.css
extension/bcsmoothgallery/design/standard/stylesheets/magnific-popup.css
extension/sevenx/design/simple/stylesheets/star_rating.css
extension/sevenx/design/simple/stylesheets/libs/fontawesome/css/all.min.css
extension/sevenx/design/simple/stylesheets/main.v02.css
extension/sevenx/design/simple/stylesheets/main.v02.res.css
JS0extension/ezjscore/design/standard/lib/yui/3.17.2/build/yui/yui-min.js
extension/ezjscore/design/standard/javascript/jquery-3.7.0.min.js
extension/community_design/design/suncana/javascript/jquery.ui.core.min.js
extension/community_design/design/suncana/javascript/jquery.ui.widget.min.js
extension/community_design/design/suncana/javascript/jquery.easing.1.3.js
extension/community_design/design/suncana/javascript/jquery.ui.tabs.js
extension/community_design/design/suncana/javascript/jquery.hoverIntent.min.js
extension/community_design/design/suncana/javascript/jquery.popmenu.js
extension/community_design/design/suncana/javascript/jScrollPane.js
extension/community_design/design/suncana/javascript/jquery.mousewheel.js
extension/community_design/design/suncana/javascript/jquery.cycle.all.js
extension/sevenx/design/simple/javascript/jquery.scrollTo.js
extension/community_design/design/suncana/javascript/jquery.cookie.js
extension/community_design/design/suncana/javascript/ezstarrating_jquery.js
extension/community_design/design/suncana/javascript/jquery.initboxes.js
extension/community_design/design/suncana/javascript/app.js
extension/community_design/design/suncana/javascript/twitterwidget.js
extension/community_design/design/suncana/javascript/community.js
extension/community_design/design/suncana/javascript/roadmap.js
extension/community_design/design/suncana/javascript/ez.js
extension/community_design/design/suncana/javascript/ezshareevents.js
extension/sevenx/design/simple/javascript/main.js

Templates used to render the page:

UsageRequested templateTemplateTemplate loadedEditOverride
1node/view/full.tplfull/forum_topic.tplextension/sevenx/design/simple/override/templates/full/forum_topic.tplEdit templateOverride template
7content/datatype/view/ezimage.tpl<No override>extension/sevenx/design/simple/templates/content/datatype/view/ezimage.tplEdit templateOverride template
9content/datatype/view/ezxmltext.tpl<No override>extension/community_design/design/suncana/templates/content/datatype/view/ezxmltext.tplEdit templateOverride template
17content/datatype/view/ezxmltags/paragraph.tpl<No override>extension/ezwebin/design/ezwebin/templates/content/datatype/view/ezxmltags/paragraph.tplEdit templateOverride template
9content/datatype/view/ezxmltags/line.tpl<No override>design/standard/templates/content/datatype/view/ezxmltags/line.tplEdit templateOverride template
1pagelayout.tpl<No override>extension/sevenx/design/simple/templates/pagelayout.tplEdit templateOverride template
 Number of times templates used: 44
 Number of unique templates used: 6

Time used to render debug report: 0.0002 secs