diff --git a/app/assets/javascripts/application.js b/app/assets/javascripts/application.js index ead01a8ff8..62387fc330 100644 --- a/app/assets/javascripts/application.js +++ b/app/assets/javascripts/application.js @@ -70,21 +70,76 @@ $(document).ready(function () { // See https://turbo.hotwired.dev/reference/drive#turbo.session.drive Turbo.session.drive = false; - var headerWidth = 0, - compactWidth = 0; + var $expandedSecondaryMenu = $("header nav.secondary > ul"), + $collapsedSecondaryMenu = $("#compact-secondary-nav > ul"), + secondaryMenuItems = [], + moreItemWidth = 0, + breakpointWidth = 768; function updateHeader() { var windowWidth = $(window).width(); - if (windowWidth < compactWidth) { - $("body").removeClass("compact-nav").addClass("small-nav"); - } else if (windowWidth < headerWidth) { - $("body").addClass("compact-nav").removeClass("small-nav"); + if (windowWidth < breakpointWidth) { + $("body").addClass("small-nav"); + expandAllSecondaryMenuItems(); } else { - $("body").removeClass("compact-nav").removeClass("small-nav"); + $("body").removeClass("small-nav"); + var availableWidth = $expandedSecondaryMenu.width(); + secondaryMenuItems.forEach(function (item) { + $(item[0]).remove(); + }); + var runningWidth = 0, + i = 0, + requiredWidth; + for (; i < secondaryMenuItems.length; i++) { + runningWidth += secondaryMenuItems[i][1]; + if (i < secondaryMenuItems.length - 1) { + requiredWidth = runningWidth + moreItemWidth; + } else { + requiredWidth = runningWidth; + } + if (requiredWidth > availableWidth) { + break; + } + expandSecondaryMenuItem($(secondaryMenuItems[i][0])); + } + for (; i < secondaryMenuItems.length; i++) { + collapseSecondaryMenuItem($(secondaryMenuItems[i][0])); + } } } + function expandAllSecondaryMenuItems() { + secondaryMenuItems.forEach(function (item) { + expandSecondaryMenuItem($(item[0])); + }); + } + + function expandSecondaryMenuItem($item) { + $item.children("a") + .removeClass("dropdown-item") + .addClass("nav-link") + .addClass(function () { + return $(this).hasClass("active") ? "text-secondary-emphasis" : "text-secondary"; + }); + $item.addClass("nav-item").insertBefore("#compact-secondary-nav"); + toggleCompactSecondaryNav(); + } + + function collapseSecondaryMenuItem($item) { + $item.children("a") + .addClass("dropdown-item") + .removeClass("nav-link text-secondary text-secondary-emphasis"); + $item.removeClass("nav-item").appendTo($collapsedSecondaryMenu); + toggleCompactSecondaryNav(); + } + + function toggleCompactSecondaryNav() { + $("#compact-secondary-nav").toggle( + $collapsedSecondaryMenu.find("li").length > 0 + ); + } + /* * Chrome 60 and later seem to fire the "ready" callback * before the DOM is fully ready causing us to measure the @@ -92,20 +147,10 @@ $(document).ready(function () { * to defer the measurement slightly as a workaround. */ setTimeout(function () { - $("header").children(":visible").each(function (i, e) { - headerWidth = headerWidth + $(e).outerWidth(); + $expandedSecondaryMenu.find("li:not(#compact-secondary-nav)").each(function () { + secondaryMenuItems.push([this, $(this).width()]); }); - - $("body").addClass("compact-nav"); - - $("header").children(":visible").each(function (i, e) { - compactWidth = compactWidth + $(e).outerWidth(); - }); - - $("body").removeClass("compact-nav"); - - $("header").removeClass("text-nowrap"); - $("header nav.secondary > ul").removeClass("flex-nowrap"); + moreItemWidth = $("#compact-secondary-nav").width(); updateHeader(); diff --git a/app/assets/stylesheets/common.scss b/app/assets/stylesheets/common.scss index b179ec5ada..44e84585e2 100644 --- a/app/assets/stylesheets/common.scss +++ b/app/assets/stylesheets/common.scss @@ -131,10 +131,6 @@ header { font-size: 14px; } - nav.primary { - margin-right: auto; - } - .username { max-width: 12em; } @@ -174,7 +170,11 @@ nav.primary { nav.secondary { .nav-link { - padding: 0.3rem; + padding: 0 0.3rem; + } + + > ul { + height: 1.5em; } } @@ -191,15 +191,6 @@ nav.primary, nav.secondary { display: none; } -body.compact-nav { - #compact-secondary-nav { - display: inline-block; - } - .compact-hide { - display: none; - } -} - body.small-nav { #menu-icon { display: block; @@ -236,6 +227,10 @@ body.small-nav { nav.secondary { flex-direction: column; + > ul { + height: auto; + } + .user-menu, .login-menu { width: 100%; } diff --git a/app/helpers/application_helper.rb b/app/helpers/application_helper.rb index fcf253289e..20170f2b4c 100644 --- a/app/helpers/application_helper.rb +++ b/app/helpers/application_helper.rb @@ -42,7 +42,7 @@ def body_class end def header_nav_link_class(path) - ["nav-link", current_page?(path) ? "text-secondary-emphasis" : "text-secondary"] + ["nav-link", current_page?(path) ? "active text-secondary-emphasis" : "text-secondary"] end def application_data diff --git a/app/views/layouts/_header.html.erb b/app/views/layouts/_header.html.erb index ff95be2f5b..58f3c424b6 100644 --- a/app/views/layouts/_header.html.erb +++ b/app/views/layouts/_header.html.erb @@ -27,59 +27,43 @@ -