-1

I'm coding a solution to add and remove form fiends dynamically.

This is the action plan:

Hit the green "+" button to append another input exactly like it at the end of the form, then the button changes itself to a red "x" button.

Hit the red "x" button and it completely removes the clicked/touched input.

When I hit the first green button, ok. it performs exactly what I want. Same goes to the first red one. The mess starts when I try to remove or add more than one, cause the unique buttons which works are the 2 when the page loads.

I also think I have to do a function to add a new unique class to every input due to back-end database record at the future. but I also don't know how to do it.

Here's a Fiddle: http://fiddle.jshell.net/Ja9yE/2/

$(document).ready(function(){
var newField = '<div class="field-wrapper"><input type="text" class="field" disabled="disabled" /><div class="button-holder"><div class="button-add"><img src="http://www.ricardostrobel.com.br/add-cancel-color.svg"></div></div></div>'

$(document).on("touchend mouseup",".button-add",function(e){
    e.stopPropagation(); e.preventDefault();
    $(this).removeClass("button-add").addClass("button-cancel");
    $(".field").removeAttr("disabled");

    $(newField).hide().appendTo("form").fadeIn(500);

});

$(document).on("touchend mouseup",".button-cancel", function(){
    $(this).closest(".field-wrapper").fadeOut("fast");          
});

});
user229044
  • 232,980
  • 40
  • 330
  • 338
Strobel
  • 167
  • 1
  • 9
  • "I think it's self explanatory, as you can see in this Fiddle:" That's **not ok**. Your question needs to be self-contained, and answerable with out opening any external links. Your question's meaningful content needs to be **in the question**. – user229044 Aug 22 '13 at 02:35
  • possible duplicate of [Event binding on dynamically created elements?](http://stackoverflow.com/questions/203198/event-binding-on-dynamically-created-elements) – Sphvn Aug 22 '13 at 02:35
  • @meagar Ok, I edited my question, sorry for that, if you could get back on your decision it'll be great :) – Strobel Aug 22 '13 at 02:43

2 Answers2

2

jQuery dynamic elements 101.... handle events using event delegation!!!

$(document).ready(function(){
    var newField = '<div class="field-wrapper"><input type="text" class="field" disabled="disabled" /><div class="button-holder"><div class="button-add"><img src="http://www.ricardostrobel.com.br/add-cancel-color.svg"></div></div></div>'

    $(document).on("touchend mouseup",".button-add",function(e){
        e.stopPropagation(); e.preventDefault();
        $(this).removeClass("button-add").addClass("button-cancel");
        $(".field").removeAttr("disabled");

        $(newField).hide().appendTo("form").fadeIn(500);

    });

    $(document).on("touchend mouseup",".button-cancel", function(){
        $(this).closest(".field-wrapper").fadeOut("fast");          
    });

});

Demo: Fiddle

When you use a normal event registration model, it will register the handlers directly to the targeted which are present in the dom at the point of the handler registration execution. So elements which are added later dynamically will not get those handlers.

The solution to this is to use event delegation, in this model the handler is registered to a ancestor element which will be present when the page is loaded with the a selector to filter out the source element. This makes use of event propagation - events happening in an element is propagated to all the ancestor elements(there are few exceptions like focus event). So an event happening in an element gets propagated to the ancestor element in one of them the handler is registered then the events source element(event.target) and its ancestors is matched against the selector passed as the second parameter, if it is satisfied then the handler is executed.

Arun P Johny
  • 384,651
  • 66
  • 527
  • 531
  • It works, thank you! Could you explain me your solution? I have never seen that code structure you wrote on buttons. – Strobel Aug 22 '13 at 02:36
  • 1
    @Strobel There is a nice explanation here: http://stackoverflow.com/a/18144022/261564 – Sphvn Aug 22 '13 at 02:37
  • 1
    @Strobel Also see the jQuery API docs for `.on()` http://api.jquery.com/on/ - **Direct and delegated events** section covers this topic. – Sphvn Aug 22 '13 at 02:43
0

You need re-register the event handler after the new element created or delete. Another approach would be register an event handler for the parent div. and check which child element (.button-add or .button-cancel) got clicked, and then apply your logic to clicked element.

Jake Lin
  • 11,146
  • 6
  • 29
  • 40