您的位置:首页 > Web前端 > JavaScript

javascript 跨文档调用技术

2010-03-11 21:43 399 查看
这是一种很有前途的技术,可惜生不逢时,IE刚打垮网景,火狐又冒出来了。这种技术是我在设计超级数组对象时发现的。由于直接继承原生数组问题多,我只有用Object与Array的原型方法构建一个新类。不用说,效率不太理想。直到我已把超级数组臻至完美的今天,我还在不断寻找新的替代方案,于是我就想到用另一个文档的数组对象来构建。经测试,IE下是完美的。后来我又发现早在2006年全知全能的DE大神早已做了这样的探索,在《How To Subclass The JavaScript Array Object》中应用这种技术,我只不过是重新把它发挖出来而已。但是,以后就没有下文了,DE大神在他的Base2类库构建Array2对象时也没有应用这种技术。不明真相的我一头扎下去,哎呀!DE大神你真坏,有陷阱也不通报声!

下面就拿DE大神的例子改一下,演示究竟出了什么状况?!

window.onload = function(){
//创建一个iframe
var iframe = document.createElement("iframe");
iframe.style.display = "none";
document.body.appendChild(iframe);
// 取得iframe文档的数组对象
frames[frames.length - 1].document.write(
"<script>parent.Array2 = Array;<\/script>");
var a = Array2(1,2,3,4),
b = a.slice(2)
alert(b instanceof Array)//万恶的safari与firefox总是试图把沙箱文档的数组实例转化为本地文档的数组实例
a.push(5);
alert(a instanceof Array)//同上,safari与firefox受影响的方法是所有返回数组的方法……晕
}


<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8" />
<meta content="IE=8" http-equiv="X-UA-Compatible"/>
<title>跨文档调用 by 司徒正美 </title>
<script type="text/javascript">

window.onload = function(){

//创建一个iframe
var iframe = document.createElement("iframe");
iframe.style.display = "none";
document.body.appendChild(iframe);
// 取得iframe文档的数组对象
frames[frames.length - 1].document.write(
"<script>parent.Array2 = Array;<\/script>");
var a = Array2(1,2,3,4),
b = a.slice(2)
alert(b instanceof Array)//万恶的safari与firefox总是试图把沙箱文档的数组实例转化为本地文档的数组实例
a.push(5);
alert(a instanceof Array)//同上,safari与firefox受影响的方法是所有返回数组的方法……晕
}
</script>
</head>
<body>

</body>
</html>

运行代码

为了方便,我把iframe中的文档对象的javascript环境中的数组对象称之为沙箱数组,意即,它不受本地数组对象影响。对,本地数组的原型进行扩展,不会殃及沙箱数组。俗话说,龙生龙,凤生风,老鼠的儿子会打洞!事实也应该如此!看,firefox与safari做了什么好事!沙箱数组变成原生数组了,我们在沙箱数组上做的扩展成了废物了!而且现在是linux大多数系统捆绑firefox,Mac捆绑safari,真不好办……

别以为跨文档调用技术只能干这事,只是它的潜力还有待发掘而已。现在再解释一下上面那段用到的长长的定语。什么叫做“iframe中的文档对象的javascript环境……”?由于框架技术的发展,一个页面并不只有一个文档对象(在HTML5中,有关框架的标签只死剩iframe了)。最顶层的我们称之为本地文档,iframe与frame的文档我称之为沙箱文档。由于它们的相对独立性,人们最喜欢用iframe做富文本编辑器,省得调用document.execCommand( "BackColor", "", "red" )命令,整个页面都红了。不过,本地文档也好,iframe文档也好,它们都属于HTML文档。另,创建HTML文档也不单止iframe标签(frame标签我向来无视),还有ActiveXObject与createDocument,DOMParser等方法。

ActiveXObject是指ActiveXObject("htmlfile"),谷歌的gtalk就是用它结合其他技术实现push的技术。ActiveXObject("htmlfile")创建的文档是一个完美的HTML文档,它拥有document.title,document.body等HTML DOM专有的属性,还能运行javascript。全局变量this就是我们要找的全局对象,它还拥有我们想要的一切,Array,Boolean,String,Date,Object等等。我们需要调用它们为我们做事,问题是标准浏览器能有像ctiveXObject("htmlfile")这样便捷的方法创建另一个文档吗?这些文档能拥有独立的javascript运行环境吗?这正是我们下面要讲的。

w3c还真是实现了一些创建文档的方法,不过都比较偏~~~

利用createHTMLDocument(title)创建文档

title参数为tilte元素的innerText。

window.onload = function(){
try{
var doc = document.implementation.createHTMLDocument('跨文本调用技术 by 司徒正美');
var html = doc.documentElement
alert(html)        //测试是否存在HTML元素
alert(html.tagName)//注意大小写,HTML文档会把元素节点的tagName与nodeName大写化,按理应该会返回“HTML”
var body = doc.body
alert(body);      //测试document.body
if("title" in doc){
alert(doc.title)//测试document.title
}
var head = doc.getElementsByTagName("head")[0]
alert(head);
if(head && "innerHTML" in head){
alert("head.innerHTML = "+head.innerHTML)//测试innerHTML,HTML文档的元素节点都会支持这属性,及head与title是否存在套嵌关系
alert("html.innerHTML = "+html.innerHTML)
}
if("outerHTML" in html){  //outerHTML也是HTML5的标准API
alert("html.outerHTML = "+html.outerHTML)
}
var script = doc.createElement("script");
html.insertBefore(script,null);
script.appendChild(doc.createTextNode("alert('能调用javascript')"))//测试是否能动态解析脚本,注意这里是否弹出
var xpath = doc.evaluate && doc.evaluate('//title', doc, null, 7, null);
alert("测试xpath")
alert(xpath && xpath.snapshotItem(0) )
}catch(e){
alert("不支持createHTMLDocument方法")
}
}


<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8" />
<meta content="IE=8" http-equiv="X-UA-Compatible"/>
<title>跨文档调用 by 司徒正美 </title>
<script type="text/javascript">
window.onload = function(){
try{
var doc = document.implementation.createHTMLDocument('跨文本调用技术 by 司徒正美');
var html = doc.documentElement
alert(html) //测试是否存在HTML元素
alert(html.tagName)//注意大小写,HTML文档会把元素节点的tagName与nodeName大写化,按理应该会返回“HTML”
var body = doc.body
alert(body); //测试document.body
if("title" in doc){
alert(doc.title)//测试document.title
}
var head = doc.getElementsByTagName("head")[0]
alert(head);
if(head && "innerHTML" in head){
alert("head.innerHTML = "+head.innerHTML)//测试innerHTML,HTML文档的元素节点都会支持这属性,及head与title是否存在套嵌关系
alert("html.innerHTML = "+html.innerHTML)
}
if("outerHTML" in html){ //outerHTML也是HTML5的标准API
alert("html.outerHTML = "+html.outerHTML)
}
var script = doc.createElement("script");
html.insertBefore(script,null);
script.appendChild(doc.createTextNode("alert('能调用javascript')"))//测试是否能动态解析脚本,注意这里是否弹出
var xpath = doc.evaluate && doc.evaluate('//title', doc, null, 7, null);
alert("测试xpath")
alert(xpath && xpath.snapshotItem(0) )
}catch(e){
alert("不支持createHTMLDocument方法")
}
}
</script>
</head>
<body>

</body>
</html>

运行代码

.table1 {
border:1px solid #666;border-collapse:collapse;width:700px
}
.table1 th ,.table1 td{
border:1px solid #666;
}

IE6IE8FF3.6safari4.0opera10.50chrome5.0
能否创建文档×××
doc.documentElement为HTML标签×××
是否支持title属性×××
是否支持body属性×××
元素节点是否支持innerHTML×××
元素节点是否支持outerHTML×××
是否支持动态解析脚本××××××
是否支持xpath×××
有关这方法更多的资料可点这里这里,很可能成为HTML5的标准API。

利用createDocument(namespaceURI , qualified , doctype )创建文档

第一个参数为字符串,指定命名空间,第二个参数为字符串,指定第一个元素的标签类型(tagName),第三个参数为对象,这个不用说吧,见字明义。

window.onload = function(){
try{
var doc = document.implementation.createDocument(null, 'html', null);
var html = doc.documentElement
alert("doc.documentElement = "+html)        //测试是否存在HTML元素
alert("html.tagName = "+html.tagName)//注意大小写,HTML文档会把元素节点的tagName与nodeName大写化,按理应该会返回“HTML”
var body = doc.body
alert("doc.body = "+body);      //测试document.body
if("title" in doc){
doc.title = "跨文档调用 by 司徒正美 "
var title = doc.getElementsByTagName("title")[0]
alert("title元素是否存在 = "+ title)
alert("doc.title = "+doc.title)//测试document.titl
}
var head = doc.getElementsByTagName("head")[0]
alert("是否有head元素 = " + head);
if(head && "innerHTML" in head){
alert("head.innerHTML = "+head.innerHTML)//测试innerHTML,HTML文档的元素节点都会支持这属性,及head与title是否存在套嵌关系
alert("html.innerHTML = "+html.innerHTML)
}
if("outerHTML" in html){  //outerHTML也是HTML5的标准API
alert("html.outerHTML = "+html.outerHTML)
}
var script = doc.createElement("script");
html.insertBefore(script,null);
script.appendChild(doc.createTextNode("alert('能调用javascript')"))//测试是否能动态解析脚本,注意这里是否弹出
alert("测试xpath = "+ doc.evaluate )
}catch(e){
alert("不支持createDocument方法")
}
}


<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8" />
<meta content="IE=8" http-equiv="X-UA-Compatible"/>
<title>跨文档调用 by 司徒正美 </title>
<script type="text/javascript">window.onload = function(){ try{ var doc = document.implementation.createDocument(null, 'html', null); var html = doc.documentElement alert("doc.documentElement = "+html) //测试是否存在HTML元素 alert("html.tagName = "+html.tagName)//注意大小写,HTML文档会把元素节点的tagName与nodeName大写化,按理应该会返回“HTML” var body = doc.body alert("doc.body = "+body); //测试document.body if("title" in doc){ doc.title = "跨文档调用 by 司徒正美 " var title = doc.getElementsByTagName("title")[0] alert("title元素是否存在 = "+ title) alert("doc.title = "+doc.title)//测试document.titl } var head = doc.getElementsByTagName("head")[0] alert("是否有head元素 = " + head); if(head && "innerHTML" in head){ alert("head.innerHTML = "+head.innerHTML)//测试innerHTML,HTML文档的元素节点都会支持这属性,及head与title是否存在套嵌关系 alert("html.innerHTML = "+html.innerHTML) } if("outerHTML" in html){ //outerHTML也是HTML5的标准API alert("html.outerHTML = "+html.outerHTML) } var script = doc.createElement("script"); html.insertBefore(script,null); script.appendChild(doc.createTextNode("alert('能调用javascript')"))//测试是否能动态解析脚本,注意这里是否弹出 alert("测试xpath = "+ doc.evaluate ) }catch(e){ alert("不支持createDocument方法") } }</script>
</head>
<body>

</body>
</html>

运行代码

IE6IE8firefox3.6safari4.0.4opera10.50chrome5.0
能否创建文档××
doc.documentElement为HTML标签××
是否支持title属性××××××
是否支持body属性××××××
元素节点是否支持innerHTML××××××
元素节点是否支持outerHTML××××××
是否支持动态解析脚本××××××
是否支持xpath××
▲是因为标准浏览器返回的是 [object Element],而非正确的[object HTMLHtmlElement],证明它生成的是XML文档。

有关这方法更多的资料可点这里

利用命名空间与createDocument创建文档

window.onload = function(){
try{
var namespace = 'http://www.w3.org/1999/xhtml';
var doc = document.implementation.createDocument(namespace, 'html', null);
var html = doc.documentElement
alert("doc.documentElement = "+html)        //测试是否存在HTML元素
alert("html.tagName = "+html.tagName)//注意大小写,HTML文档会把元素节点的tagName与nodeName大写化,按理应该会返回“HTML”
if("title" in doc){
doc.title = "跨文档调用 by 司徒正美 "
var title = doc.getElementsByTagName("title")[0]
if(!!title){
alert("本来就存在title元素 "+ +doc.title)//测试document.title
}else{
alert("开始创建元素")
try{
html.innerHTML = "<head><title>由innerHTML创建的title</title></head><body></body>"
}catch(e){
var head = doc.createElement("head");
html.appendChild(head);
var title = doc.createElement("title");
head.appendChild(title);
title.appendChild(doc.createTextNode("由DOM API创建的title"));
var body = doc.createElement("body");
html.appendChild(body);
}
alert("doc.title = "+ doc.title)
}
}
if("innerHTML" in html){
alert("html.innerHTML = "+html.innerHTML)
}
if("outerHTML" in html){
alert("html.outerHTML = "+html.outerHTML)
}
alert("doc.body = "+doc.body)
var script = doc.createElement("script");
html.insertBefore(script,null);
script.appendChild(doc.createTextNode("alert('能调用javascript')"))//测试是否能动态解析脚本,注意这里是否弹出
alert("测试xpath = "+ doc.evaluate )
}catch(e){
alert("不支持createHTMLDocument方法")
}
}


<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8" />
<meta content="IE=8" http-equiv="X-UA-Compatible"/>
<title>跨文档调用 by 司徒正美 </title>
<script type="text/javascript">
window.onload = function(){
try{
var namespace = 'http://www.w3.org/1999/xhtml';
var doc = document.implementation.createDocument(namespace, 'html', null);
var html = doc.documentElement
alert("doc.documentElement = "+html) //测试是否存在HTML元素
alert("html.tagName = "+html.tagName)//注意大小写,HTML文档会把元素节点的tagName与nodeName大写化,按理应该会返回“HTML”
if("title" in doc){
doc.title = "跨文档调用 by 司徒正美 "
var title = doc.getElementsByTagName("title")[0]
if(!!title){
alert("本来就存在title元素 "+ +doc.title)//测试document.title
}else{
alert("开始创建元素")
try{
html.innerHTML = "由innerHTML创建的title"
}catch(e){
var head = doc.createElement("head");
html.appendChild(head);
var title = doc.createElement("title");
head.appendChild(title);
title.appendChild(doc.createTextNode("由DOM API创建的title"));
var body = doc.createElement("body");
html.appendChild(body);
}
alert("doc.title = "+ doc.title)
}
}
if("innerHTML" in html){
alert("html.innerHTML = "+html.innerHTML)
}
if("outerHTML" in html){
alert("html.outerHTML = "+html.outerHTML)
}
alert("doc.body = "+doc.body)
var script = doc.createElement("script");
html.insertBefore(script,null);
script.appendChild(doc.createTextNode("alert('能调用javascript')"))//测试是否能动态解析脚本,注意这里是否弹出
alert("测试xpath = "+ doc.evaluate )
}catch(e){
alert("不支持createHTMLDocument方法")
}
}
</script>
</head>
<body>

</body>
</html>

运行代码

IE6IE8firefox3.6safari4.0.4opera10.50chrome5.0
能否创建文档××
doc.documentElement为HTML标签××
是否支持title属性×××
是否支持body属性×××××
元素节点是否支持innerHTML××
元素节点是否支持outerHTML×××
是否支持动态解析脚本××××××
是否支持xpath××
有几点需要注意的:

上述方法创建的是只有一个元素节点的HTML文档,由于是使用XHTML的命名空间,因此准确来说是XTHML文档。

XHTML的元素节点的tagName与nodeName是区分大小写的。

XHTML文档是没有实现body属性,opera的情况是特殊。

利用文档类型与createDocument创建文档

window.onload = function(){
try{
var doctype = document.implementation.createDocumentType('html',
'-//W3C//DTD HTML 4.01//EN', 'http://www.w3.org/TR/html4/strict.dtd');
var doc = document.implementation.createDocument(null, 'html', doctype);
var html = doc.documentElement
alert("doc.documentElement = "+html)        //测试是否存在HTML元素
alert("html.tagName = "+html.tagName)//注意大小写,HTML文档会把元素节点的tagName与nodeName大写化,按理应该会返回“HTML”
if("title" in doc){
doc.title = "跨文档调用 by 司徒正美 "
var title = doc.getElementsByTagName("title")[0]
if(!!title){
alert("本来就存在title元素 "+ +doc.title)//测试document.title
}else{
alert("开始创建元素")
try{
if("innerHTML" in html)
html.innerHTML = "<head><title>由innerHTML创建的title</title></head><body></body>"
}catch(e){
var head = doc.createElement("head");
html.appendChild(head);
var title = doc.createElement("title");
head.appendChild(title);
title.appendChild(doc.createTextNode("由DOM API创建的title"));
var body = doc.createElement("body");
html.appendChild(body);
}
alert("doc.title = "+ doc.title)
}
}
var head = document.getElementsByName("head")[0];
alert("head = "+head)
if("innerHTML" in html){
alert("html.innerHTML = "+html.innerHTML)
}
if("outerHTML" in html){
alert("html.outerHTML = "+html.outerHTML)
}
alert("doc.body = "+doc.body)
var script = doc.createElement("script");
html.insertBefore(script,null);
script.appendChild(doc.createTextNode("alert('能调用javascript')"))//测试是否能动态解析脚本,注意这里是否弹出
alert("测试xpath = "+ doc.evaluate )
}catch(e){
alert("不支持createHTMLDocument方法")
}
}


<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8" />
<meta content="IE=8" http-equiv="X-UA-Compatible"/>
<title>跨文档调用 by 司徒正美 </title>
<script type="text/javascript">window.onload = function(){ try{ var doctype = document.implementation.createDocumentType('html', '-//W3C//DTD HTML 4.01//EN', 'http://www.w3.org/TR/html4/strict.dtd'); var doc = document.implementation.createDocument(null, 'html', doctype); var html = doc.documentElement alert("doc.documentElement = "+html) //测试是否存在HTML元素 alert("html.tagName = "+html.tagName)//注意大小写,HTML文档会把元素节点的tagName与nodeName大写化,按理应该会返回“HTML” if("title" in doc){ doc.title = "跨文档调用 by 司徒正美 " var title = doc.getElementsByTagName("title")[0] if(!!title){ alert("本来就存在title元素 "+ +doc.title)//测试document.title }else{ alert("开始创建元素") try{ if("innerHTML" in html) html.innerHTML = "<head><title>由innerHTML创建的title</title></head><body></body>" }catch(e){ var head = doc.createElement("head"); html.appendChild(head); var title = doc.createElement("title"); head.appendChild(title); title.appendChild(doc.createTextNode("由DOM API创建的title")); var body = doc.createElement("body"); html.appendChild(body); } alert("doc.title = "+ doc.title) } } var head = document.getElementsByName("head")[0]; alert("head = "+head) if("innerHTML" in html){ alert("html.innerHTML = "+html.innerHTML) } if("outerHTML" in html){ alert("html.outerHTML = "+html.outerHTML) } alert("doc.body = "+doc.body) var script = doc.createElement("script"); html.insertBefore(script,null); script.appendChild(doc.createTextNode("alert('能调用javascript')"))//测试是否能动态解析脚本,注意这里是否弹出 alert("测试xpath = "+ doc.evaluate ) }catch(e){ alert("不支持createHTMLDocument方法") } }</script>
</head>
<body>

</body>
</html>

运行代码

IE6IE8firefox3.6safari4.0.4opera10.50chrome5.0
能否创建文档××
doc.documentElement为HTML标签××
是否支持title属性××××××
是否支持body属性××××××
元素节点是否支持innerHTML××××××
元素节点是否支持outerHTML××××××
是否支持动态解析脚本××××××
是否支持xpath××

利用document.cloneNode(true)创建文档

window.onload = function(){
try{
var doc = document.cloneNode(true);
var html = doc.documentElement
alert("doc.documentElement = "+html)        //测试是否存在HTML元素
alert("html.tagName = "+html.tagName);
alert("html.html = "+html.innerHTML)
if(doc.title){
alert("doc.title = "+doc.title);
}else{
doc.title = "司徒正美";
var title = doc.getElementsByTagName("title")[0];
alert("title.innerHTML = "+title.innerHTML);
}
alert("doc.body = "+doc.body)
var script = doc.createElement("script");
doc.body.appendChild(script);
if(!+"\v1"){
script.text = "alert('能调用javascript')"
}else{
script.appendChild(doc.createTextNode("alert('能调用javascript')"));
}
alert("测试xpath = "+ doc.evaluate )
}catch(e){
alert("不支持document.cloneNode(true)方法")
}
}


<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8" />
<meta content="IE=8" http-equiv="X-UA-Compatible"/>
<title>跨文档调用 by 司徒正美 </title>
<script type="text/javascript">window.onload = function(){ try{ var doc = document.cloneNode(true); var html = doc.documentElement alert("doc.documentElement = "+html) //测试是否存在HTML元素 alert("html.tagName = "+html.tagName); alert("html.html = "+html.innerHTML) if(doc.title){ alert("doc.title = "+doc.title); }else{ doc.title = "司徒正美"; var title = doc.getElementsByTagName("title")[0]; alert("title.innerHTML = "+title.innerHTML); } alert("doc.body = "+doc.body) var script = doc.createElement("script"); doc.body.appendChild(script); if(!+"\v1"){ script.text = "alert('能调用javascript')" }else{ script.appendChild(doc.createTextNode("alert('能调用javascript')")); } alert("测试xpath = "+ doc.evaluate ) }catch(e){ alert("不支持document.cloneNode(true)方法") } }</script>
</head>
<body>

</body>
</html>

运行代码

IE6IE8firefox3.6safari4.0.4opera10.50chrome5.0
能否创建文档×××
doc.documentElement为HTML标签×××
是否支持title属性×××
是否支持body属性×××
元素节点是否支持innerHTML×××
元素节点是否支持outerHTML××××
是否支持动态解析脚本××××
是否支持xpath×××××
注意:IE下,document.cloneNode(true)不能复制title元素的innerHTML!

到目前,我们发现w3c实现的那一堆方法实在太屎了,竟然不支持创建另一个javascript运行环境。因此想得到拥有javascript运行环境的文档对象,我们还是得靠iframe与ActiveXObject("htmlfile")!

/*
get another HTMLDocument which can run javascript!
Copyright 2010
Dual licensed under the MIT or GPL Version 2 licenses.
author "司徒正美(cheng)" http://www.cnblogs.com/rubylouvre/ */
(function(global) {
var expando = '__dom__' + (new Date - 0),
mode = (function(){
if (global.ActiveXObject && global.location && global.location.protocol !== 'file:') {
try {
return new ActiveXObject('htmlfile') && 1;
} catch (e) {}
}
return 2;
})(),
getSandboxDocument = (function(){
// 获取另一个全局对象
if (mode === 1){
return function() {
var htmlfile = new ActiveXObject('htmlfile');
htmlfile.open();
htmlfile.write('<script>this.author ="司徒正美";document.global = this;<\/script>');
htmlfile.close();
return htmlfile.global;
};
}else  if (mode === 2){
return function() {
var idoc, iframe, result,
doc = global.document,
parentNode = doc.body || doc.documentElement,
name  = '__iframe__' + expando  ;
try {
iframe = doc.createElement('<iframe name="' + name + '">');
} catch (e) {
(iframe = doc.createElement('iframe')).name = name;
}
iframe.style.display = 'none';
parentNode.insertBefore(iframe, parentNode.firstChild);
try {
(idoc = global.frames[name].document).open();
var str = '<html><head><title>iframe</title><script>this.author ="司徒正美";parent.' +
expando + ' = this;<\/script></head><body></body></html>'
idoc.write(str);
idoc.close();
} catch (e) {
//opera9不支持在document.documentElement中插入iframe
throw new Error('Creating a sandbox by iframe is fail.');
}
result = global[expando];
try{
delete global[expando]
}catch(e){//IE下失败!
global[expando] = undefined
}
return result;
}
}else{
return function() {
throw new Error('Creating a sandbox is fail.');
};
}
})();
global.getSandboxDocument = getSandboxDocument
})(this);


<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8" />
<meta content="IE=8" http-equiv="X-UA-Compatible"/>
<title>跨文档调用 by 司徒正美 </title>
<script type="text/javascript">
(function(global) {
var expando = '__dom__' + (new Date - 0),
mode = (function(){
if (global.ActiveXObject && global.location && global.location.protocol !== 'file:') {
try {
return new ActiveXObject('htmlfile') && 1;
} catch (e) {}
}
return 2;
})(),
getSandboxDocument = (function(){
// 获取另一个全局对象
if (mode === 1){
return function() {
var htmlfile = new ActiveXObject('htmlfile');
htmlfile.open();
htmlfile.write('<script>this.author ="司徒正美";document.global = this;<\/script>');
htmlfile.close();
return htmlfile.global;
};
}else if (mode === 2){
return function() {
var idoc, iframe, result,
doc = global.document,
parentNode = doc.body || doc.documentElement,
name = '__iframe__' + expando ;
try {
iframe = doc.createElement('<iframe name="' + name + '">');
} catch (e) {
(iframe = doc.createElement('iframe')).name = name;
}
iframe.style.display = 'none';
parentNode.insertBefore(iframe, parentNode.firstChild);
try {
(idoc = global.frames[name].document).open();
var str = '<html><head><title>iframe</title><script>this.author ="司徒正美";parent.' +
expando + ' = this;<\/script></head><body></body></html>'
idoc.write(str);
idoc.close();
} catch (e) {
//opera9不支持在document.documentElement中插入iframe
throw new Error('Creating a sandbox by iframe is fail.');
}
result = global[expando];
try{
delete global[expando]
}catch(e){//IE下失败!
global[expando] = undefined
}
return result;
}
}else{
return function() {
throw new Error('Creating a sandbox is fail.');
};
}
})();
global.getSandboxDocument = getSandboxDocument
})(this);
window.onload = function(){
var sandbox = getSandboxDocument(),
doc = sandbox.document,
html = doc.documentElement;
alert("doc.documentElement = "+html)
alert("html.tagName = "+html.tagName);
alert("sandbox.author = "+sandbox.author);//测试是否为沙箱全局对象
alert("window.author = "+ this.author);
var body = doc.body
alert("doc.body = "+doc.body)
if("title" in doc){
alert("doc.title = "+ doc.title)
}else{
var title = doc.getElementsByTagName("title")[0]
title.innerHTML ="iframe title";
alert("doc.title = "+ doc.title)
}
if("innerHTML" in html){
alert("html.innerHTML = "+html.innerHTML)
}
if("outerHTML" in html){
alert("html.outerHTML = "+html.outerHTML)
}
var script = doc.createElement("script");
html.insertBefore(script,null);
if(!+"\v1"){
script.text = "alert('能调用javascript')";
}else{
script.appendChild(doc.createTextNode("alert('能调用javascript')"))//测试是否能动态解析脚本,注意这里是否弹出
}
alert("测试xpath = "+ doc.evaluate )
}
</script>
</head>
<body>

</body>
</html>

运行代码

IE6IE8firefox3.6safari4.0.4opera10.50chrome5.0
能否创建文档
doc.documentElement为HTML标签
是否支持title属性
是否支持body属性
元素节点是否支持innerHTML
元素节点是否支持outerHTML×
是否支持动态解析脚本
是否支持xpath××
这种技术我算毫无保留地公开出来了,如果有谁知道怎样利用它创建一个不污染本地数组的数组类,也请不吝赐教!

2ch
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: