window.onload 的问题

随着ajax的流行,页面中的JS代码越来越多。一般我们用JS处理页面时,都是使用window.onload等到页面加载完毕后再来处理,否则有时会出现文档未加载完毕而报的错误了。

但window.onload有一个不好的地方,它会等到整个页面(包括图片,flash等)全部加载完毕后,才会执行。一个页面中如果有很多图片,中间会有较长的延迟才会去执行我们的代码。

具体效果:http://www.ajaxeye.com/labs/domready.htm(注意页面中的两个小方块颜色,一开始默认都是红色,注意颜色的改变)

上面页面中,会在DOM树加载完毕后window.onload时分别改变两个小方块的颜色为绿色。

解决方法可以参见英文原文:
http://dean.edwards.name/weblog/2005/09/busted/
http://dean.edwards.name/weblog/2006/06/again/

解决方法就是想办法监听DOM树加载完毕的事件,等DOM树载完毕后执行我们的代码

  • Firefox、Opera9下,可以监听DOMContentLoaded事件来处理
  • IE下,可以给script标签加defer来处理

偶这个是从mootools,prototype中抠出来的IE,Firefox下测试通过

  1. Event.addDOMReadyEvent = function($callback) {   
  2.     var timer, fired = false;   
  3.        
  4.     function fireDOMReadyEvent() {   
  5.         if (fired) {   
  6.             return;   
  7.         }   
  8.         if (timer) {   
  9.             window.clearInterval(timer);   
  10.         }   
  11.         fired = true;   
  12.         $callback();   
  13.     }   
  14.        
  15.     // firefox, opera, safari ...    
  16.     if (document.addEventListener) {   
  17.         if (window.webkit) {   
  18.             timer = window.setInterval(function() {   
  19.                 if (/loaded|complete/.test(document.readyState)) {   
  20.                     fireDOMReadyEvent();   
  21.                 }   
  22.             }, 10);   
  23.                
  24.             Event.addEvent(window, 'load', fireDOMReadyEvent);   
  25.         } else {   
  26.             // firefox, opera9 使用 DOMContentLoaded   
  27.             document.addEventListener("DOMContentLoaded", fireDOMReadyEvent, false);   
  28.         }   
  29.     } else {   
  30.         // Internet Explorer中使用 defer 属性   
  31.         var src = (window.location.protocol == 'https') ? '://0' : 'javascript:void(0)';   
  32.         document.write('<SCRIPT id=__tbOnDOMReady src="' + src + '" defer><\/script>');   
  33.         $('__tbOnDOMReady').onreadystatechange = function() {   
  34.             if (this.readyState == 'complete') {   
  35.                 this.onreadystatechange = null;   
  36.                 fireDOMReadyEvent();   
  37.             }   
  38.         };   
  39.     }   
  40. }  
 

本文相关评论|Comments

to abo:
这篇日志的代码片段是不能正常运行的,只是写出了各浏览器下实现DOMReady的关键代码,如果要实例,请看http://www.ajaxeye.com/labs/domready.htm
JS代码可以直接另存
你好,这个东东正是我寻觅已久的,不过Event.addDOMReadyEvent 怎么个用法呢,我试了好几次都不对?望博主有空给个实例,不胜感激!
 

发表该文评论|Send Comment