Frana
Frana

Reputation: 85

My Nav icon does not close

Hi there I am trying to create a side nav, and I cannot manage to close the menu with a second function of "onclick()"

the navigation opens perfectly but then it does not close. Here is my fiddle, I was just hoping to get help on having a added onlick function that closes the nav when clicking on the nav icon again.

function myFunction(x) {
  x.classList.toggle("change");
  document.getElementById("mySidenav").style.width = "220px";
  document.getElementById("Content").style.paddingLeft = "0px";
  document.body.style.opacity = "0.1";

}
/* The side navigation menu */

.sidenav {
  height: 100%;
  width: 0;
  /* 0 width - change this with JavaScript */
  position: fixed;
  z-index: 400;
  right: 0;
  background-color: #0F0F0F;
  overflow-x: hidden;
  padding-top: 90px;
  transition: 0.5s;
  -webkit-transition: 0.5s;
  -moz-transition: 0.5s;
  opacity: 0.8;
}
/* The navigation menu links */

.sidenav a {
  padding: 8px 8px 8px 10px;
  text-decoration: none;
  font-size: 18px;
  text-align: right;
  vertical-align: middle;
  justify-content: center;
  display: flex;
  line-height: 20px;
  color: #FFFFFF;
  transition: 0.3s;
}
/* When you mouse over the navigation links, change their color */

.sidenav a:hover,
.offcanvas a:focus {
  color: #00CB10;
  text-decoration: underline;
}
.menu-icon {
  display: inline-block;
  position: fixed;
  z-index: 500;
  cursor: pointer;
  margin-right: 15px;
  margin-top: 15px;
  margin-left: 96%;
}
.bar1,
.bar2,
.bar3 {
  width: 30px;
  height: 4px;
  background-color: #0F0F0F;
  border-radius: 10px;
  margin: 6px 0;
  transition: 0.4s;
}
/* Rotate first bar */

.change .bar1 {
  -webkit-transform: rotate(-45deg) translate(-9px, 5px);
  transform: rotate(-45deg) translate(-9px, 5px);
}
/* Fade out the second bar */

.change .bar2 {
  opacity: 0;
}
/* Rotate last bar */

.change .bar3 {
  -webkit-transform: rotate(45deg) translate(-8px, -6px);
  transform: rotate(45deg) translate(-8px, -6px);
}
<div id="Menu" class="menu-icon" onclick="myFunction(this)">
  <div class="bar1"></div>
  <div class="bar2"></div>
  <div class="bar3"></div>
</div>

<div id="mySidenav" class="sidenav">
  <!--Start Side Nav-->
  <a href="#">Our Story</a>
  <a href="#">Products</a>
  <a href="#">Contact Us</a>
  <a href="#">Login/Sign up</a>
</div>
<!---->

Upvotes: 2

Views: 122

Answers (4)

Kumar
Kumar

Reputation: 280

I have added new class called toggleClass and I have provided width:220px, and I have commented document.getElementById("mySidenav").style.width = "220px"

working fiddle

Upvotes: 1

Cladiuss
Cladiuss

Reputation: 535

You don't need to set the width in JS. You are toggling an additionnal class when the menu is open, you can play with this.

Another point is that you shouldn't change the body opacity (it will affect the menu too), but only the main content div. Or display an overlay div with a fixed position (100% width and height, background and opacity) so it creates an effect of disabled content.

In my exemple I commented the unnecessary js lines, and I added somme CSS :

function myFunction(x) {
  x.classList.toggle("change");
  //document.getElementById("mySidenav").style.width = "220px";
  //document.getElementById("Content").style.paddingLeft = "0px";
  document.body.style.opacity = "0.1";

}
/* The side navigation menu */

.sidenav {
  height: 100%;
  width: 0;
  /* 0 width - change this with JavaScript */
  position: fixed;
  z-index: 400;
  right: 0;
  background-color: #0F0F0F;
  overflow-x: hidden;
  padding-top: 90px;
  transition: 0.5s;
  -webkit-transition: 0.5s;
  -moz-transition: 0.5s;
  opacity: 0.8;
}
/* The navigation menu links */

.sidenav a {
  padding: 8px 8px 8px 10px;
  text-decoration: none;
  font-size: 18px;
  text-align: right;
  vertical-align: middle;
  justify-content: center;
  display: flex;
  line-height: 20px;
  color: #FFFFFF;
  transition: 0.3s;
}
/* When you mouse over the navigation links, change their color */

.sidenav a:hover,
.offcanvas a:focus {
  color: #00CB10;
  text-decoration: underline;
}
.menu-icon {
  display: inline-block;
  position: fixed;
  z-index: 500;
  cursor: pointer;
  margin-right: 15px;
  margin-top: 15px;
  margin-left: 96%;
}
.bar1,
.bar2,
.bar3 {
  width: 30px;
  height: 4px;
  background-color: #0F0F0F;
  border-radius: 10px;
  margin: 6px 0;
  transition: 0.4s;
}
/* Rotate first bar */

.change .bar1 {
  -webkit-transform: rotate(-45deg) translate(-9px, 5px);
  transform: rotate(-45deg) translate(-9px, 5px);
}
/* Fade out the second bar */

.change .bar2 {
  opacity: 0;
}
/* Rotate last bar */

.change .bar3 {
  -webkit-transform: rotate(45deg) translate(-8px, -6px);
  transform: rotate(45deg) translate(-8px, -6px);
}
.change + .sidenav {
  width: 220px;
}
<div id="Menu" class="menu-icon" onclick="myFunction(this)">
  <div class="bar1"></div>
  <div class="bar2"></div>
  <div class="bar3"></div>
</div>

<div id="mySidenav" class="sidenav">
  <!--Start Side Nav-->
  <a href="#">Our Story</a>
  <a href="#">Products</a>
  <a href="#">Contact Us</a>
  <a href="#">Login/Sign up</a>
</div>
<!---->

Upvotes: 1

Rounin
Rounin

Reputation: 29521

The key thing missing from your set up is that #mySidenav needs to be able to toggle between states as well as .menu-icon.

Consequently, you need to set up myFunction() so that it toggles the class .change on both .menu-icon and #mySidenav.

function myFunction() {
var x = document.getElementsByClassName('menu-icon')[0]; 
var mySidenav = document.getElementById('mySidenav');

x.classList.toggle('change');
mySidenav.classList.toggle('change');
}

var menuIcon = document.getElementsByClassName('menu-icon')[0];
menuIcon.addEventListener('click',myFunction,false);
/* The side navigation menu */

.sidenav {
height: 100%;
width: 0;
/* 0 width - change this with JavaScript */
position: fixed;
z-index: 400;
right: 0;
background-color: #0F0F0F;
overflow-x: hidden;
padding-top: 90px;
transition: 0.5s;
-webkit-transition: 0.5s;
-moz-transition: 0.5s;
opacity: 0.8;
}
/* The navigation menu links */

.sidenav a {
padding: 8px 8px 8px 10px;
text-decoration: none;
font-size: 18px;
text-align: right;
vertical-align: middle;
justify-content: center;
display: flex;
line-height: 20px;
color: #FFFFFF;
transition: 0.3s;
}
/* When you mouse over the navigation links, change their color */

.sidenav a:hover,
.offcanvas a:focus {
color: #00CB10;
text-decoration: underline;
}
.menu-icon {
display: inline-block;
position: fixed;
z-index: 500;
cursor: pointer;
margin-right: 15px;
margin-top: 15px;
margin-left: 96%;
}
.bar1,
.bar2,
.bar3 {
width: 30px;
height: 4px;
background-color: #0F0F0F;
border-radius: 10px;
margin: 6px 0;
transition: 0.4s;
}
/* Rotate first bar */

.change .bar1 {
-webkit-transform: rotate(-45deg) translate(-9px, 5px);
transform: rotate(-45deg) translate(-9px, 5px);
background-color: rgb(255,255,255);
}
/* Fade out the second bar */

.change .bar2 {
opacity: 0;
}
/* Rotate last bar */

.change .bar3 {
-webkit-transform: rotate(45deg) translate(-8px, -6px);
transform: rotate(45deg) translate(-8px, -6px);
background-color: rgb(255,255,255);
}

#mySidenav.change {
width: 220px;
}

#Content.change {
padding-left: 0;
}

body.change {
opacity: 0.1;
}
<div id="Menu" class="menu-icon">
<div class="bar1"></div>
<div class="bar2"></div>
<div class="bar3"></div>
</div>

<div id="mySidenav" class="sidenav">
<!--Start Side Nav-->
<a href="#">Our Story</a>
<a href="#">Products</a>
<a href="#">Contact Us</a>
<a href="#">Login/Sign up</a>
</div>

Upvotes: 0

Pratyush
Pratyush

Reputation: 535

If you are trying to set the width in javascript,then you can go for a check whether the menu is open or not.

However the above answer is more appropriate in this case.

function myFunction(x) {
  x.classList.toggle("change");
  var width=document.getElementById("mySidenav").style.width;
  if(width!="220px" || width=="") 
  {
     document.getElementById("mySidenav").style.width="220px";
  }
  else
  {
     document.getElementById("mySidenav").style.width="0px";
  }
  document.getElementById("Content").style.paddingLeft = "0px";
  document.body.style.opacity = "0.1";

}
/* The side navigation menu */

.sidenav {
  height: 100%;
  width: 0;
  /* 0 width - change this with JavaScript */
  position: fixed;
  z-index: 400;
  right: 0;
  background-color: #0F0F0F;
  overflow-x: hidden;
  padding-top: 90px;
  transition: 0.5s;
  -webkit-transition: 0.5s;
  -moz-transition: 0.5s;
  opacity: 0.8;
}
/* The navigation menu links */

.sidenav a {
  padding: 8px 8px 8px 10px;
  text-decoration: none;
  font-size: 18px;
  text-align: right;
  vertical-align: middle;
  justify-content: center;
  display: flex;
  line-height: 20px;
  color: #FFFFFF;
  transition: 0.3s;
}
/* When you mouse over the navigation links, change their color */

.sidenav a:hover,
.offcanvas a:focus {
  color: #00CB10;
  text-decoration: underline;
}
.menu-icon {
  display: inline-block;
  position: fixed;
  z-index: 500;
  cursor: pointer;
  margin-right: 15px;
  margin-top: 15px;
  margin-left: 96%;
}
.bar1,
.bar2,
.bar3 {
  width: 30px;
  height: 4px;
  background-color: #0F0F0F;
  border-radius: 10px;
  margin: 6px 0;
  transition: 0.4s;
}
/* Rotate first bar */

.change .bar1 {
  -webkit-transform: rotate(-45deg) translate(-9px, 5px);
  transform: rotate(-45deg) translate(-9px, 5px);
}
/* Fade out the second bar */

.change .bar2 {
  opacity: 0;
}
/* Rotate last bar */

.change .bar3 {
  -webkit-transform: rotate(45deg) translate(-8px, -6px);
  transform: rotate(45deg) translate(-8px, -6px);
}
<div id="Menu" class="menu-icon" onclick="myFunction(this)">
  <div class="bar1"></div>
  <div class="bar2"></div>
  <div class="bar3"></div>
</div>

<div id="mySidenav" class="sidenav">
  <!--Start Side Nav-->
  <a href="#">Our Story</a>
  <a href="#">Products</a>
  <a href="#">Contact Us</a>
  <a href="#">Login/Sign up</a>
</div>
<!---->

Upvotes: 0

Related Questions