skip to Main Content

First of all I’m adding a button via js:

let newTextArea = "<div class='row mt-4'><div class='col'><button type='button' class='btn btn-light rimuovi' onclick='removeIt()'>Rimuovi</button></div</div>";

Once on the page, I might want to remove it so I’m calling that function on a click:

function removeIt(e) {
  e.closest(".row").remove();
}

but I’m getting

Cannot read properties of undefined (reading 'closest') at removeIt

3

Answers


  1. You just forgot to pass your element (e) in the paramters in your JS fonction on the HTML.

    So, try with :

    onclick = 'removeIt(this)';
    
    

    Working example:

    function removeIt(e) {
      e.closest(".row").remove();
    }
    <div class="row">
      <button onclick='removeIt(this)'>Rimuovi</button>
    </div>

    Hope this helps you.

    Login or Signup to reply.
  2. As others mentioned, you forgot to pass "this" as a parameter to your removeIt() method. The "this" keywords refers to, in this case, the element in which the click listener is used (your button). With the "this" keyword set as a parameter, JS can now look for a "closest" element with the class "row". It starts from the button and goes up the dom-tree until it finds an element with a className "row" or until it reaches the root.

    Working example:

    <!DOCTYPE html>
    <html>
      <body>
        <div class="row mt-4">
          <div class="col">
            <button
              type="button"
              class="btn btn-light rimuovi"
              onclick="removeIt(this)"
            >
              Rimuovi
            </button>
          </div>
        </div>
    
        <script>
          function removeIt(element) { 
            closest = element.closest('.row');
            closest.remove();
          }
        </script>
      </body>
    </html>
    Login or Signup to reply.
  3. The main issue is because you aren’t providing the e argument when you call the removeIt() function in the onclick attribute.

    However you should note that using an inline onclick attribute is not good practice. A better way to achieve what you need is to attach an unobtrusive delegated event handler which accepts the Event object as an argument. You can then use that Event to retrieve the Element object which triggered the handler. Something like this:

    const rowTemplate = document.querySelector('#row-template');
    const container = document.querySelector('.container');
    const addBtn = document.querySelector('.add');
    
    addBtn.addEventListener('click', () => {
      container.innerHTML += rowTemplate.innerHTML;
    });
    
    container.addEventListener('click', e => {
      if (e.target.matches('.rimuovi'))
        e.target.closest('.row').remove();
    });
    <button class="add">Add</button>
    <div class="container"></div>
    
    <template id="row-template">
      <div class="row mt-4">
        <div class="col">
          <button type="button" class="btn btn-light rimuovi">Rimuovi</button>
        </div>
      </div>
    </template>
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search