YUI Library Home

YUI Library Examples: Event Utility: Using onAvailable, onContentReady, and onDOMReady

Event Utility: Using onAvailable, onContentReady, and onDOMReady

As web pages get richer, they tend to get slower. One way to make your pages as responsive as possible is to carefully storyboard the page-load and page-paint processes so that the interactions most central to the page's purpose are enabled as early as possible. The window object's load event won't happen until the full DOM and all image data have loaded. Putting off script execution until after the page loads can be optimal for some scripts, but sometimes you won't want to wait that long to make something draggable, to load a Calendar Control, to draw a Tabview, and so on.

The YUI Event Utility gives you three additional interesting moments that occur during a page's load process:

  1. onAvailable: onAvailable targets a single element and fires when that element is available (when it responds to document.getElementById()) — but you can't count on the element's children having been loaded at this point.
  2. onContentReady: When you care about not just your target element but its children as well, use onContentReady. This method will tell you that your target element and all of its children are present in the DOM.
  3. onDOMReady: Some DOM scripting operations cannot be performed safely until the page's entire DOM has loaded. onDOMReady will let you know that the DOM is fully loaded and ready for you to modify via script.

In the example box below, onAvailable, onContentReady and onDOMReady are all in use. A <div> (with a green background) loads; it has 100 chidren; one of those children is an arbitrarily large image that will take awhile to load. Keep an eye on the logger console at right. You'll see that the <div> (1) becomes available, (2) its content becomes ready (after all of its 100 children have loaded), (3) the DOM becomes ready, and finally (4) the page loads. (Note: In the Logger console, newer messages appear at the top.)

  • child node #0
  • child node #1
  • child node #2
  • child node #3
  • child node #4
  • child node #5
  • child node #6
  • child node #7
  • child node #8
  • child node #9
  • child node #10
  • child node #11
  • child node #12
  • child node #13
  • child node #14
  • child node #15
  • child node #16
  • child node #17
  • child node #18
  • child node #19
  • child node #20
  • child node #21
  • child node #22
  • child node #23
  • child node #24
  • child node #25
  • child node #26
  • child node #27
  • child node #28
  • child node #29
  • child node #30
  • child node #31
  • child node #32
  • child node #33
  • child node #34
  • child node #35
  • child node #36
  • child node #37
  • child node #38
  • child node #39
  • child node #40
  • child node #41
  • child node #42
  • child node #43
  • child node #44
  • child node #45
  • child node #46
  • child node #47
  • child node #48
  • child node #49
  • child node #50
  • child node #51
  • child node #52
  • child node #53
  • child node #54
  • child node #55
  • child node #56
  • child node #57
  • child node #58
  • child node #59
  • child node #60
  • child node #61
  • child node #62
  • child node #63
  • child node #64
  • child node #65
  • child node #66
  • child node #67
  • child node #68
  • child node #69
  • child node #70
  • child node #71
  • child node #72
  • child node #73
  • child node #74
  • child node #75
  • child node #76
  • child node #77
  • child node #78
  • child node #79
  • child node #80
  • child node #81
  • child node #82
  • child node #83
  • child node #84
  • child node #85
  • child node #86
  • child node #87
  • child node #88
  • child node #89
  • child node #90
  • child node #91
  • child node #92
  • child node #93
  • child node #94
  • child node #95
  • child node #96
  • child node #97
  • child node #98
  • child node #99
Uluru

Source Code for This Example:

Markup:

The markup used to create the DOM is very simple, consisting of a <div> that holds a <ul> with 100 child <li>s and a single ~3MB image. The <ul> will take a little time to load, and the image (loading over the internet) will take a few seconds to load even on a fast connection. That should allow us to see in the Logger console some time deltas between when the <div> whose ID is contentContainer becomes available, when its children (those 100 <li>s) are ready, when the DOM is ready (including all the navigation elements on the page), and lastly when the page loads (ie, when that ~3MB image is fully loaded).

1<div id="contentContainer"
2 
3    <!--a ul with an arbitrarily large number of children:--> 
4    <ul> 
5        <li>...</li> 
6        <!--...100 more of these--> 
7    </ul> 
8 
9    <img src="http://developer.yahoo.com/yui/docs/assets/examples/exampleimages/large/uluru.jpg" width="500" alt="Uluru" id="image" /> 
10 
11</div> 
view plain | print | ?

CSS:

The CSS colors the contentContainer element and hides the big list to keep the example more compact.

1<style> 
2    #contentContainer {padding:1em; background:#999966;} 
3    #contentContainer ul {height:0px; overflow:hidden;} 
4</style> 
view plain | print | ?

JavaScript:

In the script, we create an object called Timing within the example namespace. That object contains our event handlers. The handlers log a message about each event to the Logger console.

1YAHOO.example.Timing = function() { 
2 
3    //create shortcut for YAHOO.util.Event: 
4    var Event = YAHOO.util.Event; 
5 
6    //the returned object here will be assigned 
7    //to YAHOO.example.Timing and its members will 
8    //then be publicly available: 
9    return { 
10 
11        //we'll use this handler for onAvailable, onContentReady, //and onDOMReady: 
12        fnHandler: function(message) { 
13            //onDOMReady uses the Custom Event signature, with the object 
14            //passed in as the third argument: 
15            if(arguments.length > 2) { 
16                message = arguments[2]; 
17            } 
18            YAHOO.log(message, "info""example"); 
19             
20        }, 
21 
22        //we'll use this handler for the page load event: 
23        fnLoadHandler: function(oEvent, message) { 
24            YAHOO.log(message, "info""example"); 
25 
26            Event.onDOMReady(function() { 
27                YAHOO.log('A new onDOMReady subscriber that is attached after the moment has occured will still be notified.'); 
28            }); 
29        }, 
30 
31        init: function() { 
32             
33            //assign page load handler: 
34            Event.on(window, "load"this.fnLoadHandler, "The window.onload event fired.  The page and all of its image data, including the large image of Uluru, has completed loading."); 
35 
36            //assign onDOMReady handler: 
37            Event.onDOMReady(this.fnHandler, "The onDOMReady event fired.  The DOM is now safe to modify via script."); 
38             
39            //assign onContentReady handler: 
40            Event.onContentReady("contentContainer"this.fnHandler, "The onContentReady event fired for the element 'contentContainer'.  That element and all of its children are present in the DOM."); 
41 
42            //assign onAvailable handler: 
43            Event.onAvailable("contentContainer"this.fnHandler, "The onAvailable event fired on the element 'contentContainer'.  That element is present in the DOM."); 
44 
45        } 
46 
47    } 
48 
49}(); 
50 
51//initialize the example: 
52YAHOO.example.Timing.init(); 
view plain | print | ?

Configuration for This Example

You can load the necessary JavaScript and CSS for this example from Yahoo's servers. Click here to load the YUI Dependency Configurator with all of this example's dependencies preconfigured.

YUI Logger Output:

Logger Console

INFO 2736ms (+0) 11:58:10 PM:

global

A new onDOMReady subscriber that is attached after the moment has occured will still be notified.

INFO 2736ms (+0) 11:58:10 PM:

Event

DOMReady-> Subscriber { obj: null, overrideContext: no }

INFO 2736ms (+0) 11:58:10 PM:

example

The window.onload event fired. The page and all of its image data, including the large image of Uluru, has completed loading.

INFO 2736ms (+0) 11:58:10 PM:

Event

DOMReady-> Subscriber { obj: null, overrideContext: no }

INFO 2736ms (+0) 11:58:10 PM:

Event

DOMReady-> Subscriber { obj: null, overrideContext: no }

INFO 2736ms (+0) 11:58:10 PM:

example

The onDOMReady event fired. The DOM is now safe to modify via script.

INFO 2736ms (+0) 11:58:10 PM:

Event

DOMReady-> Subscriber { obj: The onDOMReady event fired. The DOM is now safe to modify via script., overrideContext: no }

INFO 2736ms (+28) 11:58:10 PM:

Event

Firing CustomEvent: 'DOMReady', context: [object Object], args: , subscribers: 3

INFO 2708ms (+2665) 11:58:10 PM:

LogReader instance0

LogReader initialized

INFO 43ms (+0) 11:58:07 PM:

example

The onContentReady event fired for the element 'contentContainer'. That element and all of its children are present in the DOM.

INFO 43ms (+43) 11:58:07 PM:

example

The onAvailable event fired on the element 'contentContainer'. That element is present in the DOM.

INFO 0ms (+0) 11:58:07 PM:

global

Logger initialized

More Event Utility Resources:

Copyright © 2009 Yahoo! Inc. All rights reserved.

Privacy Policy - Terms of Service - Copyright Policy - Job Openings