Manipulating a jquery Children by clicking another

Asked

Viewed 61 times

1

Hello, I would like to make a script similar to accordion.

My HTML

<div class="pergunta">
    <h3>Titulo</h3>
    <article>Texto</article>
</div>

<div class="pergunta">
     <h3>Titulo</h3>
     <article>Texto</article>
</div>

The idea is that when you click on H3, open the corresponding article. I made my jQuery as follows

var aux = 0;
$(".pergunta").click(function(){
    if(aux == 0){
        $("article", this).slideDown();
        aux++;
    }else{
        $("article", this).slideUp();
        aux--;
    }
});

Compile. But if I click anywhere on the div question, it closes again. So I wanted to do something like:

var aux = 0;    
$(".pergunta h3").click(function(){
    if(aux == 0){
        $(this).parent().children('article').slideDown();
        aux++;
    }else{
        $(this).parent().children('article').slideUp();
        aux--;
    }
});

Don’t compile, I imagine you’re wrong. Just to be clear. How can I do without using Ids? In order to save code.

  • Strange, because I tested your last code in which you say does not compile, but it works perfectly, as you can see here: https://jsfiddle.net/leandrobeandrade/sz24gcbf/

1 answer

4


Imagine the following situation:

By clicking on a <h3> within a <div class="pergunta"> for the first time, its variable aux will have the value incremented to 1. Then by clicking on a <h3> other’s <div>, the value of the variable aux will be maintained, ie will be executed the else for that other element.

I believe this is the problem in your code, because the variable x, the way you used it, it is in global scope and is therefore "shared" at the moment the click events are triggered.

One solution is to use the attribute data HTML5 to manage the status of individual elements (whether they are "visible" or not).

For example:

$(".pergunta > h3").on('click', function () {
  // Captura o próximo elemento após o <h3>, no caso, o <article>
  var article = $(this).next(); 
  
  // Captura todos os <article>, exceto o que está sendo referenciado
  var all = $('.pergunta > article').not(article);
  
  if (article.data('visivel') === false) {
    article.data('visivel', true).slideDown();
    
    // Fecha todos os outros <article>
    all.data('visivel', false).slideUp();
  } else {
    article.data('visivel', false).slideUp();
  }
});
.pergunta > h3 {
  cursor: pointer;
}

article {
  display: none;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>

<div class="pergunta">
    <h3>Titulo</h3>
    
    <article data-visivel="false">Texto</article>
</div>

<div class="pergunta">
     <h3>Titulo</h3>
     
     <article data-visivel="false">Texto</article>
</div>

Answering your question, I believe that in this case it is not necessary to use Ids, since it is a shared interaction (several elements with the same behavior).

I hope I’ve helped!

  • 1

    Thank you, Paulo! For the solution and the excellent explanation. It contributed too much to my learning :)

Browser other questions tagged

You are not signed in. Login or sign up in order to post.