Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
241 views
in Technique[技术] by (71.8m points)

javascript - Manipulate jquery menu on re-size for responsive layout

There is simple menu with list itmes. UL LI. width and numbers of LI is dynamic. And there is dropdown kind of thing "more" on hover/click it will show remaining LI , which will not fit available space.

I tried using jquery while user resize windows from right to left, it will hide the last visible menu item. What is the possible way to do this revers and also add LI in "more" link.

Tried some option, as width is less when we resize then list item move below and increase height of UL so using this method I am able to hide last visible. code

http://jsbin.com/flexmenu/2/edit

Step 1

resize of window

Step 2enter image description here

Step 3enter image description here

These steps will be reverse when user re-size (increase the width)

Markup

<div class="twelve columns filter-wrapper">
    <ul class="nav-bar-filter" id="nav-bar-filter">
        <li><a href="#">All</a></li>
        <li><a href="#">Small</a></li>
        <li><a href="#">Medium</a></li>
        <li><a href="#">Extra large</a></li>
        <li><a href="#">Text</a></li>
        <li><a href="#">Small-1</a></li>
        <li><a href="#">Medium-1</a></li>
        <li><a href="#">Extra large text</a></li>
        <li><a href="#">Large text</a></li>
        <li><a href="#">Text</a></li>
    </ul>
<ul id="more-nav">
  <li><a href="#">More > </a>
    <ul class="subfilter"><li><a href="#">Text</a></li></ul>
  </li>    
</ul>
</div>

Basically this menu will be used for responsive layout menu.Any help in this will be helpful. Edit 1: added markup

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Answer

0 votes
by (71.8m points)

Well, I've tried to build some script for doing it, here's what I've got:

$().ready(function () { 

    //we reconstruct menu on window.resize
    $(window).on("resize", function (e) {                                                   
        var parentWidth = $("#nav-bar-filter").parent().width() - 40;
        var ulWidth = $("#more-nav").outerWidth();                  
        var menuLi = $("#nav-bar-filter > li");                 
        var liForMoving = new Array();      
        //take all elements that can't fit parent width to array
        menuLi.each(function () {                       
            ulWidth += $(this).outerWidth(); 
            if (ulWidth > parentWidth) {
                console.log(ulWidth);
                liForMoving.push($(this));
            }
        });                         
        if (liForMoving.length > 0) {   //if have any in array -> move them to "more" ul
            e.preventDefault();                     
            liForMoving.forEach(function (item) {
                item.clone().appendTo(".subfilter");
                item.remove();
            });                         
        }
        else if (ulWidth < parentWidth) { //check if we can put some 'li' back to menu
            liForMoving = new Array();
            var moved = $(".subfilter > li");
            for (var i = moved.length - 1; i >= 0; i--) { //reverse order
                var tmpLi = $(moved[i]).clone();
                tmpLi.appendTo($("#nav-bar-filter"));
                ulWidth += $(moved[i]).outerWidth();
                if (ulWidth < parentWidth) {                                
                    $(moved[i]).remove();
                }
                else {
                    ulWidth -= $(moved[i]).outerWidth();
                    tmpLi.remove();
                }                           
            }                       
        }                       
        if ($(".subfilter > li").length > 0) { //if we have elements in extended menu - show it
            $("#more-nav").show();
        }
        else {
            $("#more-nav").hide();
        }
    });

    $(window).trigger("resize"); //call resize handler to build menu right
});

And JSFiddle sample

Had to change your css styles to make it work properly. What we do is:

  1. Get width of parent container, initial width of main menu is zero, but we probably have to show the additional menu, so we get its size as well.
  2. On window.resize we loop through all elements in main menu (horizontal) accumulating each element width in the ulWidth variable.
  3. Once the width of main menu is more than width of parent container -> we need to move the rest of menu items to the submenu (vertical) - so we push those elements to an array liForMoving.
  4. If array liForMoving isn't empty - we clone its elements, append them to the submenu and remove them from the main menu.
  5. If width of all elements in mainMenu is minor than the width of its container, we need to check if we can move some elements from the submenu to the main one
  6. We iterate through submenu elements, grab each item, append to main menu (if you have different fonts and paddings in menus - final size of element will differ), check if its size is good to fit the parent container. If it is - we remove element from submenu ($(moved[i]).remove()), if it's not - we remove appended element (tmpLi.remove())
  7. Finally we check if the submenu has any items, and show/hide it.

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...