www.webdeveloper.com
Results 1 to 15 of 15

Thread: Check whether a menu has sub menu

  1. #1
    Join Date
    Sep 2008
    Posts
    47

    Check whether a menu has sub menu

    Hi all

    How can I check whether a menu has submenu? If there is no submenu, I will want the keyboard navigation (using arrow keys) to be at the next menu selected. Any ideas how to do that? I have added the code snippet on that:

    function selectNextMenu() {
    // Moves to the submenu of the current item (if any) or to the next menu
    var index; // Reference to index of current menu
    // Reference to submenu or current menu
    var curMenu = currentMenu || mainMenu;

    if (currentMenuItem && currentMenuItem.submenu) {
    curMenu = currentMenu;
    index = currentMenuItem.index;
    }

    else if (currentMenu){
    curMenu = currentMenu.topMenu;
    index = currentMenu.topItem.index + 1;

    if (index >= curMenu.items.length) {
    curMenu = null;
    }

    }

    else {
    index = 0;
    curMenu = mainMenu;
    }

    if (!curMenu) {
    hidePrevMenu();
    }

    else {
    showSubmenu(curMenu.items[index].submenu);
    }

    }


    Regards
    Nedave

  2. #2
    Join Date
    Feb 2008
    Posts
    1,666
    You're going to have to explain more -- because it looks like this is the correct test for determining if the current menu item has a submenu or not:
    Code:
    if (currentMenuItem && currentMenuItem.submenu) {

  3. #3
    Join Date
    Sep 2008
    Posts
    47

    Re: MrNobody

    Hi MrNobody

    Thanks for your interest in my question. What I means is that I am using <li> for menu items and <ul> for the actual menu itself and that if I were to move from one <ul> to another, the navigation keys does not move to the next menu item.

    Regards
    Nedave

  4. #4
    Join Date
    Feb 2008
    Posts
    1,666
    Well, the code you posted does not show the use of any navigation keys at all.

  5. #5
    Join Date
    Sep 2008
    Posts
    47

    Re: MrNobody

    Hi MrNobody

    Ok. I have posted my codes below. Do let me know if you have further suggestions.

    Regards
    Nedave
    Last edited by nedave; 01-09-2009 at 05:03 PM.

  6. #6
    Join Date
    Feb 2008
    Posts
    1,666
    I don't download files from this site. If you can provide a public link, then I will check it out.

  7. #7
    Join Date
    Sep 2008
    Posts
    47

    Re: MrNobody (Part 1)

    Hi MrNobody

    Thanks. Noted. I have posted all my codes I have at the moment in the messages below. You would need to copy and paste the codes and name individual code snippets accordingly to see it in the browser what I mean. Do let me know your views and any improvements to help me. Your assistance is appreciated.

    File 1: nedave.js

    var currentMenu;
    var currentMenuItem;
    var mainMenu;
    document.write('<link rel="stylesheet" type="text/css" href="nedavejs.css">');

    function hideLastMenu()
    {
    // Hides the last menu
    if (currentMenu) {
    currentMenu.menuUl.style.visibility = 'hidden';
    }
    if (currentMenuItem) {
    currentMenuItem.itemLi.className = '';
    }
    currentMenuItem = currentMenu = null;
    }

    function showSubmenu(submenu)
    {
    // First hides all other menus, then displays the requested submenu in the appropriate position
    hideLastMenu();
    var submenuUl = submenu.menuUl;
    if (!submenuUl) {
    return;
    }
    currentMenu = submenu;
    submenuUl.style.visibility = 'visible';
    if (currentMenu.topMenu === currentMenu.parentMenu) {
    var topItemLi = currentMenu.topItem.itemLi;
    submenuUl.style.left = topItemLi.offsetLeft + 'px';
    submenuUl.style.top = topItemLi.offsetTop + topItemLi.offsetHeight + 'px';
    }
    }

    function showParentMenu()
    {
    submenuUl = currentMenu.parentMenu.menuUl;
    var curMenu = currentMenu;
    hideLastMenu();
    submenuUl.style.visibility = 'visible';
    focusMenuItem(curMenu.parentItem)
    }

    function focusMenuItem(item)
    {
    // Sets the appropriate menu item as current (needed for the arrow key movement)
    if (currentMenuItem) {
    currentMenuItem.itemLi.className = '';
    }
    currentMenu = item.parentMenu;
    currentMenuItem = item;
    item.itemLi.className = 'highlighted';
    }

    function nextTag(el, tagName)
    {
    // Finds the first occurence of a tag at a particular level of the DOM
    while (el) {
    if (el.nodeType === 1) {// i.e. is an element rather than text node, etc.
    if (el.tagName.toLowerCase() === tagName) {
    break;
    }
    }
    el = el.nextSibling;
    }
    return el;
    }

    function Menu(menuUl, parentItem) {
    // menu class
    // creates a menu by parsing the HTML DOM, starting with the ul that has the id 'id'
    // id = id of menu
    // parentItem = item that leads to this menu, if any (will be null for main menu)
    // parentMenu = menu above this menu
    // items = array of menuItems
    // menuUl = reference to the ul in the document that represents this menu
    // hasSubmenu = true if any of the menu items have a submenu
    function MenuItem(id, itemLi, parentMenu, submenuId) {
    // menuItem class
    // id = id of menu item
    // itemLi = reference to the li in the document that represents the menu item
    // index = index to the menu item within the parent menu's array
    // parentMenu = reference to the menu that contains this item
    // submenu = reference to submenu created using by using the submenuId provided, if any
    // topMenu = menu at top of tree (will be null for the top menu itself)
    // topItem = menu item at top of tree that leads to this one
    this.id = id;
    this.itemLi = itemLi;
    this.parentMenu = parentMenu;
    this.index = parentMenu.items.length;
    if (submenuId) {
    this.submenu = new Menu(submenuId, this);
    }
    }
    if (typeof(menuUl) === 'string') {
    menuUl = document.getElementById(menuUl);
    }
    this.id = menuUl.id;
    this.parentItem = parentItem;
    if (parentItem) {
    this.parentMenu = parentItem.parentMenu;
    this.topMenu = this.parentMenu.topMenu;
    this.topItem = this.parentMenu.topItem || this.parentItem;
    }
    else {
    this.topMenu = this;
    this.getMenuById = {};
    }
    this.topMenu.getMenuById[this.id] = this;
    this.items = [];
    this.menuUl = menuUl;
    var ulWidth = menuUl.offsetWidth;
    menuUl.style.width = ulWidth + 40 + 'px'; // Fixes float problem with IE
    var el = nextTag(this.menuUl.firstChild, 'li');
    var numItems = 0;
    if (this.parentMenu && this.parentMenu !== this.topMenu) {
    var backLi = document.createElement('li');
    backLi.id = this.id + numItems;
    numItems ++;
    backLi.appendChild(document.createTextNode('\u21d0 '));
    var child = this.parentItem.itemLi.firstChild.nextSibling;
    while (child && (child.nodeType !== 1 || child.tagName.toLowerCase() !== 'ul')){
    backLi.appendChild(child.cloneNode(true));
    child = child.nextSibling
    }
    this.menuUl.insertBefore(backLi, el);
    this.items[this.items.length] = (new MenuItem(backLi.id, backLi, this));
    }
    // This while loop navigates through the menu, creating items as it finds them
    while (el) {
    // Is there an id already defined? If not, create one
    if (!el.id) {
    el.id = this.id + numItems;
    }
    var submenuUl = nextTag(el.firstChild, 'ul');
    if (submenuUl) {
    // If a submenu exists for this item, then attach the appropriate events to open it on focus
    // If this is already a submenu, we use the showSubSubMenu function which positions the menu to the side.
    // We also append a right arrow to the menu item.
    // If this is the main menu, then we use the showSubMenu function to display the menu underneath.
    submenuUl.id = el.id + '_sub';
    if (parentItem) {
    var arrowDiv = document.createElement('div');
    arrowDiv.className = 'rtarrow';
    arrowDiv.appendChild(document.createTextNode('\u21d2')); // right arrow
    el.insertBefore(arrowDiv, el.firstChild);
    }
    this.items[this.items.length] = (new MenuItem(el.id, el, this, submenuUl));
    this.hasSubmenu = true;
    }
    else {
    // This is a menu item with no submenu
    this.items[this.items.length] = (new MenuItem(el.id, el, this));
    }
    numItems ++;
    el = nextTag(el.nextSibling, 'li');
    }
    }


    function selectNextItem()
    {
    // Moves down through the current menu, looping round if needed
    var index;
    var curMenu;
    if (currentMenuItem) {
    curMenu = currentMenuItem.parentMenu;
    index = currentMenuItem.index + 1;
    if (index >= curMenu.items.length) {
    index = 0;
    }
    }
    else {
    curMenu = currentMenu;
    index = 0;
    }
    if (curMenu.items[index]) {
    focusMenuItem(curMenu.items[index]);
    }
    }

    function selectPrevItem()
    {
    // Moves up through the current menu, looping round if needed
    var index;
    var curMenu;
    if (currentMenuItem) {
    curMenu = currentMenuItem.parentMenu;
    index = currentMenuItem.index - 1;
    if (index < 0) {
    index = curMenu.items.length - 1;
    }
    }
    else {
    curMenu = currentMenu;
    index = curMenu.items.length - 1;
    }
    if (curMenu.items[index]) {
    focusMenuItem(curMenu.items[index]);
    }
    }

    function selectNextMenu()
    {
    // Moves to the submenu of the current item if any, or otherwise to the next menu
    var curMenu;
    var index;
    if (currentMenuItem && currentMenuItem.submenu) {
    curMenu = currentMenu;
    index = currentMenuItem.index;
    }
    else if (currentMenu){
    curMenu = currentMenu.topMenu;
    index = currentMenu.topItem.index + 1;
    if (index >= curMenu.items.length) {
    curMenu = null;
    }
    }
    else {
    curMenu = mainMenu;
    index = 0;
    }
    if (!curMenu) {
    hideLastMenu();
    }
    else {
    showSubmenu(curMenu.items[index].submenu);
    }
    }

    function selectPrevMenu()
    {
    // Moves to the parent menu if any, or if not to the previous menu
    var curMenu = currentMenu || mainMenu;
    var index;
    if (curMenu !== curMenu.topMenu && curMenu.parentMenu !== curMenu.topMenu) {
    // We are currently in a sub-sub menu, so move up
    curMenu = curMenu.parentMenu;
    index = 0;
    }
    else {
    // We are in one of the main submenus, so move to the previous one
    if (currentMenu) {
    curMenu = curMenu.topMenu;
    index = currentMenu.topItem.index - 1;
    }
    else {
    index = curMenu.topMenu.items.length - 1;
    }
    if (index < 0) {
    curMenu = null;
    }
    else {
    curMenu = curMenu.items[index].submenu
    }
    }
    if (!curMenu) {
    hideLastMenu()
    }
    else {
    showSubmenu(curMenu);
    }
    }

    function windowKeydown(e)
    {
    // Implements functionality to allow moving through the menus with the arrow keys
    e = e || event;
    switch (e.keyCode)
    {
    case 40: // down arrow
    if (currentMenu) {
    selectNextItem();
    }
    else {
    return true;
    }
    break;
    case 38: // up arrow
    if (currentMenu) {
    selectPrevItem();
    }
    else {
    return true;
    }
    break;
    case 39: // right arrow
    selectNextMenu();
    break;
    case 37: // left arrow
    selectPrevMenu();
    break;
    default:
    return true;
    }
    return false;
    }


    window.onload = function(){
    mainMenu = new Menu('mainMenu');
    };
    document.onkeydown = windowKeydown;


    Regards
    Nedave
    Last edited by nedave; 11-05-2008 at 05:12 AM.

  8. #8
    Join Date
    Sep 2008
    Posts
    47

    Re: MrNobody (Part 2)

    Hi MrNobody

    This is a continuation from my previous post as the maximum word length for the previous post has exceeded.

    File 2: nedave.html
    <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
    "http://www.w3.org/TR/html4/loose.dtd">
    <html>
    <head>
    <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
    <title>Menu Testing</title>
    <link rel="stylesheet" type="text/css" href="nedavemain.css">
    <script type="text/javascript" src="nedave.js"></script>
    </head>
    <body>
    <div class="aroundmenu">
    <ul id="mainMenu" class="menu">
    <li id="watchingvideos">Watching videos
    <ul>
    <li><a href="LoadingVid.jsp?url=http://98.150.1.100:8080/CH/Media/LP.mpg"><img src="island.png" alt="Island">The Lost Paradise</a></li>
    <li><a href="LoadingVid.jsp?url=http://98.150.1.100:8080/CH/Media/Spiderman3.mpg">Spiderman 3</a></li>
    <li><a href="LoadingVid.jsp?url=http://98.150.1.100:8080/CH/Media/LastSong.mpg">Last Song</a></li>
    <li><a href="LoadingVid.jsp?url=http://98.150.1.100:8080/CH/Media/Sims.mpg">Sims</a></li>
    <li><a href="LoadingVid.jsp?url=http://98.150.1.100:8080/CH/Media/ThePie.mpg">The Pie</a></li>
    <li><a href="LoadingVid.jsp?url=http://98.150.1.100:8080/CH/Media/AVP.mpg">AVP</a></li>
    <li><a href="LoadingVid.jsp?url=http://98.150.1.100:8080/CH/Media/HMT.mpg">HMT</a></li>
    <li><a href="LoadingVid.jsp?url=http://98.150.1.100:8080/CH/Media/JohnnyEnglish.mpg">Johnny English</a></li>
    </ul>
    </li>
    <li id="watchingtv">Watch TV Online
    <ul>
    <li>BBC</li>
    <li>GMT</li>
    <li>HFM</li>
    <li>Discovery</li>
    <li>ESPN</li>
    <li>CNN</li>
    <li>Discovery Channel</li>
    <li>Animal Planet</li>
    <li>National Geographic</li>
    </ul>
    </li>
    <li id="mealselection">Meal Selection <img src="island.png" alt="Island">
    <ul>
    <li id="mealnormal">Normal
    <ul>
    <li id="normalbreakfast">Breakfast
    <ul>
    <li>Western Breakfast</li>
    <li>Oatmeal</li>
    <li>Congee</li>
    </ul>
    </li>
    <li id="normallunch">Lunch
    <ul>
    <li>Chicken Chop</li>
    <li>Chicken Cutlet</li>
    <li>Fish and Chips</li>
    </ul>
    </li>
    <li id="normalteabreak">TeaBreak
    <ul>
    <li>Mixed Fruit Tart</li>
    <li>Green Salad</li>
    <li>Egg Tart</li>
    </ul>
    </li>
    <li id="normaldinner">Dinner
    <ul>
    <li>Fish and Chips</li>
    <li>Economy Rice</li>
    <li>Nasi Lemak</li>
    </ul>
    </li>
    </ul>
    </li>
    <li id="mealmuslim">Muslim
    <ul>
    <li>Breakfast</li>
    <li>Lunch</li>
    <li>TeaBreak</li>
    <li>Dinner</li>
    </ul>
    </li>
    <li id="mealvegetarian">Vegetarian
    <ul>
    <li>Breakfast</li>
    <li>Lunch</li>
    <li>TeaBreak</li>
    <li>Dinner</li>
    </ul>
    </li>
    <li id="viewmeal">View Selected Meal</li>
    </ul>
    </li>
    <li id="internet">Internet</li>
    <li id="pricing">Pricing
    <ul>
    <li>Payment Mode</li>
    <li>Frequently Asked Qns</li>
    <li>Survey</li>
    <li>About Us</li>
    </ul>
    </li>
    <li id="contactus">Contact Us</li>
    </ul>
    </div>
    </body>
    </html>


    File 3: nedavejs.css

    .aroundmenu {
    float: none;
    width: 100&#37;;
    position: fixed;
    top: 0;
    left: 0;
    }

    .menu {
    position: absolute;
    list-style-type: none;
    height: 5em;
    padding-left: 1em;
    padding-top: 0.5em;
    margin-top: 0;
    }

    .menu li{
    float: left;
    margin-left: 1em;
    color: lightcyan;
    background-color: royalblue;
    }

    .menu ul{
    position: absolute;
    left: -1px;
    top: -1px;
    list-style-type: none;
    margin: 0;
    padding: 0;
    background-color: #20D020;
    color: rgb(250, 223, 173);
    visibility: hidden;
    border: solid 1px black;
    }

    .menu ul li a, .menu ul li {
    background-color: #20D020;
    color: rgb(250, 223, 173);
    }

    .menu a {
    text-decoration: none;
    }

    .menu ul ul, .menu ul ul li, .menu ul ul li a {
    background-color: #2020D0;
    color: rgb(250, 223, 173);
    }

    .menu ul li {
    float: none;
    padding: 0.5em 0.5em 0.5em 0.5em;
    margin-left: 0;
    }

    .menu img {
    border: none;
    vertical-align: top;
    }

    .rtarrow {
    float: right;
    }

    div#maincontent {
    padding-top: 6em;
    }

    .submenuTitle {
    font-weight: bold;
    }

    .menu ul li.highlighted, .menu ul li.highlighted a{
    background-color: white;
    color: black;
    }


    File 4: nedavemain.css

    body {
    background: transparent;
    margin: 0;
    padding: 0;
    font-family: Arial, sans-serif;
    }


    .aroundmenu
    {
    float: left;
    width: 25%;
    }


    (NB: You may want to find any image in substitution for the image I added in nedave.html.) I apologised for any inconvenience caused.

    Regards
    Nedave

  9. #9
    Join Date
    Sep 2004
    Location
    At the corner of WALK and DONT WALK
    Posts
    1,745
    So each SubMenu is an unordered list contained in a list item?

  10. #10
    Join Date
    Sep 2008
    Posts
    47

    Re: Mr Initial Man

    Hi Mr Initial Man

    Yes. Thanks for your response to my questions. I am stuck with this problem for quite a long time. I would appreciate greatly if you would be able to help me with this.

    Regards
    Nedave

  11. #11
    Join Date
    Sep 2004
    Location
    At the corner of WALK and DONT WALK
    Posts
    1,745
    Well, it's easy to see if they have submenus: Just look for <li> elements that have <ul> elements in them. And set up all your <ul> elements with ids so you can access them easier.

    I'm not sure how to do the keystrokes, but I hope that helps.

  12. #12
    Join Date
    Sep 2004
    Location
    At the corner of WALK and DONT WALK
    Posts
    1,745
    I should have mentioned that getting your navigation menu should be easy:
    PHP Code:
    var menu document.getElementById('mainMenu'); 
    Work with that. Oh, and it's generally more help to stick your script at the end of the body.

  13. #13
    Join Date
    Sep 2008
    Posts
    47

    Re: Mr Initial Man

    Hi Mr InitalMan

    I do not really understand what you are trying to say. As all the intended JavaScript codes for the menu are meant to be generated dynamically from a Javabean, I cannot manually hard-coded all my <ul> elements with ids in order to access them easily? Or is there a way with it? Is there any option where I can create a function to search for all e images and change its size when it is selected? Anyway, why iz it more helpful to my script at the end of the body? Thanks.

    Regards
    Nedave
    Last edited by nedave; 11-11-2008 at 09:03 AM.

  14. #14
    Join Date
    Sep 2004
    Location
    At the corner of WALK and DONT WALK
    Posts
    1,745
    Quote Originally Posted by nedave View Post
    Hi Mr InitalMan

    I do not really understand what you are trying to say. As all the intended JavaScript codes for the menu are meant to be generated dynamically from a Javabean, I cannot manually hard-coded all my <ul> elements with ids in order to access them easily? Or is there a way with it? Is there any option where I can create a function to search for all e images and change its size when it is selected? Anyway, why iz it more helpful to my script at the end of the body? Thanks.

    Regards
    Nedave
    I'll answer the second question first: If Javascript is at the end of the body, it will be the last thing to load--that is, when it is loaded, the rest of the HTML is loaded into the browser.

    And when I mentioned hardcoding your <ul> elements, I meant doing it in the HTML.

  15. #15
    Join Date
    Sep 2008
    Posts
    47

    Re: Mr InitialMan

    Hi MrInitialMan

    Ok. I get your point for the second question. With regards to the hard coding part, what I am meant is that the JavaBean is meant to pass the HTML string directly to the JSP page which I am working on. As such, I need to create a function to name these <ul> elements as they can be unlimited. Is there any option where I can create a function to search all the images and change its size when it is being selected? Are you able to test out the codes using what I have done up and posted earlier?

    Regards
    Nedave

Thread Information

Users Browsing this Thread

There are currently 1 users browsing this thread. (0 members and 1 guests)

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  
HTML5 Development Center



Recent Articles