0

This code enables dropdown onclick, but it only add class when I press ABC link and when I try to add .drop class to GHI nothing happens. Also I found solutions how to do this with jQuery, but I need this vanilla JS, no jQuery please.

HTML

<ul>
    <li><a href="javascript:">ABC</a>
        <ol>
            <li><a href="#">A</a></li>
            <li><a href="#">B</a></li>
            <li><a href="#">C</a></li>
        </ol>
    </li>
    <li><a href="#">DEF</a></li>
    <li><a href="javascript:">GHI</a>
        <ol>
            <li><a href="#">G</a></li>
            <li><a href="#">H</a></li>
            <li><a href="#">I</a></li>
        </ol>
    </li>
    <li><a href="#">JKL</a></li>
    <li><a href="#">MNO</a></li>
</ul>

JavaScript

<script>
    var btn = document.querySelector('ul li a');
    var drp = document.querySelector('ol');
    btn.onclick = function()
    {
        drp.classList.toggle('drop');
    }
</script>

CSS

.drop
    {
    display: block;
    }

EDIT: Here is Vanilla JS dropdown I made: https://jsfiddle.net/vh6tywjs/11/

Jon Levi
  • 51
  • 1
  • 11
  • Try using the [`classList` API](https://developer.mozilla.org/en-US/docs/Web/API/Element/classList). `drp.classList.toggle("drop")` – mhodges May 15 '17 at 16:47
  • Oh sorry I fixed this to classList, I'll update my code. But problem still persist – Jon Levi May 15 '17 at 16:50
  • It should be drp.classList.add('drop') or drp.classList.remove('drop'). See this - http://stackoverflow.com/questions/195951/change-an-elements-class-with-javascript – vabii May 15 '17 at 16:52
  • 2
    `document.querySelector('ul li a')` will only return the first matched element. Use `querySelectorAll()` to get the all matched elements and use loop to bind the handler. – abhishekkannojia May 15 '17 at 16:52

2 Answers2

1

You want to use something like this:

var btn = document.querySelectorAll('ul li a');
for(var b = 0; b < btn.length; b++){
  btn[b].onclick = function()
  {
      if(this.parentNode.querySelector('ol') != null){
        this.parentNode.querySelector('ol').classList.toggle('drop');
      }
  }
}

When you click on an anchor link, get the containing li then search for the ol, after that toggle the class drop. Otherwise drp will always return the first ol in the document. You need querySelectorAll to select all matching elements as was mentioned in the comments. Finally, you need to apply the onclick event to each of the anchor links.

JSFiddle

gaynorvader
  • 2,619
  • 3
  • 18
  • 32
0

You have to grab the <ol> corresponding to the button that was clicked and toggle the class on that one only. You also need to add the event listener to all of the ul li a elements, not just the first one. For that, you can use querySelectorAll() in conjunction with forEach

var btns = document.querySelectorAll('ul li a');
btns.forEach(function (btn) {
  var parent = btn.parentNode;
  var drp = parent.querySelector("ol"); // get closest <ol>
  btn.onclick = function()
  {
      // make sure drp is not null
      if (drp) {
        drp.classList.toggle('drop');
      }
  }
});
.drop
{
  display: block;
}
ol {
  display: none;
}
<ul>
    <li><a href="javascript:">ABC</a>
        <ol>
            <li><a href="#">A</a></li>
            <li><a href="#">B</a></li>
            <li><a href="#">C</a></li>
        </ol>
    </li>
    <li><a href="#">DEF</a></li>
    <li><a href="javascript:">GHI</a>
        <ol>
            <li><a href="#">G</a></li>
            <li><a href="#">H</a></li>
            <li><a href="#">I</a></li>
        </ol>
    </li>
    <li><a href="#">JKL</a></li>
    <li><a href="#">MNO</a></li>
</ul>
<script>
    
</script>
mhodges
  • 10,938
  • 2
  • 28
  • 46