javascript 模拟JQuery的Ready方法实现并出现的问题
2009-12-06 00:00
1006 查看
dom加载完后执行,一直不了解,基于对网上的一些方法逻辑不了解,所以去看了《jquery源代码研究(ready函数) 》这篇文章后自己写入如下代码(已有详细说明)
由于要和jq做对比,所以测试时候需要导入jq库。函数本身是没有调用jq的,请放心引用。
代码我通过封装完成,直接Darren.ready(fn)就可执行。
后来通过测试还是出现一个奇怪的问题:在FF下的执行顺序是jq -> my -> load 。也就是说我这个函数能够在onload事件执行前触发,但会晚于jq的ready。对这个还是比较满意。
但是在IE下测试居然是:jq -> load -> my。也就是 我的这个函数虽然能够把代码提前,但是还是在onload事件执行后触发的,百思不得其解。
完同志们解答下如何实现onload之前执行,jq又是怎么实现的,我完全模拟jq的结构,但是还是不能达到目的,难道中间有漏?
另大家可以参考下面的代码
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head> <meta http-equiv="Content-Type" content="text/html; charset=gb2312" /> <title>document.ready</title> <script type="text/javascript" src="js/jquery-1.3.2.js"></script> <script type="text/javascript"> var Darren; (function(){ var isReady=false; //是否已经加载完毕 var readBound=false; //判断是否已经调用过循环事件 var readylist=[]; //把需要执行的方法先暂存在这个数组里 //判断浏览器,该方法来自Cloudgamer JavaScript Library v0.1 var Browser = (function(ua){ var b = { msie: /msie/.test(ua) && !/opera/.test(ua), opera: /opera/.test(ua), safari: /webkit/.test(ua) && !/chrome/.test(ua), firefox: /firefox/.test(ua), chrome: /chrome/.test(ua) }; var vMark = ""; for (var i in b) { if (b[i]) { vMark = i; } } if (b.safari) { vMark = "version"; } b.version = RegExp("(?:" + vMark + ")[\\/: ]([\\d.]+)").test(ua) ? RegExp.$1 : "0"; b.ie = b.msie; b.ie6 = b.msie && parseInt(b.version) == 6; b.ie7 = b.msie && parseInt(b.version) == 7; b.ie8 = b.msie && parseInt(b.version) == 8; return b; })(window.navigator.userAgent.toLowerCase()); function bindReady() { if(readBound){ //保证bindReady方法只执行一遍 return; } readBound=true; //For IE并且不是嵌套在frame中 if (Browser.msie && window==top) { (function(){ if (isReady) { return; } try { document.documentElement.doScroll("left"); //如果没加载dom完毕这个会报错 } catch (error) { setTimeout(arguments.callee, 0); //循环调用父函数,也就是ready方法 return; } Test.Done(); })(); }else if(Browser.firefox)//For FF { document.addEventListener( "DOMContentLoaded", Test.Done, false ); } } var Test={ ready:function(fn){ bindReady();//判断是否加载完毕 if(isReady) { fn.call(document); //加载完毕,直接调用 }else{ readylist.push(fn);//如果还没加载完成则将该方法暂存到readylist数组中,以便以后调用 } return this; } }; //静态方法:加载完毕执行 Test.Done=function(){ if (!isReady) { isReady=true; } readylist[0].call(document); } Darren=Test; })(); //测试 Darren.ready(function(){ alert("my"); document.getElementById("test").innerHTML="haha" //成功读取dom }); $(function(){alert("jq")}); window.onload=function(){alert("default")} </script> </head> <body> <div id="test">test</div> </body> </html>
由于要和jq做对比,所以测试时候需要导入jq库。函数本身是没有调用jq的,请放心引用。
代码我通过封装完成,直接Darren.ready(fn)就可执行。
后来通过测试还是出现一个奇怪的问题:在FF下的执行顺序是jq -> my -> load 。也就是说我这个函数能够在onload事件执行前触发,但会晚于jq的ready。对这个还是比较满意。
但是在IE下测试居然是:jq -> load -> my。也就是 我的这个函数虽然能够把代码提前,但是还是在onload事件执行后触发的,百思不得其解。
完同志们解答下如何实现onload之前执行,jq又是怎么实现的,我完全模拟jq的结构,但是还是不能达到目的,难道中间有漏?
另大家可以参考下面的代码
var ready=function(readyCall) { if(document.addEventListener) document.addEventListener("DOMContentLoaded",function() { document.removeEventListener("DOMContentLoaded",arguments.callee,false); readyCall(); },false); else if(document.attachEvent) {//for IE if(document.documentElement.doScroll && window.self==window.top) { (function() { try { document.documentElement.doScroll("left"); }catch(ex) { setTimeout(arguments.callee,5); return; } readyCall(); })(); }else {//maybe late but also for iframes document.attachEvent("onreadystatechange",function() { if(document.readyState==="complete") { document.detachEvent("onreadystatechange", arguments.callee); readyCall(); } }); } } }
相关文章推荐
- 模拟JQuery的Ready方法实现并出现的问题
- 模拟jQuery中的ready方法及实现按需加载css,js实例代码
- 1多线程的概述2多线程(创建多个线程实例,并启动多个线程)的实现方式,main主方法是单线程的4多线程的实现方式5多线程模拟火车站售票出现问题7线程的声明周期
- JavaScript之JS原生方法实现jQuery的ready()
- 用Jquery实现表格呈现数据出现的小问题(给表格添加边框颜色失败)
- 关于Javascript与表单结合时出现"对象不支持此属性或方法"的问题总结(不断更新中...)
- cocos2dx 3.x 模态对话框实现中易出现问题解决方法
- ECharts, PHP, MySQL, Ajax, JQuery 实现前后端数据可视化时出现的问题
- 用原生JavaScript实现jQuery的$.getJSON的解决方法
- JS原生方法实现jQuery的ready()
- 在discuz上实现模糊查询出现的问题及解决方法
- Webservice中如何实现方法重载--(方法名同名时出现的问题)
- 枚举 编程题#1: 画家问题(Coursera 程序设计与算法 专项课程4;枚举方法:用二进制依次加1的进位方法模拟实现)
- Jquery中$(document).ready()的作用类似于传统JavaScript中的window.onload方法
- 使用jquery的load方法设计动态加载,并解决被加载页面JavaScript失效问题
- jquery下动态显示jqGrid以及jqGrid的属性设置容易出现问题的解决方法
- 用javascript实现jquery的document.ready功能的实现代码
- 【CVTE】请使用原声Javascript实现一个方法,判断html中出现次数最多的标签,并统计这个次数
- javascript模拟评分控件实现方法