0

I am trying to add event listeners on the fly on my links with the following code (that is called 3 times with a different this.newsPost.id of course):

document.getElementById('user_news_post_comment_add_button_show_form_' + this.newsPost.id).innerHTML = 'yahoooooo' + this.newsPost.id;
document.getElementById('user_news_post_comment_add_button_show_form_' + this.newsPost.id).addEventListener('click', function() {alert('alert');});

The first line is a debug line, to see if it was a problem accessing the DOM event. But surprisingly, the first line updates the 3 links with yahooooo1 or 2 or 3, but the second line attaches the event only on the third link.

I guess you don't have enough information to solve the problem, but maybe you can give me some hints where i should look.


To provide more information, I am looping here:

for (var i = 0; i < newsPostArray.length; ++i) {
    if (i != 0) {
        container.innerHTML += '<hr />';
    }

    this.showNewsPostSingle(container, newsPostArray[i]);
}

Then I have:

UserNewsPostList.prototype.showNewsPostSingle = function (container, newsPost) {
    var content = '<div class="user_news_post">';
    content += '<div id="user_news_post_comment_' + newsPost.id + '" class="user_news_post_comment"></div>';
    content += '</div>';
    container.innerHTML += content;
    new UserNewsPostListComment(newsPost).show(document.getElementById('user_news_post_comment_' + newsPost.id));
};

Which calls:

function UserNewsPostListComment(newsPost) {
    this.newsPost = newsPost;
}

UserNewsPostListComment.prototype.show = function(container) {
    var content = '';

    content += this.getNewsPostHTMLSingleCommentPartAdd();
    container.innerHTML = content;

    window.console.log(this.newsPost.id);

    document.getElementById('user_news_post_comment_add_button_show_form_' + this.newsPost.id).innerHTML = 'yahoooooo' + this.newsPost.id;
    document.getElementById('user_news_post_comment_add_button_show_form_' + this.newsPost.id).addEventListener('click', function() {alert('attachEvents');});
};

UserNewsPostListComment.prototype.getNewsPostHTMLSingleCommentPartAdd = function() {
    var content = '<div class="user_news_post_comment_add">';

    content += '<a id="user_news_post_comment_add_button_show_form_' + this.newsPost.id + '">LINK</a>';

    content += '</div>';

    return content;
};

Console shows: 4 3 2 1


Additional update: By doing step by step debugging in Chrome with the dev tools, it seems each links loses the click event as soon as the next

 container.innerHTML += '<hr />'; 

is executed in the first loop. Any reason why appending to a parent innerHTML (this one or another one) would delete the event listener added?

Brian Tompsett - 汤莱恩
  • 5,753
  • 72
  • 57
  • 129
abd
  • 379
  • 3
  • 14
  • You should show just a bit more of code so we can understand what's the closure of `this` or get an eye to your wrapping environment. – Roko C. Buljan Mar 26 '16 at 21:47
  • Would be even better if you can post a minimal but verifiable sample code, HTML, JS... – Roko C. Buljan Mar 26 '16 at 21:48
  • I believe you need to use IIFE. Please post more code for us to help you better. – Rahul Desai Mar 26 '16 at 21:51
  • Posted more code, and since the innerHTML of the link is updated with the proper id in the first getElementById, i don't think the ID is the issue: I get yahoooo1, yahooooo2, yahooooo3, yahoooo4 shown – abd Mar 26 '16 at 22:19

2 Answers2

2

With the line by line debug, I found out the next .innerHTML += was removing the events.

From that, I was able to find this problem: Manipulating innerHTML removes the event handler of a child element? and I was able to solve mine by using:

.insertAdjacentHTML('beforeend', 'test');
// instead of
.innerHTML += 'test';
abd
  • 379
  • 3
  • 14
0

I simulated your code and its working fine for me.

https://jsfiddle.net/zqt4bjtt/

following JS code used for simulation. Please see the jsfiddle for full simulation

id = 1;
while(id < 4){
    document.getElementById('user_news_post_comment_add_button_show_form_' + id).innerHTML = 'yahoooooo' + id;
    document.getElementById('user_news_post_comment_add_button_show_form_' + id).addEventListener('click', function() {alert(this.id);});
  id++;

}

Possibly the error maybe your this.newsPost.id is not changing. Hard to tell with the snippet provided

printfmyname
  • 983
  • 15
  • 30