#javascript #jquery
Всем привет! Подскажите, как можно реализовать такое меню (на jQuery): Схематично нарисовано: Суть работы: При уменьшении размера экрана (.on('resize') или при маленьком экране, пункты меню которые не помещаются $(document).width(), перемещаются из главного ul списка в второстепенный, как показано на картинке. При обратном действии (т.е при увеличении размера экрана), пункты меню которые уже можно отобразить - отображать. Ширина li - автоматическая, в зависимости от содержимого. Мое решение: В массив занес все значения ширины каждого отдельного элемента li. После загрузки страницы и изменения размера экрана, выполнял функцию, которая: Проверяла ширину всего меню и ширину всего документа. ЕСЛИ ширина документа меньше ширины меню: меню.children('li').slice(последний-элемент).prependTo(второстепенное-меню); В рекурсии прогонял, пока, не подтверждалась, ЧТО ширина документа больше ширины меню, тогда, пытался вставить первый пункт второстепенного меню в конец и проверить еще раз ширину меню и ширину экрана(окна). Если, при этом, ширина меню меньше ширины экрана, то добавлял элемент в главное меню: второстепенное-меню.children('li').slice(0, 1).appendTo(меню); Все работало, НО работало очень плохо - постоянно мигало, иногда вставляло элемент, когда он не подходил по ширине. Вот такая вот "печальбеда" Интересно, как бы вы решили такую задачу (алгоритм - что проверять? от чего отталкиваться)? Возможно, есть уже готовое решение моей проблемы? Может есть какая-то библиотека jQuery? Только учусь...
Ответы
Ответ 1
попробуйте так $().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 em 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 }); body { font-family: verdana; color: #999999; font-size: 12px; font-weight: bold; text-transform: uppercase; } .row { width: 1020px; } #more-nav { display: none; vertical-align: top; padding-left: 0; width: 150px; } .subfilter { padding-left: 0; } .subfilter>li { padding: 0 8px; list-style-type: none; } .subfilter>li>a { display: block; padding: 4px 8px; } #nav-bar-filter>li { display: inline-block; } #nav-bar-filter { padding-left: 0; } a { text-decoration: none; color: inherit; } li { list-style-type: none; padding: 0 8px; } #nav-bar-filter, #more-nav { display: inline-block; } .subfilter { display: block; }
Комментариев нет:
Отправить комментарий