8

I'm running into a bug with my code. I am cloning a div so that the user can add multiple customers.

            var num = $('.clonedInput').length; // how many "duplicatable" input fields we currently have
            var newNum = new Number(num + 1);   // the numeric ID of the new input field being added
            var newElem = $('#divInput' + num).clone().attr('id', 'divInput' + newNum); // create the new element via clone(), and manipulate it's ID using newNum value

            // clear input value for cloned items and do not remove text for del button.
            newElem.find('input:not(.DeleteBtn),textarea').val('');
            //newElem.find('input[type="submit"]

            // Replace clone num with incremental num.
            newElem.find(':input').each(function () {
                $(this).attr('id', $(this).attr('id').replace(/\d+/, newNum));
                $(this).attr('name', $(this).attr('name').replace(/\d+/, newNum));
            });

            // insert the new element after the last "duplicatable" input field
            $('#divInput' + num).after(newElem);

I have provided a delete button to delete rows and I am using the class name for the button to execute a function on click .

        $(".DeleteBtn").click(function () {
            alert(".DeleteBtn Click Function -  " + $(this).attr('id'));
            var DelBtnNum = $(this).attr('id');
            DelBtnNum = DelBtnNum[DelBtnNum.length - 1];
            $('#divInput' + DelBtnNum).remove();

        });

I am able to delete the first (original) input row, but any additional customer rows are not deleted.

I have a running demo of the code located here: http://jsfiddle.net/crjunk/FB4BZ/2/

Why will the cloned items not fire the .DeleteBtn.click function?

1
  • 3
    have you tried: .clone(true) as suggested in DOC ??? jsfiddle.net/FB4BZ/3 Commented Mar 14, 2014 at 16:12

4 Answers 4

17

You need to use event delegation for supporting dynamic elements.

Since you have used jQuery 1.6 in the fiddle

$(document).delegate(".DeleteBtn", 'click', function () {
    alert(".DeleteBtn Click Function -  " + $(this).attr('id'));
    var DelBtnNum = $(this).attr('id');
    DelBtnNum = DelBtnNum[DelBtnNum.length - 1];
    $('#divInput' + DelBtnNum).remove();

});

if jQuery >= 1.7

$(document).on('click', ".DeleteBtn", function () {
    alert(".DeleteBtn Click Function -  " + $(this).attr('id'));
    var DelBtnNum = $(this).attr('id');
    DelBtnNum = DelBtnNum[DelBtnNum.length - 1];
    $('#divInput' + DelBtnNum).remove();

});

Another option is to clone the element along with the event using clone(true)

Sign up to request clarification or add additional context in comments.

1 Comment

This solved my issue. Thanks for providing the solution for jQuery 1.7 as well.
12

Because the default when using clone is to not clone events. Try passing true to clone():

var newElem = $('#divInput' + num).clone(true).attr('id', 'divInput' + newNum); // create the new element via clone(), and manipulate it's ID using newNum value

jsFiddle example

As the .clone() docs state:

.clone( [withDataAndEvents ] ) withDataAndEvents (default: false)

3 Comments

This seems to be the correct answer, delegated handlers are uneccessary when using clone(), as it can clone events and data as well.
perfect one.. this is simple and perfect
This is indeed the correct answer, and by far the most elegant
6

When you bound the click event, only one div existed, so it is the only one that has a click handler. You should change your code to use on instead of click.

$(document).on('click', ".DeleteBtn", function () {

3 Comments

This'll have the same problem you need to delegate to a higher element
jQuery 1.6.4 in the fiddle
@Jamiec You are correct. I always muck up the syntax for on when I need delegation. Editing to make the code correct.
0

try going on with .on('click',function(e){ ... }); or use live() selector (but i think live goes deprecated...)

so in your case

$(".DeleteBtn").on('click',function () { ..

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.