I am trying to convert my dropdown menu on hover to work on click with a bit of JS, but I’m getting nothing when I click. No errors, no suggestion as to where I’m failing.
(function() {
Array.prototype.forEach.call(document.getElementsByClassName("submenu"), function(el) {
el.style.marginTop = "-99px";
el.addEventListener("click", function() {
if (el.style.marginTop === "0") {
el.style.marginTop = "-99px";
} else {
el.style.marginTop = "0";
}
});
})
})();
CSS:
.navWrap {
margin: .75rem auto 0;
padding: 0 var(--gutter);
}
nav {
vertical-align: top;
text-align: left;
text-transform: uppercase;
border-top: 1px solid var(--colour1);
border-bottom: 1px solid var(--colour1);
}
nav ul {
list-style: none;
margin: 0;
padding: 0;
}
nav li {
display: inline-block;
padding: 0 .15em;
}
nav ul ul {
z-index: 1;
position: absolute;
top: auto;
left: -2em;
right: -2em;
text-align: center;
margin-top: -99em;
padding: 0 .25em;
} /*
nav ul li:hover ul {
margin-top: 0;
} */
nav ul ul li {
display: block;
width: auto;
}
nav a {
display: block;
text-decoration: none;
background-color: #fff;
color: #507399;
padding: .4em 0;
transition: color .3s ease-in-out;
box-shadow: none;
}
Shortened menu:
<div class="navWrap">
<nav>
<ul>
<li><a href="church.php">St Andrew’s</a></li>
<li><a href="#">Social</a>
<ul class="submenu">
<li><a href="village-hall.php">Village Hall</a></li>
<li><a href="events.php">Events</a></li>
</ul>
</li>
</ul>
</nav>
</div>
The problem is that the anchor tag is receiving the click and the event handler isn’t firing.
You can achieve what you want like this:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<title>Dropdown</title>
<style>
.navWrap {
margin: .75rem auto 0;
padding: 0 var(--gutter);
}
nav {
vertical-align: top;
text-align: left;
text-transform: uppercase;
border-top: 1px solid var(--colour1);
border-bottom: 1px solid var(--colour1);
}
nav ul {
list-style: none;
margin: 0;
padding: 0;
}
nav li {
display: inline-block;
padding: 0 .15em;
}
nav ul ul {
z-index: 1;
position: absolute;
top: auto;
left: -2em;
right: -2em;
text-align: center;
margin-top: -99em;
padding: 0 .25em;
}
nav ul ul li {
display: block;
width: auto;
}
nav a, .submenu > span {
display: block;
text-decoration: none;
background-color: #fff;
color: #507399;
padding: .4em 0;
transition: color .3s ease-in-out;
box-shadow: none;
}
.submenu ul {
margin-top: -99px;
}
.submenu > span:hover {
cursor: pointer;
}
</style>
</head>
<body>
<div class="navWrap">
<nav>
<ul>
<li><a href="church.php">St Andrew’s</a></li>
<li class="submenu">
<span>Social</span>
<ul>
<li><a href="village-hall.php">Village Hall</a></li>
<li><a href="events.php">Events</a></li>
</ul>
</li>
</ul>
</nav>
</div>
<script>
const submenus = document.querySelectorAll('.submenu');
[...submenus].forEach((subMenu) => {
const dropDown = subMenu.querySelector('ul');
subMenu.addEventListener('click', () => {
if (dropDown.style.marginTop === '0px') {
dropDown.style.marginTop = '-99px';
} else {
dropDown.style.marginTop = '0px';
}
});
});
</script>
</body>
</html>
Maybe you could also keep the CSS to make it hover, then remove it in your JS so that teh menu works if JS is disabled.
HTH
2 Likes
Hi there gandalf458,
have you considered using a possible CSS
only solution, like this example perhaps…
<!DOCTYPE HTML>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width,height=device-height,initial-scale=1">
<title>Untitled Document</title>
<!--<link rel="stylesheet" href="screen.css" media="screen">-->
<style media="screen">
ul {
margin: 0;
padding: 0;
list-style: none;
}
li {
display: inline-block;
padding: 0 0.15em;
}
ul ul {
position: absolute;
z-index: 1;
top: auto;
left: -2em;
right: -2em;
margin-top: -99em;
padding: 0 0.25em;
text-align: center;
}
ul ul li {
display: block;
width: auto;
}
a, label {
display: block;
padding: 0.4em 0;
background-color: #fff;
color: #507399;
text-decoration: none;
transition: color 0.5s ease-in-out;
box-shadow: none;
cursor: pointer;
}
#cb1:checked ~ ul .submenu1,
#cb2:checked ~ ul .submenu2 {
margin-top: 0;
}
#cb1:checked ~ ul label[for=cb1],
#cb2:checked ~ ul label[for=cb2] {
color: #f00;
}
</style>
</head>
<body>
<input id="cb1" type="radio" name="r" hidden>
<input id="cb2" type="radio" name="r" hidden>
<input id="cb3" type="radio" name="r" hidden>
<ul>
<li><a href="church.php">St Andrew’s</a></li>
<li><a href="#"><label for="cb1">Social</label></a>
<ul class="submenu1">
<li><a href="village-hall.php">Village Hall</a></li>
<li><a href="events.php">Events</a></li>
</ul>
</li>
<li><a href="#"><label for="cb2">Other Stuff</label></a>
<ul class="submenu2">
<li><a href="#">Link 1</a></li>
<li><a href="#">Link 2</a></li>
</ul>
</li>
<li><a href="#"><label for="cb3">Close Dropdown</label></a>
</ul>
</body>
</html>
coothead
3 Likes
Many thanks guys. Two options, I am a lucky wizard!
2 Likes
Gandalf
Closed
June 14, 2020, 10:16pm
5
This topic was automatically closed 91 days after the last reply. New replies are no longer allowed.