Dipak
Dipak

Reputation: 939

Custom toggle function in Pure JavaScript

Here, why toggle approach in not working ?

I am trying to run custom function and loop this function in pure JavaScript.

I am expecting Jquery toggle. When header is clicked then add dsplyBlck to it's child article, remove dsplyBlck to it's child article when header is re-click.

window.onload = function(){
  var hdr = document.querySelectorAll('header');
  for(var i=0; i<hdr.length; i++){
    hdr[i].onclick = function(){
      var elm = this.closest('section').querySelector('article');
      tgglArticle(elm,this);
    }
  }
}

function tgglArticle(elm, hdr){
  elm.classList.add('dsplyBlck');
  hdr.addEventListener('click',function(){
    console.log('Here message is displaying, but remove class not working');
    elm.classList.remove('dsplyBlck');
    tgglArticle(elm,hdr);
  })
}
.dsplyNne{
  display:none;
}
.crsr{
  cursor:pointer;
}
.dsplyBlck{
  display:block;
}
<section>
  <header class='crsr'>
    Header
  </header>
  <article class='dsplyNne'>
    Details
  </article>
</section>
<section>
  <header class='crsr'>
    Header
  </header>
  <article class='dsplyNne'>
    Details
  </article>
</section>

Upvotes: 1

Views: 443

Answers (3)

Gerard
Gerard

Reputation: 15806

I have rewritten the javascript. Documentation in the source.

window.onload = () => {
  // Capture the header elements in an array
  const hdr = [...document.querySelectorAll('header')];
  // Add an eventlistener for each header element
  hdr.map( (h) => {
    h.addEventListener( "click", (e) => {
      // Toggle the class for the next sibling (article)
      const t = e.currentTarget.nextElementSibling;
      t.classList.toggle("dsplyNne");
    });
  });
}
.dsplyNne {
  display: none;
}

.crsr {
  cursor: pointer;
}

.dsplyBlck {
  display: block;
}
<section>
  <header class='crsr'>
    Header
  </header>
  <article class='dsplyNne'>
    Details
  </article>
</section>
<section>
  <header class='crsr'>
    Header
  </header>
  <article class='dsplyNne'>
    Details
  </article>
</section>

Upvotes: 1

Emy
Emy

Reputation: 639

solution:

function toggleElm(elem) {
  let x = document.getElementById(elem);
  if (x.classList.contains('dsplyBlck')) {
    x.classList.add('dsplyNne');
    x.classList.remove('dsplyBlck');
  } else {
    x.classList.add('dsplyBlck');
    x.classList.remove('dsplyNne');
  }
} 
<html>
  <head>
    <style>
      .dsplyNne{
        display:none;
      }
      .crsr{
        cursor:pointer;
      }
      .dsplyBlck{
        display:block;
      }
    </style>
  </head>
  <body>
    <section>
      <header class='crsr' onclick="toggleElm('target1')">
        Header
      </header>
      <article class='dsplyNne' id="target1">
        Details
      </article>
    </section>
    <section>
      <header class='crsr' onclick="toggleElm('target2')">
        Header
      </header>
      <article  class='dsplyNne' id="target2">
        Details
      </article>
    </section>
  </body>
</html>

Upvotes: 1

hgb123
hgb123

Reputation: 14891

You just have to simplify these by using Element.classList.toggle('YOUR_CLASS') (doc)

window.onload = function() {
  var hdr = document.querySelectorAll('header');
  for (var i = 0; i < hdr.length; i++) {
    hdr[i].onclick = function() {
      var elm = this.closest('section').querySelector('article');
      elm.classList.toggle('dsplyBlck');
    }
  }
}
<html>

<head>
  <style>
    .dsplyNne {
      display: none;
    }
    
    .crsr {
      cursor: pointer;
    }
    
    .dsplyBlck {
      display: block;
    }
  </style>
</head>

<body>
  <section>
    <header class='crsr'>
      Header
    </header>
    <article class='dsplyNne'>
      Details
    </article>
  </section>
  <section>
    <header class='crsr'>
      Header
    </header>
    <article class='dsplyNne'>
      Details
    </article>
  </section>
</body>

</html>

Upvotes: 1

Related Questions