1

How come the following does not work (attribute values are all 'undefined')

$(".item").wrap('<a href="' + $(this).attr("data-pid") + '.html"></a>');

but this code does?

$('.item').each(function(){
    $(this).wrap('<a href="' + $(this).attr("data-pid") + '.html"></a>');
});

Thanks

2
  • this is defined by the parent function, in your case this would be global window or whatever you have. If you create a function this will be defined as the element you are targeting. Commented Mar 4, 2014 at 14:30
  • It is a scoping thing. I'm not really sure what the this in '<a href="' + $(this).attr("data-pid") + '.html"></a>' would be referring to without more context. The this in the second example refers to the .item because of the anonymous function it was called from more or less belonging to the .item. Commented Mar 4, 2014 at 14:31

3 Answers 3

2

It's because calling $(this) when looking up a class means you are effectively looking at a collection of objects not the individual object which has the attr property (the collection doesn't have an attr property as it wouldn't make sense for it to have one).

Iterating over the collection with $.each means you can access each element and access its attr property.

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

Comments

2
$('.item').each(function(){
    $(this).wrap('<a href="' + $(this).attr("data-pid") + '.html"></a>');
});

this refer to the current element in the each function block


Better Version of your code

$('.item').wrap(function () {
    return '<a href="' + $(this).data("pid") + '.html"></a>';
});

$(".item").wrap('<a href="' + $(this).attr("data-pid") + '.html"></a>');

here this is window object which doesn't have attr("data-pid") so it return undefined

5 Comments

The OP seems to know that, as the code you posted is exactly what he posted saying that it works. He wants to know why the first example doesn't work.
@j08691 was just updating sir. Updated now
Does the callback function in wrap() automatically iterate through the collection, i.e. all elements? If yes then why is it better than each()?
@ScepticalJule yes it does you can try it :)
I just did and it works like charms but I needed to understand what I write.
0

The dot in $('.whatever') indicates a selector of class names, which doesn't guarantee you finding a unique element. This means you could potential be selecting a collection instead which you'd need to iterate over or do a .each() over.

If you have an ID to use instead, you could try this:

$('#whatever')

Which is a selector based on ID instead. As long as you're safe with your ID's (only one element has that ID name), it should be safe.

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.