3

I'm working with jQuery for the first time and need some help. I have html that looks like the following:

<div id='comment-8' class='comment'>
    <p>Blah blah</p>
    <div class='tools'></div>
</div>

<div id='comment-9' class='comment'>
    <p>Blah blah something else</p>
    <div class='tools'></div>
</div>

I'm trying to use jQuery to add spans to the .tools divs that call variouis functions when clicked. The functions needs to receive the id (either the entire 'comment-8' or just the '8' part) of the parent comment so I can then show a form or other information about the comment.

What I have thus far is:

<script type='text/javascript'>

    $(function() {
        var actionSpan = $('<span>[Do Something]</span>');
        actionSpan.bind('click', doSomething);

        $('.tools').append(actionSpan);
     });

     function doSomething(commentId) { alert(commentId); }

</script>

I'm stuck on how to populate the commentId parameter for doSomething. Perhaps instead of the id, I should be passing in a reference to the span that was clicked. That would probably be fine as well, but I'm unsure of how to accomplish that.

Thanks, Brian

6 Answers 6

6

Event callbacks are called with an event object as the first argument, you can't pass something else in that way. This event object has a target property that references the element it was called for, and the this variable is a reference to the element the event handler was attached to. So you could do the following:

function doSomething(event)
{
    var id = $(event.target).parents(".tools").attr("id");
    id = substring(id.indexOf("-")+1);
    alert(id);
}

...or:

function doSomething(event)
{
    var id = $(this).parents(".tools").attr("id");
    id = substring(id.indexOf("-")+1);
    alert(id);
}
Sign up to request clarification or add additional context in comments.

Comments

1

To get from the span up to the surrounding divs, you can use <tt>parent()</tt> (if you know the exact relationship), like this: <tt>$(this).parent().attr('id')</tt>; or if the structure might be more deeply nested, you can use parents() to search up the DOM tree, like this: <tt>$(this).parents('div:eq(0)').attr('id')</tt>.

To keep my answer simple, I left off matching the class <tt>"comment"</tt> but of course you could do that if it helps narrow down the div you are searching for.

Comments

0

You don't have a lot of control over the arguments passed to a bound event handler.

Perhaps try something like this for your definition of doSomething():

function doSomething() { 
  var commentId = $(this).parent().attr('id');
  alert(commentId); 
}

2 Comments

Check the HTML, it's actually the grandparent that has the id attribute, not the parent.
Indeed, the object with the trigger is inserted into the 'tools' div, I missed that. Thanks.
0

It might be easier to loop through the comments, and add the tool thing to each. That way you can give them each their own function. I've got the function returning a function so that when it's called later, it has the correct comment ID available to it.

The other solutions (that navigate back up to find the ID of the parent) will likely be more memory efficient.

<script type='text/javascript'>

$(function() {
  $('.comment').each(function(comment) {
    $('.tools', comment).append(
      $('<span>[Do Something]</span>')
          .click(commentTool(comment.id));
    );
  });
});

function commentTool(commentId) {
  return function() {
    alert('Do cool stuff to ' + commentId);
  }
}

</script>

Comments

0

Getting a little fancy to give you an idea of some of the things you can do:

var tool = $('<span>[Tool]</span>');

var action = function (id) {
    return function () {
        alert('id');
    }
}

$('div.comment').each(function () {
    var id = $(this).attr('id');

    var child = tool.clone();
    child.click(action(id));

    $('.tools', this).append(child);
});

Comments

0

The function bind() takes, takes the element as a parameter (in your case the span), so to get the id you want from it you should do some DOM traversal like:

function doSomething(eventObject) { 
    var elComment = eventObject.parentNode.parentNode; //or something like that, 
                                                       //didn't test it
    var commentId= elComment.getAttribute('commentId')
    alert(commentId); 
}

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.