Home > Blockchain >  Display only the nearest element with the given class
Display only the nearest element with the given class

Time:12-23

How can I change the code so that when I click on the reply-img, only the following element with the reply-form class is displayed, but the others are not displayed at the same time.

I have several elements with the reply-img class and I always want to display the closest element with the reply-form class

HTML blade.php

<div >
    @foreach($comments as $comment)
    
    <div >
       ...
                            
       <div >
           <img src="{{asset('img/react.svg')}}" alt="">
       </div>
    </div>
    ...
    <form class='login-form mmm ml-x reply-form'</form>
    
    @endforeach
...
</div>

JS

<script>
        // Get all image elements
        var images = document.querySelectorAll(".reply-img");
    
        // Attach a click event listener to each image
        images.forEach(function(image) {
            image.addEventListener("click", function() {
                // Show all forms
                var forms = document.querySelectorAll(".reply-form");
                forms.forEach(function(form) {
                    form.style.display = "block";
                });
            });
        });
    </script>

CodePudding user response:

You can use the image element's .parentElement twice to navigate up the tree to the <div >. Then use .nextElementSibling to get to the form element.

Like this:

const img = document.querySelector('img');
const form = img.parentElement.parentElement.nextElementSibling;
console.log(form.innerHTML);
<div >
  <div >
    <img src="https://via.placeholder.com/150" />
  </div>
</div>
<form class='login-form mmm ml-x reply-form'>blah</form>

CodePudding user response:

you will need to change your function so that it shows only the next form and not all of them:

images.forEach(function(image) {
  image.addEventListener("click", function() {
    let ele = image.parentNode.nextElementSibling;
    while(ele){
      if(ele.matches('.reply-form')){
        ele.style.display = "block";
        return;
      }
      ele = ele.nextElementSibling;
    }
  });
});

CodePudding user response:

I find it cleaner to toggle a class on the comments to indicate the active comment. Then we can handle the forms with CSS.

Here's an example of that:

const comments = document.querySelectorAll('.comments');

document.querySelectorAll('.reply-img').forEach(img => img.addEventListener('click', function() {
  comments.forEach(x => x.classList.remove('active-comment'));
  this.parentElement.classList.add('active-comment');
}))
.reply-form {
  width: 100px;
  height: 50px;
  background: lightblue;
  margin: 10px 0;
}

.comments:not(.active-comment) .reply-form {
  display: none;
}
<div >

  <div >
    <div >
      <img src="https://via.placeholder.com/50" alt="">
    </div>
  </div>
  ...
  <form class='login-form mmm ml-x reply-form'></form>
  <div >
    <div >
      <img src="https://via.placeholder.com/50" alt="">
    </div>
  </div>
  ...
  <form class='login-form mmm ml-x reply-form'></form>
  <div >
    <div >
      <img src="https://via.placeholder.com/50" alt="">
    </div>
  </div>
  <form class='login-form mmm ml-x reply-form'></form>
  ...
</div>

This can also be done without JavaScript, just CSS. By adding the tabindex attribute to the comments, the comments get a focus state. Now we can use the focus state to toggle the display of the forms.

Note that in this case clicking on the comment will cause the form to display, not only clicking on the image.

.reply-form {
  width: 100px;
  height: 50px;
  background: lightblue;
  margin: 10px 0;
}

.comments:not(:focus) .reply-form {
  display: none;
}
<div >

  <div  tabindex="0">
    <div >
      <img src="https://via.placeholder.com/50" alt="">
    </div>
  </div>
  ...
  <form class='login-form mmm ml-x reply-form'></form>
  <div  tabindex="0">
    <div >
      <img src="https://via.placeholder.com/50" alt="">
    </div>
  </div>
  ...
  <form class='login-form mmm ml-x reply-form'></form>
  <div  tabindex="0">
    <div >
      <img src="https://via.placeholder.com/50" alt="">
    </div>
  </div>
  <form class='login-form mmm ml-x reply-form'></form>
  ...
</div>

  • Related