e.target.hasClass() not working on all matching elements

I have a confusing situation ? I am making a to do list, and each (dynamically generated, hence no .click() ) task looks like the following:

<a href="#" class="col-xs-12 list-group-item task">
    <div class="col-xs-8 spacer p-l-0">
        <div class="col-xs-1 checkbox">
            <span class="fa fa-square-o"></span>
        </div>
        <div class="col-xs-11 p-x-0">
            <span class="task-text">Do that really cool thing</span>
            <p class="date m-b-0"><small class="text-muted"></small></p>
        </div>
    </div>
    <div class="col-xs-3 text-xs-right tag-container pull-xs-right p-r-0" id="tags1">
        <span class="label label-primary tag">cool</span>
        <span class="label label-primary tag">list</span>
    </div>
    <button type="button" class="btn btn-danger btn-sm task-button delete-button pull-xs-right"><i class="fa fa-times"></i></button>
    <button type="button" class="btn btn-warning btn-sm task-button edit-button pull-xs-right"><i class="fa fa-pencil"></i></button>

(I'm not sure why the last /a tag isn't showing up here, but it's there.

I have a function that runs when you click on the full task (simplified here):

$('#taskList').on("click", ".task", function(e) {
    if ($(e.target).is('button')) return;
    alert('clicked task');
});

As you can see, I DON'T want it to run if the user clicks either of the buttons, but I do want it to run at any other time. This works great for the "edit" button but for some reason doesn't work for the "delete" button and I cannot figure out why. Why isn't the button selector working for both? Happy to provide extra documentation as needed!

Thanks so much.

Answers 1

  • I would suggest attaching click handlers to your buttons and within those to call e.stopPropagation(), for example:

    $('#task-list').on('click', '.delete-button', onDeleteClick);
    
    var onDeleteClick = function(e) {
      e.stopPropagation();
      // perform deletion here... 
    };
    
    // same for other buttons...
    

    Then you can rest assured that the events won't bubble up into your task element:

    $('#taskList').on("click", ".task", onTaskClick);
    
    
    var onTaskClick = function(e) {
      // if button was clicked, this will never fire.
    }
    

Related Articles