1

I have a function that supposed to do a toggle after a click,

but this line of code doesn't do the job after first click.

var toggle = document.querySelector('header nav ul').className = (toggle) ? '' : 'open';

  • only if i execute it in the console it works..

Plunker: https://embed.plnkr.co/B5iFwB/

enter image description here

Moti Winkler
  • 308
  • 1
  • 4
  • 19
  • http://stackoverflow.com/questions/18880890/how-do-i-toggle-an-elements-class-in-pure-javascript – l2aelba Jan 09 '17 at 11:38

4 Answers4

2

You're seeing this behaviour because your code references a variable toggle which is declared in the same statement. It works in the console because by the time the expression is evaluated for the second time toggle now exists.

I can't suggest an improvement because I don't know how you expect the function to work, given you don't define an initial value for toggle before your statement evaluates.

Also, you're using jQuery, but using Vanilla.js code-style within your jQuery event-handler. You should change your code to be more consistent: either only use idiomtic jQuery or idiomatic Vanilla.js.

Dai
  • 141,631
  • 28
  • 261
  • 374
2

var toggle is inside a block that is not global, you need to write code like:

var toggle;
document.querySelector('.btn-menu').addEventListener('click', function(){
    toggle = document.querySelector('header nav ul').className = (toggle) ? '' : 'open';
});
Sanjay Nishad
  • 1,537
  • 14
  • 26
  • No initial value of `toggle` is given, so `(toggle)` (in the ternary expression) will evaluate to `false`. This may or may not be desirable. The OP should set an initial value to prevent confusion by future programmers. – Dai Jan 09 '17 at 11:41
  • then just remove `var` from inside block – Sanjay Nishad Jan 09 '17 at 11:42
  • 1
    Note, any variable defined outside a function will make it global. – Rajesh Jan 09 '17 at 11:44
0

There is no need for toggle

You should check if open class is available on element, then remove it else add it. You can use .classList.add and .classList.remove to achieve this:

Updated Code

Sample:

document.querySelector('.btn-menu').addEventListener('click', function() {
  var nav = document.querySelector('header nav ul');
  if (nav.classList.contains('open'))
    nav.classList.remove('open')
  else
    nav.classList.add('open')
})
body {
  margin-top: 80px;
}

header {
  width: 100%;
}

header .btn-menu{
  background: #e5e5e5;
  direction: rtl;
  font-size: 25px;
  padding-right: 10px;
  cursor: pointer;
}

header nav ul {
  margin: 0;
  list-style-type: none;
  text-align: center;
  background-color: #1b2125;
  height: 0;
}

header nav ul.open {
  height: auto;
}

header nav li a {
  color: #fff;
}
<header>
  <nav>
    <div class="btn-menu">≡</div>
    <ul>
      <li><a href="">Home</a>
      </li>
      <li><a href="">About</a>
      </li>
      <li><a href="">Services</a>
      </li>
    </ul>
  </nav>
</header>
Community
  • 1
  • 1
Rajesh
  • 24,354
  • 5
  • 48
  • 79
0

Add this to your code it will do top to bottom toggle,

  $('.btn-menu').on('click',function(){
$('header nav ul').slideToggle( "slide" );

});

also you need to add JQuery to your code. Add this in your head

<script src="https://code.jquery.com/jquery-1.10.2.js"></script>
PMArtz
  • 148
  • 9