Adding an additional submenu to a collapsible/expandable menu

Discussion in 'HTML' started by Jonathan, Jan 5, 2007.

  1. Jonathan

    Jonathan Guest

    Hello All,

    I am in the process of creating a 2/3 level collapsible/exspanible menu
    (called "nav") where users can click on a category and have the
    submenus appear beneath it and so on (allow users to click on another
    category and have that expand).

    Example:

    >Corp Info
    >>Corp Overview
    >>Remote Sites

    >Departments
    >>Human Resources
    >>HR Staff
    >>HR Forms
    >>HR Etc.


    Currently the code below allows the users to the drill down one level,
    but I want it to be able to drill down an additional level. Any help
    would be much appreciated.

    Jonathan


    Current Code:
    ****************************************************************************
    <style type="text/css">
    #nav {width: 170px; height: 500px}
    #nav, #nav ul, #nav li {margin: 0; padding: 0; list-style: none;}
    #nav li {clear: both;}
    #nav li b {display: block; height: 1.2em; color: white; background:
    #000033; width: 100%; border-top: thin solid #CCCCCC; padding: 4px;}
    #nav li ul li a {display: block; height: 1.2em; width: 100%; padding:
    4px; text-decoration: none; color: black; background: #ededed;
    border-top: thin solid #CCCCCC;}
    #nav li ul li {font-size: 92%; border: #000033; background: none;}
    #nav li ul li a:hover {color: #000033; background: orange; }
    </style>

    <script type="text/javascript">

    function setCookie (name, value, path, domain, secure, expires)
    {
    document.cookie= name + "=" + escape(value) +
    ((expires) ? "; expires=" + expires.toGMTString() : "") +
    ((path) ? "; path=" + path : "") +
    ((domain) ? "; domain=" + domain : "") +
    ((secure) ? "; secure" : "");
    }

    function getCookie (name)
    {
    var dc = document.cookie;
    var prefix = name + "=";
    var begin = dc.indexOf("; " + prefix);
    if (begin == -1)
    {
    begin = dc.indexOf(prefix);
    if (begin != 0) return null;
    }
    else
    {
    begin += 2;
    }
    var end = document.cookie.indexOf(";", begin);
    if (end == -1)
    {
    end = dc.length;
    }
    return unescape(dc.substring(begin + prefix.length, end));
    }

    function deleteCookie (name, path, domain)
    {
    if (getCookie(name))
    {
    document.cookie = name + "=" +
    ((path) ? "; path=" + path : "") +
    ((domain) ? "; domain=" + domain : "") +
    "; expires=Thu, 01-Jan-70 00:00:01 GMT";
    }
    }


    function addLoadEvent (func)
    {
    var oldonload = window.onload;
    if (typeof window.onload != 'function')
    {
    window.onload = func;
    }
    else
    {
    window.onload = function()
    {
    oldonload();
    func();
    }
    }
    }

    </script>

    <script type="text/javascript">

    function menu_init ()
    {
    var menu = document.getElementById('nav');
    var subs = menu.childNodes;

    var j = 0;

    for (var i=0 ; subs; i++)
    {
    if (subs.tagName=='LI')
    {
    hs = subs.getElementsByTagName('B');
    heading = hs[0];
    ss = subs.getElementsByTagName('UL');
    submenu = ss[0];

    j++;

    heading.onclick = function () { menu_toggle(this); };

    if (getCookie('menu'+j)=='1')
    submenu.style.display = 'block';
    else if (getCookie('menu'+j)=='0')
    submenu.style.display = 'none';
    else if (j==1)
    submenu.style.display = 'block';
    else
    submenu.style.display = 'none';
    }
    }
    }

    function menu_toggle (heading)
    {
    var section = heading.parentNode;
    var submenus = section.getElementsByTagName('UL');
    var submenu = submenus[0];

    if (submenu.style.display=='none')
    submenu.style.display = 'block';
    else
    submenu.style.display = 'none';

    var j = 0;

    var menu = document.getElementById('nav');
    var subs = menu.childNodes;
    for (var i=0 ; subs; i++)
    {
    if (subs.tagName=='LI')
    {
    hs = subs.getElementsByTagName('B');
    h = hs[0];
    j++;

    if (h==heading && submenu.style.display=='none')
    setCookie('menu'+j, '0', '/');
    else if (h==heading)
    setCookie('menu'+j, '1', '/');
    }
    }


    }

    addLoadEvent(menu_init);

    </script>

    <!--[if IE 6]>
    <script type="text/javascript">
    // Suckerfish-like code to get B:hover working in IE 6.
    function sucker_bold ()
    {
    bs = document.getElementById("nav").getElementsByTagName('B');
    for (i=0; bs; i++)
    {
    node = bs;
    node.onmouseover=function() { this.className+=" over"; }
    node.onmouseout=function() { this.className=this.className.replace("
    over", ""); }
    }
    }
    addLoadEvent(sucker_bold);
    </script>
    <![endif]-->

    <DIV id=leftNavContainer>
    <ul id="nav">
    <li>
    <b>Corporate Information</b>
    <ul>
    <li><a href="#">Corporate
    Overview</a></li>
    <li><a href="#">Remote Sites</a></li>
    </ul>
    </li>
    <li>
    <b>Departments</b>
    <!--<ul>-->
    <ul>
    <li><a href="#">Human
    Resources</a></li>
    <!-- <li><a href="">HR Staff</a></li>
    <li><a href="">HR Forms</a></li>
    <li><a href="">Benefits</a></li>
    </ul>-->
    <li><a
    href="#">Accounting</a></li>
    <!-- <ul>
    <li><a href="">Accounting
    Staff</a></li>
    <li><a href="">Organizational
    Chart</a></li>
    </ul>-->
    </ul>
    </li>

    </ul>
    </div>
    *********************************************************************************************************
     
    Jonathan, Jan 5, 2007
    #1
    1. Advertising

  2. Jonathan

    Toby Inkster Guest

    Jonathan wrote:

    > Currently the code below allows the users to the drill down one level,
    > but I want it to be able to drill down an additional level. Any help
    > would be much appreciated.


    This looks startlingly like an old script of mine.

    I've not tried it with three nav levels, but I *believe* the key is to
    replace this:

    subs = menu.childNodes();

    with this:

    subs = menu.getElementsByTagName('LI');

    --
    Toby A Inkster BSc (Hons) ARCS
    Contact Me ~ http://tobyinkster.co.uk/contact
     
    Toby Inkster, Jan 5, 2007
    #2
    1. Advertising

  3. Toby Inkster wrote:
    > Jonathan wrote:
    >
    >> Currently the code below allows the users to the drill down one level,
    >> but I want it to be able to drill down an additional level. Any help
    >> would be much appreciated.

    >
    > This looks startlingly like an old script of mine.
    >
    > I've not tried it with three nav levels, but I *believe* the key is to
    > replace this:
    >
    > subs = menu.childNodes();
    >
    > with this:
    >
    > subs = menu.getElementsByTagName('LI');
    >


    I did up a demo for someone here recently that is a little more modern
    for attaching the events and degrades to a fully expanded list if
    JavaScript is disabled

    <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN"
    "http://www.w3.org/TR/html4/strict.dtd">
    <html>
    <head>
    <title>template</title>
    <style type="text/css">
    #sm1,#sm2,#sm3 {
    display: block;
    }
    </style>

    <script type="text/javascript">
    var buf='<style type="text/css">#sm1, #sm2, #sm3 { display: none;
    }</style>';
    document.write(buf);
    </script>

    <script type="text/javascript">

    var menus=new Array('m1', 'm2', 'm3');

    function toggle(e){
    var me;
    if(!e) var e=window.event;
    if(e.target) me=e.target; // W3C
    else if(e.srcElement) me=e.srcElement; // MSIE
    if(me.nodeType == 3) me=me.parentNode; // Safari bug on elements
    with TEXT

    var id='s' + me.id;
    var submenu=document.getElementById(id);
    me.flag =! me.flag;
    if(me.flag) submenu.style.display="block";
    else submenu.style.display="none";
    }

    function initMenus(){
    for( var i=0; i<menus.length; i++){
    var menu=document.getElementById(menus);

    //alert('Init ' + menus + ' which is ' + menu.tagName );

    menu.flag=false;

    if(menu.addEventListener){
    menu.addEventListener('click', toggle, false);
    }
    else if(menu.attachEvent){ //MS IE support
    menu.attachEvent('onclick', toggle);
    }
    }
    }

    // attach event after page loads
    if( window.addEventListener ) {
    window.addEventListener('load',initMenus,false); //legacy
    } else if( document.addEventListener ) {
    document.addEventListener('load',initMenus,false); //proper
    } else if( window.attachEvent ) {
    window.attachEvent("onload", initMenus); //IE only
    }

    </script>

    </head>
    <body>

    <ul>
    <li><a href="#" id="m1">Menu 1</a>
    <ul id="sm1">
    <li>Submenu 1.1</li>
    <li>Submenu 1.2</li>
    <li>Submenu 1.3</li>
    </ul>
    </li>
    <li><a href="#" id="m2">Menu 2</a>
    <ul id="sm2">
    <li>Submenu 2.1</li>
    <li>Submenu 2.2</li>
    <li>Submenu 2.3</li>
    <li>Submenu 2.4</li>
    </ul>
    </li>
    <li><a href="#" id="m3">Menu 3</a>
    <ul id="sm3">
    <li>Submenu 3.1</li>
    <li>Submenu 3.2</li>
    </ul>
    </li>
    <ul>

    </body>
    </html>

    --
    Take care,

    Jonathan
    -------------------
    LITTLE WORKS STUDIO
    http://www.LittleWorksStudio.com
     
    Jonathan N. Little, Jan 5, 2007
    #3
  4. Jonathan

    Jonathan Guest

    Jonathan,

    Is there anything special that I need to do to view your example? I
    saved your code (as an new html file) and attempted to view it to no
    avail. What would you suggest me to do to view your example. Thanks
    for your assistance.

    Jonathan

    Jonathan N. Little wrote:
    > Toby Inkster wrote:
    > > Jonathan wrote:
    > >
    > >> Currently the code below allows the users to the drill down one level,
    > >> but I want it to be able to drill down an additional level. Any help
    > >> would be much appreciated.

    > >
    > > This looks startlingly like an old script of mine.
    > >
    > > I've not tried it with three nav levels, but I *believe* the key is to
    > > replace this:
    > >
    > > subs = menu.childNodes();
    > >
    > > with this:
    > >
    > > subs = menu.getElementsByTagName('LI');
    > >

    >
    > I did up a demo for someone here recently that is a little more modern
    > for attaching the events and degrades to a fully expanded list if
    > JavaScript is disabled
    >
    > <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN"
    > "http://www.w3.org/TR/html4/strict.dtd">
    > <html>
    > <head>
    > <title>template</title>
    > <style type="text/css">
    > #sm1,#sm2,#sm3 {
    > display: block;
    > }
    > </style>
    >
    > <script type="text/javascript">
    > var buf='<style type="text/css">#sm1, #sm2, #sm3 { display: none;
    > }</style>';
    > document.write(buf);
    > </script>
    >
    > <script type="text/javascript">
    >
    > var menus=new Array('m1', 'm2', 'm3');
    >
    > function toggle(e){
    > var me;
    > if(!e) var e=window.event;
    > if(e.target) me=e.target; // W3C
    > else if(e.srcElement) me=e.srcElement; // MSIE
    > if(me.nodeType == 3) me=me.parentNode; // Safari bug on elements
    > with TEXT
    >
    > var id='s' + me.id;
    > var submenu=document.getElementById(id);
    > me.flag =! me.flag;
    > if(me.flag) submenu.style.display="block";
    > else submenu.style.display="none";
    > }
    >
    > function initMenus(){
    > for( var i=0; i<menus.length; i++){
    > var menu=document.getElementById(menus);
    >
    > //alert('Init ' + menus + ' which is ' + menu.tagName );
    >
    > menu.flag=false;
    >
    > if(menu.addEventListener){
    > menu.addEventListener('click', toggle, false);
    > }
    > else if(menu.attachEvent){ //MS IE support
    > menu.attachEvent('onclick', toggle);
    > }
    > }
    > }
    >
    > // attach event after page loads
    > if( window.addEventListener ) {
    > window.addEventListener('load',initMenus,false); //legacy
    > } else if( document.addEventListener ) {
    > document.addEventListener('load',initMenus,false); //proper
    > } else if( window.attachEvent ) {
    > window.attachEvent("onload", initMenus); //IE only
    > }
    >
    > </script>
    >
    > </head>
    > <body>
    >
    > <ul>
    > <li><a href="#" id="m1">Menu 1</a>
    > <ul id="sm1">
    > <li>Submenu 1.1</li>
    > <li>Submenu 1.2</li>
    > <li>Submenu 1.3</li>
    > </ul>
    > </li>
    > <li><a href="#" id="m2">Menu 2</a>
    > <ul id="sm2">
    > <li>Submenu 2.1</li>
    > <li>Submenu 2.2</li>
    > <li>Submenu 2.3</li>
    > <li>Submenu 2.4</li>
    > </ul>
    > </li>
    > <li><a href="#" id="m3">Menu 3</a>
    > <ul id="sm3">
    > <li>Submenu 3.1</li>
    > <li>Submenu 3.2</li>
    > </ul>
    > </li>
    > <ul>
    >
    > </body>
    > </html>
    >
    > --
    > Take care,
    >
    > Jonathan
    > -------------------
    > LITTLE WORKS STUDIO
    > http://www.LittleWorksStudio.com
     
    Jonathan, Jan 5, 2007
    #4
  5. Jonathan wrote:
    > Jonathan,
    >
    > Is there anything special that I need to do to view your example? I
    > saved your code (as an new html file) and attempted to view it to no
    > avail. What would you suggest me to do to view your example. Thanks
    > for your assistance.


    Nope only that your have JavaScript enabled and DOM1 browser. Mind you
    this just just a strip down example. When first loaded should only see
    the three main menu items. Click one on and the submenu should expand...

    --
    Take care,

    Jonathan
    -------------------
    LITTLE WORKS STUDIO
    http://www.LittleWorksStudio.com
     
    Jonathan N. Little, Jan 5, 2007
    #5
  6. Jonathan

    BootNic Guest

    [snip]
    >> var buf='<style type="text/css">#sm1, #sm2, #sm3 { display: none;
    >> }</style>';

    watch for line wrap
    [snip]
    >> if(me.nodeType == 3) me=me.parentNode; // Safari bug on
    >> elements with TEXT

    watch for line wrap
    [snip]
    > Jonathan <> wrote:
    > news:
    > Jonathan,
    >
    > Is there anything special that I need to do to view your example? I
    > saved your code (as an new html file) and attempted to view it to no
    > avail. What would you suggest me to do to view your example. Thanks
    > for your assistance.


    Fix the line wrap and perhaps it will work for you.

    --
    BootNic Friday, January 05, 2007 11:54 PM

    Optimism and humor are the grease and glue of life. Without both of
    them we would never have survived our captivity.
    *Philip Butler, Vietnam POW*
     
    BootNic, Jan 6, 2007
    #6
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. chlori
    Replies:
    2
    Views:
    482
    Toby A Inkster
    Mar 3, 2004
  2. ste
    Replies:
    11
    Views:
    34,950
    nobbiesp
    Jul 5, 2010
  3. Exch
    Replies:
    0
    Views:
    397
  4. jobs
    Replies:
    0
    Views:
    3,894
  5. jobs
    Replies:
    0
    Views:
    408
Loading...

Share This Page