1

I have the following HTML :

<button type="button" id="Button">Go</button>
<div id="validation"></div>

I'm trying to add event handlers to dynamically generated elements in the following way :

Click button -> Generate element X inside div #validation -> Attach event handler to element X

$(document).ready(function(){
    ID = 1;

    $("#Button").click(function(){

        /*generate new div inside div #validation with id #validationID
        1st one would be #validation1
        it contains a form with name accepterID and a button with name refuserID
        1st ones would be accepter1 and refuser1*/
        var newline = `
                    <div id="validation${ID}">
                        <form name="accepter${ID}">
                            <input type="hidden" name="name" value="phoegasus">
                            <button type="submit" value="valider">
                        </form>
                        <button name="refuser${ID}">refuser</button>
                    </div>
                    `
        $("#validation").append(newline);

        /*attach event handlers to the generated elements
        1st iteration would attach handlers to accepter1 and refuser1 */

        $("#validation").on('submit',"form[name^='accepter"+ID+"']",function(e){
            $("#validation" + ID).remove();
            //remove div validationID after submitting form
        });

        $("#validation").on('click',"button[name^='refuser"+ID+"']",function(){
            $("#validation" + ID).remove();
            //remove div validationID
        });

        ID++;

    });
});

When I submit the form or I click the generated button I want to remove the div that contains them. If I press the button refuser1, it should delete the div #validation1.

When the elements are generated the handlers aren't attached to them.

The code doesn't work when it's executed during the onclick event but when I execute it in the navigator console it works.

I tried using DOMSubtreeModified on the div with id #validation, but it didn't work.

Phoegasus
  • 21
  • 6
  • First, see this: https://stackoverflow.com/questions/4472528/javascript-jquery-closure-function-syntax – Jhonatan S. Souza Apr 16 '19 at 16:27
  • What is the value of `ID` when the handlers are created? It would help to see a full working example with all the HTML and JS which creates the new elements and adds the handlers to them. That being said, it seems like it would be better to use a common class on all the elements you create and then use a single delegated event handler to manage all of them. – Rory McCrossan Apr 16 '19 at 16:30
  • 2
    You need to provide a [mcve]. Your event handlers do nothing, and the code which creates the elements is missing. It's impossible to tell from your example code that it doesn't work, let along determine why. – Quentin Apr 16 '19 at 16:30
  • Creating a unique delegate event listener after each new element is created, specific to that element, seems like an anti-pattern. – Taplar Apr 16 '19 at 16:31

1 Answers1

0

you can manage it by using a class (or another element) in second argument of your on function.

For that, DO NOT declare your event listeners inside your add event.

This is a full working example :

$("#validation").on('submit',"form.validation-form",function(e){
  e.preventDefault();
  console.log('form', $(this).attr('data-id'), ' submitted');
});



$("#validation").on('click',"button.validation-refuser",function(){
  console.log('clicked on refuser for form ', $(this).attr('data-value'));
    //code
});

var ID = 1;
$('#my-adder').on('click', function () {
  $('#validation').append('<form name="accepter'+ID+'" class="validation-form" data-id="'+ID+'"><input type="text" placeholder="my text field" /><button class="validation-refuser" name="refuser'+ID+'" data-value="'+ID+'">Refuser button</button><button type="submit">SUBMIT</button></form>');
  ID++;
})
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div id="validation">
  <form name="accepter0" class="validation-form" data-id="0">
    <input type="text" placeholder="my text field" />
    <button type="button" class="validation-refuser" name="refuser0" data-value="0">Refuser button</button>
    <button type="submit">SUBMIT</button>
  </form>
</div>

<button id="my-adder">ADD A FORM</button>

Hope it helps

Julien Bourdic
  • 1,398
  • 1
  • 12
  • 29
  • I did not use a class, instead I used a common name between all forms (accepter, without adding the ID), and a common name between all buttons (refuser, without adding the ID), and used the data-id attribute to identify the elements. Thus I don't need a new event handler with each new element that I add. – Phoegasus Apr 16 '19 at 17:41