Home > Back-end >  How do I convert a hover dropdown menu to a clickable sidebar dropdown menu on mobile?
How do I convert a hover dropdown menu to a clickable sidebar dropdown menu on mobile?

Time:10-18

I'm building a navigation menu on my website and I've ran into a problem regarding a dropdown sub-menu on mobile. On desktop, using w3Schools as a reference, I created a sub-menu that displays a ul on hover.

On mobile, however, I'm having two problems:

  • The first is that I want to be able to click to open the menu. I've tried to look into solutions for having a clickable menu toggle on mobile and a hover toggle on desktop, but I don't know much about javascript and wouldn't know where to start. I've also tried making the menu open by clicking on both desktop and mobile, but I would prefer if it was hoverable on desktop.
  • I also want the menu to display differently on mobile and tablet. I want it to be a block that spans the width of my popout sidebar rather than a popup as it is on desktop. I've tried to style the menu differently to make it fit my vision (almost like an accordion dropdown), but it opens over the top of my other list items. Instead, I want it to open and push down the list items.

Any help would be appreciated!

Here's my code (this version includes a click-to-open menu on desktop and mobile):

/* When the user clicks on the button,
toggle between hiding and showing the dropdown content */
function subOpen() {
  document.getElementById("myDropdown").classList.toggle("show");
}

// Close the dropdown menu if the user clicks outside of it
window.onclick = function(event) {
  if (!event.target.matches('.sub-menu-link')) {
    var dropdowns = document.getElementsByClassName("sub-menu-content");
    var i;
    for (i = 0; i < dropdowns.length; i  ) {
      var openDropdown = dropdowns[i];
      if (openDropdown.classList.contains('show')) {
        openDropdown.classList.remove('show');
      }
    }
  }
}


//Code for hamburger menu toggle
const menuBtn = document.querySelector(".menu-btn");
let menuOpen = !1;
menuBtn.addEventListener("click", () => {
  menuOpen ? (menuBtn.classList.remove("open"), menuOpen = !1, document.documentElement.style.overflow = "scroll", document.body.scroll = "yes") : (menuBtn.classList.add("open"), menuOpen = !0, document.documentElement.style.overflow = "hidden", document.body.scroll = "no")
})
body {
  margin: 0;
  font-family: -apple-system, BlinkMacSystemFont, Segoe UI, Roboto, Helvetica Neue, Arial, Noto Sans, sans-serif, Apple Color Emoji, Segoe UI Emoji, Segoe UI Symbol, Noto Color Emoji;
  font-size: 1rem;
  font-weight: 400;
  line-height: 1.5;
  color: #333;
  background-color: #fff;
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
}

a {
  text-decoration: none;
}

.header-cont {
  display: flex;
  max-width: 1350px;
  margin: auto;
  justify-content: space-between;
  padding: 0 1rem 0 1rem;
  box-sizing: border-box;
}

.header-cont,
.nav-link {
  align-items: center;
}

.header-nav,
.nav-item {
  height: 60px;
}

.header {
  background: #fff;
  box-shadow: 0 0 10px -3px rgb(0 0 0 / 50%);
}

.header-cont {
  display: flex;
  max-width: 1350px;
  margin: auto;
  justify-content: space-between;
  padding: 0 1rem 0 1rem;
  box-sizing: border-box;
}

.nav-link,
.sub-menu-link {
  padding: 0 1rem 0 1rem;
  font-weight: 600;
  color: #0f0f0f !important;
  cursor: pointer;
}

.sub-menu-link:after {
  position: absolute;
  right: 15px;
  content: "⌃";
  font-size: 15px;
  border: none;
  transform: rotate(180deg);
  visibility: hidden!important;
}

.header-menu {
  margin-right: 20px;
}

.header-menu li:last-child {
  margin-bottom: 0;
  padding-bottom: 0;
}

.only-mobile {
  display: none !important;
}

.nav-item,
.nav-link {
  display: inline-block;
}

.nav-item {
  line-height: 60px;
}

.drop-chevron {
  margin-left: 10px;
  height: 13px;
  fill: #0f0f0f;
}

.nav-item:hover svg {
  fill: #00007a !important;
}

.nav-item:hover {
  background-color: #00007a0d;
  transition: background-color 0.3s;
}

.nav-link:hover,
.sub-menu-link:hover {
  color: #00007a !important;
  transition: 0.3s;
  text-decoration: none !important;
}

.sub-menu {
  position: relative !important;
}

.sub-menu-link {
  display: inline-block !important;
  text-decoration: none !important;
}

#check,
.checkbtn {
  display: none;
}

.sub-menu-content {
  display: none;
  margin-top: -0.1rem;
  background-color: #fff !important;
  box-shadow: 0 6px 14px -1px rgb(0 5 20 / 15%);
  border-radius: 3px;
  overflow: hidden;
  position: absolute;
  width: 200px;
  z-index: 1000;
}

.sub-menu-content ul {
  list-style-type: none;
  line-height: 30px;
}

.sub-item {
  width: 200px;
  margin-left: -0.5rem;
}

.sub-menu-content li:last-child {
  border-bottom: 1px solid transparent !important;
  padding-bottom: 0.1rem !important;
  margin-bottom: -0.2rem;
}

.sub-menu-content a {
  color: #0f0f0f;
  width: 100%;
  padding: 0.8rem;
  margin-left: -2rem;
  text-decoration: none;
  display: block;
  text-align: left;
  border-left: solid 4px transparent;
}

.sub-menu-content a:hover {
  text-decoration: none;
  border-left: 4px solid #ff9f1c;
  background-color: #00007a0d;
  color: #00007a !important;
}


/*.sub-menu:hover .sub-menu-content {
    display: block;
}*/

.checkbtn {
  font-size: 20px;
  color: #00007a;
  float: right;
  line-height: 60px;
  margin-right: 1rem;
  cursor: pointer;
}

@media (max-width: 1025px) {
  selector .header-logo {
    margin-top: 0.1rem;
    padding-top: 0;
  }
  .header-cont {
    justify-content: space-between;
  }
  .only-mobile,
  .sub-menu-link {
    display: block !important;
  }
  .checkbtn,
  .nav-link,
  .sub-menu {
    display: block;
  }
  .drop-chevron {
    display: none;
  }
  .sub-menu-content {
    padding: 0 18px;
    background-color: white;
    display: none;
    overflow: hidden;
    position: relative!important;
    box-shadow: none;
    border-radius: 0px!important;
  }
  .sub-menu-link:after {
    visibility: visible!important;
  }
  .sub-item {
    border-top: none;
    margin-left: -1rem;
    margin-top: 0rem;
    margin-bottom: 0px;
    box-sizing: border-box;
    line-height: 3rem;
    border-bottom: solid 1px #B5B5B5;
  }
  .sub-menu-content li:last-child {
    padding-bottom: 0rem!important;
    margin-bottom: 0rem;
  }
  .sub-menu-content a {
    color: #0f0f0f;
    width: 100%;
    padding: 8px;
    margin-left: 0rem;
    text-decoration: none;
    display: block;
    border-left: none;
  }
  .sub-menu-content a:hover {
    text-decoration: none;
    border-left: none;
    background-color: #00007a0d;
    color: #00007a!important;
  }
  .header-menu {
    position: absolute;
    margin-top: 60px;
    width: 80%;
    height: 100vh;
    background: #e8e8e8;
    left: -100%;
    text-align: left;
    transition: 0.5s;
    margin-right: 0;
    padding: 0;
    box-shadow: rgb(18 18 18 / 8%) 4px 4px 12px 0;
    overflow: hidden!important;
  }
  .header-menu li:first-child {
    margin-top: 0;
  }
  .header-menu :last-child {
    padding-bottom: 0 !important;
  }
  .nav-item {
    border-top: none;
    margin-left: 0;
    box-sizing: border-box;
    border-bottom: 1px solid #b5b5b5;
    width: 100%;
    text-align: left;
    line-height: 60px;
    height: 60px;
    display: block;
  }
  .nav-link:hover,
  .sub-menu-link:hover {
    background: #00007a0d;
    transition-duration: 0.25s;
  }
  #check:checked~ul {
    left: 0;
  }
}

.menu-btn {
  position: relative;
  display: flex;
  justify-content: center;
  align-items: center;
  width: 22px;
  height: 60px;
  cursor: pointer;
  transition: 0.5s ease-in-out;
}

.menu-btn__burger,
.menu-btn__burger::after,
.menu-btn__burger::before {
  width: 22px;
  height: 2.5px;
  background: #00007a;
  border-radius: 3px;
  transition: 0.3s ease-in-out;
}

.menu-btn__burger::after,
.menu-btn__burger::before {
  content: "";
  position: absolute;
}

.menu-btn__burger::before {
  transform: translateY(-6.5px);
}

.menu-btn__burger::after {
  transform: translateY(6.5px);
}

.menu-btn.open .menu-btn__burger {
  background: 0 0;
  box-shadow: none;
}

.menu-btn.open .menu-btn__burger::before {
  transform: rotate(45deg);
}

.menu-btn.open .menu-btn__burger::after {
  transform: rotate(-45deg);
}


/* Show the dropdown menu (use JS to add this class to the .dropdown-content container when the user clicks on the dropdown button) */

.show {
  display: block;
}

.submenu {
  list-style-type: none!important;
}

.subitem {
  padding: 15px;
}

.submenu {
  display: none;
}

.submenu-active .submenu {
  display: block;
}

.has-submenu:after {}

.has-submenu>a::after {
  line-height: 16px;
  font-weight: 600;
  font-size: 15px;
  border: none;
  color: #0f0f0f;
  padding-right: 0.3rem;
  padding-top: 0.2rem;
  display: inline-block;
  content: "⌃";
  transform: rotate(180deg);
}

.subitem a {
  padding: 10px 15px;
}

.submenu-active {
  background-color: #111;
  border-radius: 3px;
}

.submenu-active .submenu {
  display: block;
  position: absolute;
  left: 0;
  top: 68px;
  background: #111;
}

.submenu-active {
  border-radius: 0;
}
<div >
  <div >
    <div >
      <a aria-hidden="true" href="/">
      LOGO
</a>
    </div>
    <nav >
      <input type="checkbox" id="check">
      <label for="check" >
          <div >
    <div ></div>
  </div>
      </label>

      <ul >
        <li >
          <div >
            <a onclick="subOpen()" >link 1<svg  xmlns="http://www.w3.org/2000/svg" viewBox="0 0 512 512"><path d="M233.4 406.6c12.5 12.5 32.8 12.5 45.3 0l192-192c12.5-12.5 12.5-32.8 0-45.3s-32.8-12.5-45.3 0L256 338.7 86.6 169.4c-12.5-12.5-32.8-12.5-45.3 0s-12.5 32.8 0 45.3l192 192z"/></svg></a>
            <div id="myDropdown" >
              <ul>
                <li ><a href="#">sub link 1</a></li>
                <li ><a href="#">sub link 2</a></li>
                <li ><a href="#">sub link 3</a></li>
                <li ><a href="#">sub link 4</a></li>
              </ul>
            </div>
          </div>
        </li>

        <li ><a href="#" >link 2</a></li>
        <li ><a href="#" >link 3</a></li>
        <li ><a href="#" >link 4</a></li>
      </ul>
    </nav>
  </div>
</div>

CodePudding user response:

Add this to your CSS:

@media(min-width: 1025px){
.sub-menu:hover .sub-menu-content {
  display: block;
  }
  }

This will make sure when the screen width is larger than 1025px (such as on a desktop and not mobile) your hover function will work to show the sub menu.

CodePudding user response:

You can use Media Queries. Here are 2 helpful pages: Link 1 Link 2

  • Related