1

I have a PHP file that is generating HTML elements, and is being called from AJAX when the page loads. What I am looking to do is apply JQuery to the dynamically generated elements, so for each time a label, generated from the PHP file, is clicked something happens. I tried placing the JQuery code in the PHP file and echo it out, but that didnt work, I also placed the code in the HTML page, where the AJAX is being called, but that didnt work either.

In my HTML I have:

<body onLoad="javascript:getLabels();">, 

This calls the php file through AJAX:

function getComments() { 
    var thePage ='loadLabels.php'; 
    ... 

The PHP file as the line:

echo '<label id="labellink" class="ldClass">Label </label>'; 

which could be more then one label in the page once loaded, but all in their one <form>, so I need to use JQuery so once the labels are loaded and I click on them, I can make something happen.

2
  • Here is my code as it is at the mo, in my HTML page I have this line: <body onLoad="javascript:getLabels();">, this calls the php file through AJAX:function getComments() { var thePage ='loadLabels.php'; ... ... and the PHP file as the line: echo '<label id="labellink" class="ldClass">Label </label>'; which could be more then one label in the page once loaded, but all in their one <form>, so I need to use JQuery so once the labels are loaded and I click on them, I can make something happen. Thanks for the info regarding .On(), .live() and .delegate lads, I'll check them out !! Commented May 10, 2012 at 20:40
  • You aren't using the same ID for all of your labels are you? Commented May 10, 2012 at 21:46

6 Answers 6

2

There are 2 ways to achieve what you want.

1: attach the events to the link inside the onSuccess of your AJAX call to retrieve the content. That way when new content are added to the DOM, you'll attach the necessary events to those specific elements.

2: the recommended solution is to use event delegation. Basically, instead of attaching the events to specific elements, you attach a single event to the parent element container, and when the event is triggered, it based on conditioning the clicked target (if it has a specific class per se) you perform the specific actions. This is a technique used to handle fluid/changeable content without having to r-eattach events to the specific elements. jQuery's .on() API method provides such solution elegantly: http://api.jquery.com/on/

For example:

$("#container").on("a.changeColor", "click", function() {
  $(this).toggleClass("newColor");
});

You delegate/attach the event to the parent element with the id="container", tell it that you want all the child anchor elements with the "changeColor" class to toggle the "newColor" class. Even after you update and change the inner content of the #container element, the new elements with class "changeColor" will still inherit the behavior when clicked.

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

Comments

2

.on() (Documentation) provides a method of creating handlers for dynamic elements, that may not necessarily exist when the handler is created.

To use .on(), you need to attach the handler to a non-dynamic object higher in the DOM tree. The click will propagate up the tree from the child element, at which point the handler (delegate) attached with .on() will use the provided filter to see if the click originated in the correct object (which would be your dynamic object).

$('body').on('click', '.dynamic_element', function() {
   // Handler code
});

In this case I used body, because it won't disappear and take the handler with it. You can attach the handler to any object that is an ancestor of .dynamic_element, as long as it is a static element. Closer is generally better, but if your page is very dynamic, body will work.

The whole idea behind .on() is that handlers must be attached to an existing DOM element. If an object doesn't exist yet, you cannot attach a handler to it, and if your element is removed, the handler is removed as well. This is why $('.dynamic_element').click() won't work, unless .dynamic_element already exists. So, with .on(), we just attach the handler to something we know does exist (and won't disappear). This handler is called a "delegate". It watches for events from its child objects, which by the nature of DOM elements, propagate up the tree.

1 Comment

@jeroen: What do you mean? To use .on() in the delegate context, you need to call it on an ancestor (the delegate) and pass a selector as a filter. If you use .on() directly (without a selector), it is equivalent to .bind(), which does not apply to future dynamically added objects. See example: jsfiddle.net/5B4Kd
2

What you want is jQuery "live" http://api.jquery.com/live/

Edit: You want .on() in the newer versions of jQuery since .live() has been depreciated: http://api.jquery.com/on/

See comments below for more info.

5 Comments

Actually, he wants .on(). .live() has been deprecated in the latest versions of jQuery.
Great info! I was not aware of that change.
.live() is deprecated, and .delegate() should be used instead.
.delegate is also deprecated, fwiw.
.delegate() is also superseded by .on(). .on() combines the functionality of .live(), .delegate(), and .bind(), depending on how you pass your arguments.
1

Edit Thank you for correcting me on that. Since it is depreciated, I haven't used it in a while.

I'm sure this counts as more of a "hack" than a solution, and I will openly welcome downvotes if necessary, but you could put the post-AJAX functionality within the success function.

Also, older versions of jQuery used a function called .live() which would look for an element whether it was in the DOM or not. It's depreciated in the newest version of jQuery, but if you're willing to take that leap, I know for a fact that it worked in 1.5. (I'm talking about something like $(a).live('click', function () { });).

For the record, I would love to have posted this as a comment rather than an answer, but I don't have enough street cred for that yet.

1 Comment

That is not how you use .live(). The correct way would be $('a').live('click', function() { });. See several of the other answers for the more current way of doing this.
0

Just an example of dynamic created elements and onload bound events

var a = $("<a>").attr('href','#')
                .attr('class','elem')
                .text('click me')
                .prependTo('body');
$(document).on("click", "a.elem", function(e){ 
    e.preventDefault();
    alert("Goodbye!"); 
});

Comments

-1

Using .delegate() is the best way I have ever used.

refer http://api.jquery.com/delegate/

4 Comments

.delegate() functionality has also been superseded by .on() in the latest versions of jQuery.
It is not suppressed. Rather .on is introduced in new version for jQuery for cool naming. But delegate is a standard name. And we should follow the standard.
What? Not suppressed, superseded. It states directly in the documentation that it has been superseded. on() combines the functionality of delegate() as well as live() and bind(). It is not just for "cool naming".
Thanks for the info. I used to use .delegate()

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.