在我们通过js对dom元素进行一些操作时,就要用到DHTML所提供的操作方法;而这些操作方法在各个浏览器中的表现不是那么一致,所以就需要用到兼容写法来让我们的代码在IE,FireFox,Chrome,Safari等浏览器中都能正常运行。
我总结一些dom操作的兼容写法帮助大家更好的来解决烦人的兼容性问题。
一、Js创建元素
1,创建dom元素var ele=docment.createElement("");
这行代码,只在IE8及以下浏览器可以运行,其他浏览器报错。var ele=document.createElement("input");
这行代码是W3C的标准创建方式,在各个浏览器下面都可以运行,为兼容写法。但是如果我们想要实现jquery那种方便的元素创建方式呢?jquery源码中是使用fragment进行创建,通过正则的分析,创建元素,之后再添加上字符串中的属性等等操作实现的。
我们可以用一种简单的实现方式,那就是创建一个div,然后把要创建的元素字符串通过div的innerHTML传入,则浏览器会帮我们创建这个元素,这个操作完成后,我们可以通过div.children获取其子元素的得到我们要创建的元素,得到元素后最好把div的innerHTML清空,以便释放内存。代码如下:var div;
function createE(str){
if(!div){
div=document.createElement("div");
}
div.innerHTML=str;
var temp=div.children[0];//这里虽然所有浏览器都兼容,但是IE8以下包含注释节点。
div.innerHTML="";
return temp;
}
2,创建文本节点var text=document.createTextNode("
forth");用创建文本节点的方式可以免除html标签的转义操作。
3,创建fragement,var fragment = document.createDocumentFragment();
fragment是文档片段,可以把一系列DOM操作中fragment中进行,最后添加到body中以减少浏览器回流(layout)和重绘(reflow)的次数,对页面有一定优化作用。
4,创建注释元素,var cm=document.createComment("autor mooshine");
创建注释的用途不大,但是可以做一些其他作用,angular中对其就有应用,有兴趣的可以进一步研究。
5,创建属性createAttribute, value和nodeValue都可用var attr=document.createAttribute("id");
attr.nodeValue="mooshine";
var nattr=div.getAttributeNode("name");
var val=nattr.value;
var val=nattr.nodeValue;//这两个都能得到属性值
此方法是创建attribute对象,一般作为setAttributeNode的参数使用,其他的用途暂不清楚。
二、增加,删除元素。
增加元素的方法有appendChild,inerstBefore可用(其他的一些方法只有IE支持,兼容写法不建议),删除元素的方法有removeChild,removeNode(此方法虽然灵活性高,但只兼容IE)div.appendChild(ele);//追加添加一个元素
div.insetBefore(ele,div.children[0]);//插入一个元素。
div.removeChild(ele);//删除一个元素。
三、替换元素
替换元素的兼容方法只有一个replaceChild,其他的replaceNode,swapNode(替换,交换元素只有IE支持)var nele=document.createElement("input");
nele.type='text';
div.replaceChild(nele,password);
四、获取元素属性,修改元素属性,移除元素属性
元素属性的操作,对于原生属性可以通过.操作符操作,自定义属性可以通过,getAttribute,getAttributeNode,setAttribute,setAttributeNode操作,(据jQuery说,在IE6,7下setAttribute,getAttribute有问题,所以采用setAttributeNode,getAttributeNode)var div=document.createElement("div");
var attr=document.createAttribute("id");
attr.nodeValue="mooshine";
div.setAttributeNode(attr);
div.name="mymooshine";
div.setAttribute("class","seril");
div.setAttribute("className","seril");//兼容IE6,7实现;你也可以做一些判断来区分浏览器
var id=div.getAttributeNode("id").value;
var cls=div.getAttribute("class")||div.getAttribute("className");
div.removeAttribute("class");
var cnames=div.className;
div.className="class1 class2";//className的操作是所有浏览器都兼容的,而且方便
var id=div.getAttributeNode("id");
div.removeAttributeNode(id);
var name=div.name;//点操作属性,只用于原有属性。
操作元素属性的方法有很多用,且兼容性尚可,除了一些小问题:
1、IE6,7的className与其他浏览器不同,但是可以通过点操作className来实现所有浏览器的兼容。
2、style属性操作用setAttribute,getAttribute在火狐下有问题,我们要采用 style.cssText进行操作。3、input的type属性在IE8-是不能修改的,只能通过创建替换。
五、元素克隆clone
var div=document.getElementById("demo");
var clone=div.cloneNode(true);//深度拷贝
var clone2=div.cloneNode(false);//浅拷贝
元素克隆有一个参数,为true时连带子元素一起拷贝;为false时只拷贝元素本身。
六、getComputeStyle和currentStyle,以及defaultView。
getComputeStyle和currentStyle方法是得到浏览器中一个元素最终的属性值,不只是你设置上去的属性,还包括从父辈继承的属性,默认的属性等,比如你没有设置一个div的宽度,可以用这两个方法得到div的最终宽度,这个值是浏览器计算得出最后应用到元素上的。
var computed=document.defaultView.getComputedStyle( elem, null );//FireFox写法,其中的defaultView可以去掉,但是据说去掉的话iframe会有问题。
var computed=document.getComputedStyle( elem, null );
var currented=elem.currentStyle;//IE下获取最终样式的方法。
上面得到的是属性集合
var height=computed.getPropertyValue("height");
var height=currented["height"];
getComputedStyle的第二个参数是伪类,如果不需要伪类就设置为null,早期的firefox中第二个参数是必填值,现在已经不是必填的了,但是为了兼容性还是填上null为好。
既然这个兼容方法能获取元素最终应用的样式,那么我们是不是可以任意获取了呢,其实不然。这个兼容方法中还有很多细节要兼容,比如元素的height如果没有设置,其他浏览器返回的是具体数值,IE返回“auto”,而且还有单位的影响,IE的z-Index返回的是整数类型等差异。
这个涉及的东西比较多,我将专门用一篇文章来基于jquery的源码讲解其中的兼容性问题。
好了,就写到这里,感觉前端就是个无底洞,自己要学的东西还是很多很多的。