Using load() within ready() and changing markup IDs of those loaded

I’m trying to use <element>.load() within a document.ready() block to dynamically load specific elements from another page (on the same server) and from those loaded, add an ID to the elements by using either attr() or prop(). Here’s the problem: attr() and prop() will not add the ID to save my life. They just won’t, and from what little I understand about this, it boils down to having to do with how the elements have been loaded. For example, there’s something I read somewhere about how elements that get loaded this way have to be “bound” using something like live() or bind() before any changes can be made to the elements. Is this true?

Here’s my code:

    $('#r div form[name="loginform"]').load('foobar.htm #UserID, input[type="password"], input[type="submit"]');
    $('#r div form[name="loginform"] input[type="submit"]').prop('id', 'submit');

The first line ensures the document is done loading before anything else… No biggy there. The next line loads the login form elements (#UserID, password input, and the submit button) into the current page from the foobar.htm. It puts these into a form element. The next line I’m trying to use to change the new submit button’s ID… But no dice.

It just won’t work! No matter what I do… I’ve even tried to light some candles and poke some needles into some effigies… Just… Won’t… Work. And since I don’t know enough about binding things in jQuery / JavaScript, I’m hoping someone on here knows enough about this kind of approach to shine some light.

What am I doing wrong?

Note: When outputting the resulting “ID assignment attempt” using console.log as follows, it comes back as undefined:

console.log($('#r div form[name="loginform"] input[type="submit"]').prop('id'));

Help is VERY appreciated here. It’s so frustrating.

Hi there,

what about using .ajaxComplete()?

  $('#r div form[name="loginform"]').load('foobar.htm #UserID, input[type="password"], input[type="submit"]');
  $('#r div form[name="loginform"]').ajaxComplete(function() {
    $('#r div form[name="loginform"] input[type="submit"]').attr('id', 'submit');

This should hopefully work in your case.

@Pullo; is heading in the right direction, but .ajaxComplete is a bit too much here. .ajaxComplete responds to every AJAX request that is ever fired, not just the one(s) started on the object.
Fortunately, there’s a relatively simple alternative; just use a callback function to jQuery.load:

$(document).ready(function() {
  $('#r div form[name="loginform"]').load('foobar.htm #UserID, input[type="password"], input[type="submit"]', function() {
    $('#r div form[name="loginform"] input[type="submit"]').attr('id', 'submit');

The problem with your script was that the javascript doesn’t wait for .load to be ready, but just goes on to the next line. At that point the new data hasn’t been loaded yet, so nothing can be done.

As an aside, those selector’s you’re using look pretty overkill. Since #r is an ID, you should be able to just use the following:

$(document).ready(function() {
  $('#r form[name="loginform"]').load('foobar.htm #UserID, input[type="password"], input[type="submit"]', function() {
    $('#r input[type="submit"]').attr('id', 'submit');

Wow, that’s cool. I didn’t know you could do that.
Thanks, Rémon.

Thanks for the info, guys. I really appreciate it and I was able to have better control over the elements with the above suggestions. :slight_smile:

Rémon, could you elaborate a bit on why load() wasn’t being executed after the page finished loading? I’m a little confused about that part… Are you saying that I didn’t call / execute it correctly or that it just needed something extra to it to make it function correctly (i.e. - your callback). I guess I’m just not understanding why that callback was so important in this… :S

That’s actually quite straight forward:
You want to load elements from an external file via Ajax.
So, in your script you fire of an asynchronous request (using .load()) to go get these elements.
However, while that request off doing what you asked it to do, execution continues in your main file.
The next thing your code does is try to manipulate the elements you’re attempting to fetch.
Yet the request still hasn’t completed at this point, so the elements simply aren’t present in the DOM.

Using a callback is a way of telling JavaScript to wait until it has finished fetching the elements, before doing something with them.

I hope that makes sense. If not, I’m sure Rémon can explain it better :slight_smile:

Yeah, I guess that does make sense but how would one know to suspect something like that? I mean, how would one know something like that is responsible? I’ll have to go look again at the jQuery write-up about that function to see what’s mentioned about it because it seems logical to me to think that load() should have some form or feature which says, “…don’t continue until you’re finished,” as most functions seem to do. I mean, most functions seem to return something. Does load? And if so, shouldn’t a return of data indicate that it’s finished loading whereby execution of the script would continue?

(Again, I’ll need to go look at the load() jQuery page again, but I guess I’m just “thinking out loud.”)

There are a number of calls in JavaScript that work asynchronously - which means that they don’t wait for the call to finish before running the code that follows them. When your JavaScript or the jQuery processing you are calling uses an asynchronous command you need to use a callback function to define what is to be run using whatever the call eventually returns.

Perhaps the simplest example is the setTimeout command which simply adds the callback function you specify in the first parameter to the queue of commands to run after the time specified in the second parameter has elapsed.

It helps to read the api documentation, where you can read which parameters it can take:

.load( url [, data] [, complete(responseText, textStatus, XMLHttpRequest)] )
url - A string containing the URL to which the request is sent.
data - A map or string that is sent to the server with the request.
complete(responseText, textStatus, XMLHttpRequest) - A callback function that is executed when the request completes.

As you can see, the last parameter gives you the clue you need.

Please don’t get me wrong, I’m not telling you to RTFM.
This was something I had to learn to do myself (i.e. to read the docs), but since I have started doing this, I am amazed at how much more effective I have become.

My initial answer to your question (incorrect as it was) also proves the validity of this method.
Had I first looked at the documentation I would have seen what Rémon pointed out.
Instead I googled something like “manipulate DOM elements after load()”, found something about ajaxComplete() on Stack overflow, checked it worked and posted my answer.

Hope this helps