JS高级程序设计——第11章 DOM扩展 选择符API和元素遍历

DOM扩展 11.1 选择符API和元素遍历

一、扩展的方向

  • 对 DOM 的两个主要的扩展Selectors API(选择符 API)HTML5。此外,还有一个不那么引人瞩目的 Element Traversal (元素遍历)规范,为 DOM 添加了一些属性。
  • 虽然前述两个主要规范(特别是 HTML5)已经涵盖了大量的 DOM 扩展,但专有扩展依然存在。

二、选择符API

  1. jQuery(www.jquery.com)的核心就是通过 CSS 选择符查询 DOM 文档取得元素的引用,从而 抛开了getElementById()和getElementsByTagName()。
  2. Selectors API(www.w3.org/TR/selectors-api/)是由 W3C 发起制定的一个标准,致力于让浏览器原生支持 CSS 查询。
  3. Selectors API Level 1 的核心是两个方法:querySelector()querySelectorAll()。在兼容的浏览器中,可以通过 Document 及 Element 类型的实例调用它们。目前已完全支持 Selectors API Level 1 的浏览器有 IE 8+、Firefox 3.5+、Safari 3.1+、Chrome 和 Opera 10+。
  4. querySelector()方法:querySelector()方法接收一个 CSS 选择符,返回与该模式匹配的第一个元素,如果没有找到匹配的元素,返回 null。请看下面的例子。
//取得 body 元素
var body = document.querySelector("body");
//取得 ID 为"myDiv"的元素
var myDiv = document.querySelector("#myDiv");
//取得类为"selected"的第一个元素
var selected = document.querySelector(".selected");
//取得类为"button"的第一个图像元素
var img = document.body.querySelector("img.button");

通过 Document 类型调用 querySelector()方法时,会在文档元素的范围内查找匹配的元素。而通过 Element 类型调用 querySelector()方法时,只会在该元素后代元素的范围内查找匹配的元素。

  1. querySelectorAll()方法:querySelectorAll()方法接收的参数与 querySelector()方法一样,都是一个 CSS 选择符,但返回的是所有匹配的元素而不仅仅是一个元素。这个方法返回的是一个 NodeList 的实例
  • 具体来说,返回的值实际上是带有所有属性和方法的 NodeList而其底层实现则类似于一组元素的快照,而非不断对文档进行搜索的动态查询。这样实现可以避免使用 NodeList 对象通常会引起的大 多数性能问题。
  • 只要传给 querySelectorAll()方法的 CSS 选择符有效,该方法都会返回一个 NodeList 对象, 而不管找到多少匹配的元素。如果没有找到匹配的元素,NodeList 就是空的。
  • 与 querySelector() 类 似 , 能 够 调 用 querySelectorAll() 方 法 的 类 型 包 括 Document 、 DocumentFragment 和 Element。下面是几个例子。
//取得某<div>中的所有<em>元素(类似于 getElementsByTagName("em"))
var ems = document.getElementById("myDiv").querySelectorAll("em");
//取得类为"selected"的所有元素
var selecteds = document.querySelectorAll(".selected");
//取得所有<p>元素中的所有<strong>元素
var strongs = document.querySelectorAll("p strong");
  • 取得返回的 NodeList 中的每一个元素,可以使用 item()方法,也可以使用方括号语法,比如:
var i, len, strong;
for (i=0, len=strongs.length; i < len; i++){
	strong = strongs[i]; //或者 strongs.item(i)
    strong.className = "important";
}
  1. matchesSelector()方法:Selectors API Level 2规范为Element类型新增了一个方法matchesSelector()。这个方法接收一个参数,即 CSS 选择符,如果调用元素与该选择符匹配,返回 true;否则,返回 false。看例子。
 if (document.body.matchesSelector("body.page1")){
        //true
}
  • 在取得某个元素引用的情况下,使用这个方法能够方便地检测它是否会被 querySelector()或 querySelectorAll()方法返回。【当用括号内css选择符搜索时,调用元素会被返回】
  • 截至 2011 年年中,还没有浏览器支持 matchesSelector()方法;不过,也有一些实验性的实现。 IE 9+通过 msMatchesSelector()支持该方法,Firefox 3.6+通过 mozMatchesSelector()支持该方法, Safari 5+和 Chrome 通过 webkitMatchesSelector()支持该方法。因此,如果你想使用这个方法,最好是编写一个包装函数。
function matchesSelector(element, selector){
        if (element.matchesSelector){
            return element.matchesSelector(selector);
        } else if (element.msMatchesSelector){
            return element.msMatchesSelector(selector);
        } else if (element.mozMatchesSelector){
            return element.mozMatchesSelector(selector);
        } else if (element.webkitMatchesSelector){
            return element.webkitMatchesSelector(selector);
        } else {
            throw new Error("Not supported.");
        }
}
if (matchesSelector(document.body, "body.page1")){ //执行操作
}

三、元素遍历

  1. 对于元素间的空格IE9 及之前版本不会返回文本节点,而其他所有浏览器都会返回文本节点。这样, 就导致了在使用 childNodes 和 firstChild 等属性时的行为不一致。为了弥补这一差异,而同时又保持 DOM 规范不变,Element Traversal 规范(www.w3.org/TR/ElementTraversal/)新定义了一组属性。
  2. Element Traversal API 为 DOM 元素添加了以下 5 个属性
    childElementCount返回子元素(不包括文本节点和注释)的个数
    firstElementChild:指向第一个子元素;firstChild 的元素版。
    lastElementChild:指向最后一个子元素;lastChild 的元素版。
    previousElementSibling:指向前一个同辈元素;previousSibling 的元素版。
    nextElementSibling:指向后一个同辈元素;nextSibling 的元素版。
    支持的浏览器为 DOM 元素添加了这些属性,利用这些元素不必担心空白文本节点,从而可以更方便地查找 DOM 元素了。
  • 下面来看一个例子。过去,要跨浏览器遍历某元素的所有子元素,需要像下面这样写代码。
var i, 
	len,
    child = element.firstChild;
while(child != element.lastChild){
     if (child.nodeType == 1){ //检查是不是元素
       processChild(child);
	 }
    child = child.nextSibling;
}
  • 而使用 Element Traversal 新增的元素,代码会更简洁。
var i,
 	len,
    child = element.firstElementChild;
while(child != element.lastElementChild){
	processChild(child); //已知其是元素
    child = child.nextElementSibling;
}
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值