menu doesn't hide on second click - javascript

I'm facing a problem with a hamburger menu...
When I click on the hamburger icon there is no problem, it opens and closes without any problem, also when I click on a link I am well redirected to the sections and the menu closes, no problem so far.
But when i re open the menu and click a second time on a link section, my menu no longer wants to close and I can't figure it out why because i've put a condition, it must have a problem somewhere.. So please if you could help me to understand. Thank you very much. Here is my code :
html :
<header id="home" class="background-color">
<div id="logo">
<img src="./img/logo.svg" alt="logo">
</div>
<nav id="menu-dekstop">
Accueil
Projets
Contact
</nav>
<div class="show-menu">
<div id="logo">
<img src="./img/logo.svg" alt="logo">
</div>
</div>
<div id="menu-wrap">
<nav class="menu">
Accueil
Projets
Contact
</nav>
</div>
<div id ="menu-holder" class="menu-holder">
<button id="open-menu" class="white">
<div class="burger">
<span></span>
</div>
</button>
</div>
</header>
JavaScript
burger.addEventListener('click', menuOpen)
function menuOpen()
{
if (showMenu.style.display == 'block')
{
burger.classList.toggle('active');
menuWrap.style.display = 'none';
showMenu.style.display = 'none';
}
else
{
burger.classList.toggle('active');
menuWrap.style.display = 'block';
showMenu.style.display = 'block';
}
}

There appears to be no listener that closes the menu upon a link click.
This code will accomplish a menu hide upon link click in the header:
const header = document.getElementById('home');
header.addEventListener('click', function (evt) {
const clickTarget = evt.target;
if (clickTarget.tagName !== 'A") { return; }
burger.classList.remove('active);
menuWrap.style.display = 'none';
showMenu.style.display = 'none';
});
Why did the menu get hidden the first time a link was clicked? Not sure, but I suspect it's because the first link click caused a page reload.

Related

Open/Close Animated Hamburger Menu when Clicking Button

I'm using an animated hamburger menu (https://jonsuh.com/hamburgers/) to open a full screen menu. It's all working as expected, but I can't figure out how to have the menu close on click (and of course reverse the animation).
I was able to add the class 'is-active' using JS, and adding "onclick="openNav()" works fine, but it seems like creating onclick="toggleNav()" might be more appropriate, I just can't seem to figure out how to write that in JS.
function openNav() {
document.getElementById("popUpNav").style.height = "100%";
}
function closeNav() {
document.getElementById("popUpNav").style.height = "0%";
}
// Hamburger Menu Spin
var hamburger = document.querySelector(".hamburger");
hamburger.addEventListener("click", function() {
hamburger.classList.toggle("is-active");
});
<link href="https://cdnjs.cloudflare.com/ajax/libs/hamburgers/0.9.3/hamburgers.css" rel="stylesheet"/>
<!-- Full Screen Navigation -->
<div id="primaryNav">
<nav>
<!-- Spinning Hamburger Button -->
<button class="hamburger hamburger--spin" type="button" aria-label="Menu" aria-controls="navigation" aria-expanded="false" onclick="openNav()">
<span class="hamburger-box">
<span class="hamburger-inner"></span>
</span>
</button>
<div id="popUpNav" class="overlay" onclick="closeNav()">
<div class="overlay-content">
Link 1
Link 2
Link 3
Link 4
</div>
</div>
</nav>
</div><!-- End Primary Nav -->
What I did:
Whenever the hamburger is being clicked, then we're going to check if it's already have is-active class. If it does, then it means the menu is currently active, and we should call closeNav in this scenario. If it doesn't have is-active class, then it means we should call openNav.
closeNav and openNav will:
Add/Remove the class is-active from the hamburger.
Add/Remove the style of the menu.
PS:
Since you didn't provide your whole code, then we couldn't realy see if the current menu is 0% height or 100% height. so I changed it to display block/none only to show you that it works.
I removed the onclick attribute from the menu, since you already have an EventListener for it.
Make sure you don't include the link I provided in the example.
function openNav() {
hamburger.classList.add("is-active");
document.getElementById("popUpNav").style.display = "block";
}
function closeNav() {
hamburger.classList.remove("is-active");
document.getElementById("popUpNav").style.display = "none";
}
// Hamburger Menu Spin
var hamburger = document.querySelector(".hamburger");
hamburger.addEventListener('click', () => hamburger.classList.contains('is-active') ? closeNav() : openNav());
closeNav();
<link href="https://cdnjs.cloudflare.com/ajax/libs/hamburgers/0.9.3/hamburgers.css" rel="stylesheet"/>
<!-- Full Screen Navigation -->
<div id="primaryNav">
<nav>
<!-- Spinning Hamburger Button -->
<button class="hamburger hamburger--spin" type="button" aria-label="Menu" aria-controls="navigation"
aria-expanded="false">
<span class="hamburger-box">
<span class="hamburger-inner"></span>
</span>
</button>
<div id="popUpNav" class="overlay" onclick="closeNav()">
<div class="overlay-content">
Link 1
Link 2
Link 3
Link 4
</div>
</div>
</nav>
</div><!-- End Primary Nav -->

When clicked inside div that is toggled to show, it toggles up

I have an annoying problem, I have a button that toggles a dropdown, my intention is to hide the div when clicked on the button again, which toggle achieves, and to hide the dropdown when clicked outside why my current jquery does. However when clicking inside the div itself, it slides back up.
HTML >
<div class="navPanel">
<!-- NAV -->
<nav>
<ul id="navBar">
<div class="dynamicNav">
<div class="menu1Container">
<li class="menu1">Books
<!-- DropDown1-->
<div id="dropdownContainer-1">
</div>
</li>
</div>
</div>
</ul>
</nav>
Jquery >
$(function(){
$(".menu1").click(function(){
$("#dropdownContainer-1").slideToggle(90);
});
$(document).click(function(event) {
if (!$(event.target).is(".menu1") && !$(event.target).is(".menu1")) {
$("#dropdownContainer-1").slideUp(90); //make all inactive
}
});
});
The obvious problem is event target, I tried using a similar method ->
$(document).click(function(e) {
var target = e.target;
if (!$(target).is('.menu1') && !$(target).parents().is('.menu1')) {
$('#dropdownContainer-1').slideUp(90);
}
});
If you could help me figure this one out, I'd appreciate it!
You may use:
$(event.target).closest(".menu1").length == 0
$(".menu1").click(function(e){
e.stopPropagation(); // avoid to propagate to document click
if ($(event.target).is(".menu1")) {
$("#dropdownContainer-1").slideToggle(90);
console.log('Menu1 toggled clicking menu1');
}
});
$(document).click(function(event) {
if ($(event.target).closest(".menu1").length == 0 &&
$("#dropdownContainer-1").is(':visible')) {
// if not inside area of menu1
$("#dropdownContainer-1").slideUp(90); //make all inactive
console.log('Menu1 closed clicking outside menu1');
}
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class="navPanel">
<!-- NAV -->
<nav>
<ul id="navBar">
<div class="dynamicNav">
<div class="menu1Container" style="border-style: dotted;width:50%;">
<li class="menu1">Books
<!-- DropDown1-->
<div id="dropdownContainer-1">
<p>1111</p>
<p>1111</p>
<p>1111</p>
<p>1111</p>
<p>1111</p>
</div>
</li>
</div>
</div>
</ul>
</nav>
</div>

Jquery - Click event doesn't work after resized

I'm doing a responsive menu that check the window.resize event and, when it fits the minimum browser width, a click function for a button is allowed. If the browser width is greater, then the click function is unbound. I need to do this because the same element that is the button on the mobile version, is a visual element on the desktop version.
The problem is that, with the code that I have now, when the page is loaded (desktop or mobile screen), the click function works fine. But, if I resize the browser and click on the element again, it doesn't work. If I want to mobile nav works, I need to refresh the page to make it work. Really annoying.
To help understand what is happening, I've made a simple example. Here's is the simple code (just to check the click function issue)
HTML
<!-- WRAPPER -->
<div id="freakers-wrapper">
<!-- HEADER -->
<header id="header">
<div class="header-bottom">
<div class="container">
<div class="row">
<div class="col-md-5">
<!-- MENU -->
<nav class="menu-wrapper-left">
<a class="menu-trigger" href="#">
<span></span>
</a>
<ul id="main-menu" class="menu menu--main menu--left main-menu">
<li>Home</li>
<li class="has-children">
Shop
<ul class="sub-menu is-hidden">
<li class="go-back">Back</li>
<li>Shop 1</li>
<li>Shop 2</li>
<li>Shop 3</li>
</ul>
</li>
<li><a href="#" >Blog</a></li>
</ul> <!-- end main-menu -->
</nav> <!-- end menu-wrapper -->
</div>
<div class="col-md-2">
<div class="logo">
<a href="#">
<img src="images/logo.png" alt="Logo" class="img-responsive">
</a>
</div>
</div>
<div class="col-md-5">
<!-- MENU -->
<nav class="menu-wrapper-right">
<ul id="main-menu" class="menu menu--main menu--right main-menu">
<li>help</li>
<li>lookbook</li>
<li>model</li>
</ul> <!-- end main-menu -->
</nav> <!-- end menu-wrapper -->
</div>
</div>
</div>
</div> <!-- end header-bottom -->
</header> <!-- end header -->
<!-- MOBILE NAV -->
<div id="mobile-nav"></div>
</div> <!-- end freakers-wrapper -->
JS
(function($) {
"use strict";
$(document).ready(function () {
$(window).on('load resize', function(){
moveNavigation();
});
/* ----------------------------------------------------------------------
Main Menu
---------------------------------------------------------------------- */
//if you change this breakpoint, don't forget to update this value as well
var MqL = 1030,
menuLeft = $('.menu-wrapper-left').html(),
menuRight = $('.menu-wrapper-right').html();
console.log(menuRight);
console.log(menuLeft);
//move nav element position according to window width
// moveNavigation();
//mobile - open lateral menu clicking on the menu icon
$(document).on('click', '.menu-trigger', function(event){
event.preventDefault();
if($('#freakers-wrapper').hasClass('push-content')){
closeNav();
}else{
$('#freakers-wrapper').addClass('push-content');
$('#mobile-nav .menu').addClass('menu--open');
$(this).addClass('nav-is-visible');
}
});
//open submenu
$('.has-children').on('click', function(event){
var selected = $(this);
if( selected.children('ul').hasClass('is-hidden') ) {
selected.children('ul').removeClass('is-hidden');
}
});
//submenu items - go back link
$('.go-back').on('click', function(evt){
evt.stopPropagation();
$(this).parent('ul')
.addClass('is-hidden')
.parent('.has-children')
.parent('ul');
});
function closeNav(){
$('#freakers-wrapper').removeClass('push-content');
$('.menu--main').removeClass('menu--open');
$('.has-children ul').addClass('is-hidden');
}
function checkWindowWidth() {
//check window width (scrollbar included)
var e = window,
a = 'inner';
if (!('innerWidth' in window )) {
a = 'client';
e = document.documentElement || document.body;
}
if ( e[ a+'Width' ] >= MqL ){
closeNav();
if ( $('.menu-trigger').hasClass('menu-trigger-open') ){
$('.menu-trigger').removeClass('menu-trigger-open');
}
return true;
} else {
var menuElm = $('.main-menu .has-children');
if($('.sub-menu ul', menuElm).hasClass('left-menu')){
$('.sub-menu ul', menuElm).removeClass('left-menu');
}
return false;
}
}
function moveNavigation(){
var navigation = $('.menu--main'),
desktop = checkWindowWidth();
if ( desktop ) {
$('#mobile-nav').children().remove();
$('.menu-wrapper-left').html(menuLeft);
$('.menu-wrapper-right').html(menuRight);
} else {
navigation.appendTo('#mobile-nav');
$('.menu--main').not(':first').remove().children('li').appendTo('.menu--main:first');
}
}
$(".menu-trigger").click(function() {
$(this).toggleClass("menu-trigger-open");
});
});
}(jQuery));
If you want to see it in action, I've made a Codepen (try resize to see it working)
http://codepen.io/thehung1724/full/JYmzWr/
I hope I could explain well my problem. I've searched and didn't found a solution for this issue (or maybe I just didn't know really well what to look for). Although when you resize the screen, you can still click on the menu icon, but please notice it doesn't transform to 'X' letter and you can't click to show sub-menu
Works
Doesn't work
Any help would be appreciated!
An easy fix would be to replace
$('.has-children').on('click', function(event){
with
$(document).on('click', '.has-children', function (event) {
When you clone the nav from one place to another you are losing the pointer to the on click function for .has-children
With the $(document).on.... you're actually binding the function to the document which doesn't get disposed.
Update:
Replace the following section of javascript
$('.has-children').on('click', function (event) {
var selected = $(this);
if (selected.children('ul').hasClass('is-hidden')) {
selected.children('ul').removeClass('is-hidden');
}
});
$('.go-back').on('click', function (evt) {
evt.stopPropagation();
$(this).parent('ul').addClass('is-hidden').parent('.has-children').parent('ul');
});
With
$(document).on('click', '.has-children', function (event) {
var selected = $(this);
if (selected.children('ul').hasClass('is-hidden')) {
selected.children('ul').removeClass('is-hidden');
}
});
$(document).on('click', '.go-back', function (evt) {
evt.stopPropagation();
$(this).parent('ul').addClass('is-hidden').parent('.has-children').parent('ul');
});
Further update:
I've Forked your code in CodePen with the above changes: http://codepen.io/anon/pen/JYmVXm

How to hide/show a div inside a parent div

I am working on a site and I need to have a basic show hide functionality for part of it where, when the user clicks on a subject header, it displays an unordered list below the subject header, and then when they click on the subject header again, it will hide the content again.
I have done this in the past, but when I tried applying my code to the site I am working on, it does not work....the hidden content does not display.
Currently, I am using javascript, but if there is a better way, perhaps with pure CSS, that would be fine with me too.
Here is the code I am trying right now (I have a feeling that it isn't working becasue of a parent/child div situation, but I wasn't sure and so I was hoping someone could lead me in the right direction:
<div class="container">
<div class="row">
<div class="col-md-4">
<div class="toggle-buttons">
<div class="web-develop-toggle">
<a href="#" onClick="toggle-web-develop('web-develop-content',this)">
<img src="images/subCtxHeader3-c.png" class="img-responsive" border="0">
</a>
</div>
<div class="web-develop-content" style="display: none;">
<div class="web-develop-body">
<ul class="svc-list">
<li class="svc-bullet"><span class="svc-list">Option 1</span></li>
<li class="svc-bullet"><span class="svc-list">Option 2</span></li>
<li class="svc-bullet"><span class="svc-list">Option 3</span></li>
<li class="svc-bullet"><span class="svc-list">Option 4</span></li>
</ul>
</div>
</div>
</div>
</div>
</div>
</div>
And here is the javascript that I am using currently, which has worked for me in the past, ironically enough:
<script type="text/javascript">
function toggle-web-develop(id, link) {
var e = document.getElementById(id);
if (e.style.display == '') {
e.style.display = 'none';
} else {
e.style.display = '';
}
}
</script>
Any and all help would greatly be welcomes as I have been stuck on this for a full day.
Thanks in advance!
-- Dan
You cannot use - in a function name. Try something like toggleWebDevelop()
You are trying to find web-develop-content by id, but you are using it as a class in your HTML
<div class="web-develop-content" style="display: none;">
Should be...
<div id="web-develop-content" style="display: none;">
Also, I would use e.style.display = 'block'; instead of e.style.display = '';
DEMO

Get link name and write it down in a div

i want to use the name from the link that was clicked to show in an div. I tried many things but nothing comes out. I also have a little script to show and hide a div that worked fine until I tried to make a script for the name.
Would someone please take a quick look.
//script for hiding and display div
function showDiv() {
document.getElementById('popup').style.display = "block";
}
function hideDiv() {
document.getElementById('popup').style.display = "none";
}
and the html:
<div class="maintab">
<div class="tab" onclick="showDiv()" >Template</div>
</div>
<div id="bestelknop">**Here the name must come**</div>
<div id="popup" style="display:none">
<ul>
pixelweb
social
<a href="http://templates.pixelweb.be" target="iframe" onclick="hideDiv()" name="Templates" >templates pixelweb</a>
</ul>
</div>
Now I want to display the name van de current link in the div bestelknop.
I'm a newbee in javascript so please help me with this.
Regards,
Benny
You can pass the current link to the function.
Take a look to my working example here: http://jsfiddle.net/XfW3P/
<div class="maintab">
<div class="tab" onclick="showDiv()" >Template</div>
</div>
<div id="bestelknop">**Here the name must come**</div>
<div id="popup" style="display:none">
<ul>
pixelweb
social
<a href="http://templates.pixelweb.be" target="iframe" onclick="hideDiv(this)" name="Templates" >templates pixelweb</a>
</ul>
</div>
The JavaScript code:
function showDiv() {
document.getElementById('popup').style.display = "block";
}
function hideDiv(link) {
document.getElementById('popup').style.display = "none";
document.getElementById('bestelknop').innerHTML = link.name;
}
First, pass this into your `onclick="hideDiv(this)" in each link:
pixelweb
social
<a href="http://templates.pixelweb.be" target="iframe" onclick="hideDiv(this)" name="Templates" >templates pixelweb</a>
Then, make change your hideDiv() function:
function hideDiv(obj) {
document.getElementById('popup').style.display = "none";
document.getElementById('bestelknop').innerHTML = obj.name + " " + obj.href;
}
Fiddle: http://jsfiddle.net/bUVtA/

Categories

Resources