Dynamically generated button not working via jQuery

Viewed 57

Creating and fetching tables and buttons within the table with the help of AJAX.

The button in the brought table does not function. I cannot see any action related to the button click on the console. What could be the reason the button is not working?

Code structure for button creation:

for (var i = 0; i < finishedExams.length; i++) {
  document.getElementById('FEtemplate').innerHTML += '<tr><th>' + (i + 1) + '</th><td>' + result + '</td><td>' + title + '</td><td>' + et + '</td><td>' + humanized_time_span(date) + '</td><td><button type="button" class="btn btn-sm btn-alt-primary sendButtonData" data-qr-exam-id="' + id + '"> Send</button></div></td></tr>';
}

Code structure related for button click:

$('.sendButtonData').click(function () { 
        /* AJAX POST code here.. */
        if (response.status == true) {
            /* some codes */
        } else {
            /* some codes */
        }
    });

What have I tried?

$('body').on('click', '.sendButtonData', function(){

This code works but gets it with the ID of the first part of the table. All other buttons act as if they were working for the first row of the table.

Also, I changed the button type from "button" to "submit". Again, nothing changed.

1 Answers

I think you have attached the event listener to ".sendButtonData" elements before creating those buttons, when you click one of them nothing happen because the event was attached to the existing elements with that class name which are in this case none, but not for the future ones

$('.sendButtonData').click(function () { 
  console.log("button click!");
});

for (var i = 0; i < 5; i++) {
  document.getElementById('FEtemplate').innerHTML += '<tr><th>' + (i + 1) + '</th><td>' + " some result " + '</td><td>' + " some title " + '</td><td>' + " some et " + '</td><td>' + " some date " + '</td><td><button type="button" class="btn btn-sm btn-alt-primary sendButtonData" data-qr-exam-id="' + " some id " + '"> Send</button></div></td></tr>';
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div id="FEtemplate"></div>

So you need to attach that listener after creating those buttons like this

for (var i = 0; i < 5; i++) {
  document.getElementById('FEtemplate').innerHTML += '<tr><th>' + (i + 1) + '</th><td>' + " some result " + '</td><td>' + " some title " + '</td><td>' + " some et " + '</td><td>' + " some date " + '</td><td><button type="button" class="btn btn-sm btn-alt-primary sendButtonData" data-qr-exam-id="' + " some id " + '"> Send</button></div></td></tr>';
}

$('.sendButtonData').click(function () { 
  console.log("button click!");
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div id="FEtemplate"></div>

Or you can use event delegation like this

$('#FEtemplate').click(function(e) { 
  // only if the element has that class `sendButtonData`
  // note that in this case we're not checking for the element type to be a button
  if(e.target.className.includes("sendButtonData")) {
    console.log("button click!");
  }
});

for (var i = 0; i < 5; i++) {
  document.getElementById('FEtemplate').innerHTML += '<tr><th>' + (i + 1) + '</th><td>' + " some result " + '</td><td>' + " some title " + '</td><td>' + " some et " + '</td><td>' + " some date " + '</td><td><button type="button" class="btn btn-sm btn-alt-primary sendButtonData" data-qr-exam-id="' + " some id " + '"> Send</button></div></td></tr>';
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div id="FEtemplate"></div>

Related