DOM扩展-HTML5、专有扩展
HTML5
与类相关的扩充
1、getElementsByClassName()方法
改方法接受一个参数,即一个包含一或多个类名的字符串,返回带有指定类的所有元素的NodeList。传入多个类型时,先后顺序不重要。
1 //取得所有类中包含"username"和"current"的元素,类名的先后顺序不重要 2 var allCurrentUsername = document.getElementsByClassName('username current'); 3 //取得ID为'myDiv'的元素中都带有类名"selected"的所有元素 4 var selected = document.getElementById('myDiv').getElementsByClassName('selected');
调用这个方法时,只有位于调用元素子树中的元素才会返回。
2、classList属性
在操作类名时,需要通过className属性添加,删除和替换类名。因为className中是一个字符串,所以即使只修改字符串的一部分,也必须每次都设置整个字符串。HTML5新增加了一种操作类名的方式,那就是为所有元素都添加classList属性。这个classList属性是新集合类型DOMTiokenList的实例。与其他DOM集合类似,DOMTokenList有一个表示自己包含多少元素的length属性,而要取得每个元素可以使用item()方法,也可以使用方括号语法。此外,这个新类型还定义如下方法:
//Alt + 41406、Alt + 41407
【1】add(value):将给定的字符串添加到列表中,如果以存在就不在添加;
【2】contains(value):表示列表中是否存在给定的值,如果存在就返回true,反之返回false;
【3】remove(value):从列表中删除给定的字符串;
【4】toggle(value):如果列表中存在给定的值,删除它,如果列表中没有给定的值,添加它;
1 //添加"currrent"类 2 div.classList.add('current'); 3 //切换"user"类 4 div.classList.toggle('user');
焦点管理
document.activeElement属性,这个属性始终会引用DOM中当前获得了焦点的元素。元素获得焦点的方法通常有页面加载,用户输入和在代码中调用focus()方法。
1 var button = document.getElementById('myButton'); 2 button.focus(); 3 console.log(document.activeElement === button); //true
默认情况下,文档刚刚加载完成时,document.activeElement的值为document.body,当文档加载时document.activeElement的值为null;
document.hasFocus()方法,这个方法用于确定文档是否获得了焦点;
1 var button = document.getElementById('myButton'); 2 button.focus(); 3 console.log(documet.hasFocus()); //true
HTMLDocument的变化
HTML5扩展了HTMLDocument,增加了新的功能
1、readyState属性
它有两个可能的值
【1】loading,正在加载文档。
【2】complete,已经加载完文档。
使用document.readyState的最恰当方式,就是通过它来实现一个指示文档已经加载完成的指示器
2、兼容模式
在标准模式下,document.compatMode的值等于"CSS1Compat",而在混杂模式下,document.compatMode的值等于"BackCompat"。
3、head属性
作为对document.body引用文档的<body>元素的补充,HTML5新增了document.head属性,引用文档的<head>元素,要引用文档的<head>元素,可以结合使用这个属性和另一种后备方法。
1 var head = document.head || document.getElementsByTagName('head')[0];
字符集属性
HTML5新增了几个与文档字符集有关的属性,其中,charset属性表示文档中实际使用的字符集,也可以用来指定新字符集。默认情况下,这个属性的值为"UTF-16";
1 console.log(document.charset); //"UTF-16" 2 document.charset = "UTF-8";
另一个属性是defaultCharset,表示根据默认浏览器及操作系统的设置,当前文档默认的字符集应该是什么。如果文档没有默认的字符集,那charset和defaultCharset属性的值可能会不一样,例如:
1 if(document.charset != document.defaultCharset){ 2 console.log("Custom character set being used."); 3 }
自定义数据属性
HTML5规定可以为元素添加非标准的属性,但要添加前缀data-,目的是为元素提供与渲染无关的信息,或者提供语义信息。这些属性可以任意添加、随便命名,只要以data-开头即可
1 <div id="myDiv" data-appid="12345" data-myname="Nicholas"></div>
添加了自定义属性后,可以通过dataset属性来访问自定义属性的值,只不过属性名没有data-前缀
1 var div = document.getElementById('myDiv'); 2 3 //取得自定义属性的值 4 var appid = div.dataset.appid; 5 var myName = div.dataset.myName; 6 7 //设置值 8 div.dataset.appid = 23456; 9 div.dataset.myName = "Michael";
如果需要给元素添加一些不可见的数据以便进行其他处理,那就要用到自定义数据属性
插入标记
在读模式下,innerHTML属性会返回与调用元素的所有子节点(包括元素、注释和文本节点)对应的HTML标记;在写模式下,innerHTML会根据指定的值创建新的DOM树,然后用这个DOM树完全替换调用元素原先的所有子节点;下面是一个例子
1 <div> 2 <p>This is a <strong>paragraph</strong>with a list following it.</p> 3 <ul> 4 <li>Item 1</li> 5 <li>Item 2</li> 6 <li>Item 3</li> 7 </ul> 8 </div>
对于上面的<div>来说,他的innerHTMl属性会返回如下字符串。
1 <p>This is a <strong>paragraph</strong>with a list following it.</p> 2 <ul> 3 <li>Item 1</li> 4 <li>Item 2</li> 5 <li>Item 3</li> 6 </ul>
不要指望所有浏览器返回的innerHTML值完全相同,使用innerHTML属性也有一些限制。比如,在大多数浏览器中,通过innerHTML插入<script>元素并不会执行其中的脚本。但IE8除外,但是也有要求:
【1】必须为<script>元素指定defer属性
【2】<script>元素必须位于"有作用域的元素"之后(<script>元素被认为是"无作用域的元素",也就是在页面中看不到,与<style>或注释类似)
下面的代码达不到目的:
1 div.innerHTML = "<script defer>alert('hi')<\/script>";
要想达到目的就要在前面添加一个"有作用域的元素",可以使一个文本节点,也可以是一个没有结束标签的元素例如<input>,下面的代码都能执行;
1 div.innerHTML = "_<script defer>alert('hi')<\/script>"; 2 div.innerHTML = "<div> </div><script defer>alert('hi')<\/script>"; 3 div.innerHTML = "<input111<script defer>alert('hi')<\/script>";
2、outerHTML属性
在读模式下,outerHTML返回调用它的元素及所有子节点的HTML标签。在写模式下,outerHTML会根据指定的HTML字符串创建新的DOM子树,然后用这个DOM子树完全替换调用元素
1 <div> 2 <p>This is a <strong>paragraph</strong>with a list following it.</p> 3 <ul> 4 <li>Item 1</li> 5 <li>Item 2</li> 6 <li>Item 3</li> 7 </ul> 8 </div>
如果在div上调用outerHTML,会返回上述所有代码,包括div;不过,由于浏览器解析和解释HTML标记的不同,结果也可能有所不同;(这里的不同于使用innerHTML属性时存在的差异是一样的)
1 div.outerHTML = "<p>This is a paragraph.</p>";
这行代码完成的操作与下列代码是一样的
1 var p = document.createElement('p'); 2 p.appendChild(documetn.createTextNode("This is a paragraph")); 3 div.parentNode.replaceChild(p,div);
结果,就是新创建的<p>元素会取代DOM树中的<div>元素
3、insertAdjacentHTML()方法
它接受两个参数:插入位置和要插入的HTML文本;第一个参数必须是下列值之一:
beforebegin:在当前元素前插入一个同辈元素;
afterbegin:在当前元素之下插入一个新的子元素或在第一个子元素之前再插入新的子元素
beforeend:在当前元素之下插入一个新的子元素或在最后一个子元素之前再插入新的子元素
afterend:在当前元素之后插入一个同辈元素;
1 //作为第一个子元素插入 2 element.insertAdjacentHTML("afterbegin","<p>Hello world!</p>");
scrollIntoView()方法
scrollIntoView()方法可以再所有HTML元素上调用,通过滚动浏览器窗口或某个容器元素,调用元素就可以出现在视口中。如果给这个方法传入true或者不传入任何参数,那么窗口滚动之后会让调用元素的顶部和视口顶部尽可能齐平。如果传入false作为参数,调用元素会尽可能全部出现在视口中
1 //让元素可见 2 document.forms[0].scrollIntoView();
专有扩展
children属性
children属性是HTMLCollection的实例,只包含元素中同样还是元素的子节点。除此之外children属性与childNodes没有什么区别。
contains()方法
这个方法接受一个参数,即要检测的后代节点。如果被检测的节点是后代节点,该方法返回true;否则返回false。调用contains()方法的应该是祖先节点。
1 console.log(document.documentElement.contains(document.body)); //true
使用DOM Level 3 compareDocumentPosition()也能够确定节点间的关系,它会返回一个表示该关系的位掩码
1:无关
2:居前
4:居后
8:包含
16:被包含
插入文本
1、innerText属性
innerText读取值时,它会按照由浅入深的顺序,将子文档树中的所有文本拼接起来。在通过innerText写入值时,结果会删除元素的所有子节点,插入包含相应文本值的文本节点,如下:
1 <div> 2 <p>This is a <strong>paragraph</strong>with a list following it.</p> 3 <ul> 4 <li>Item 1</li> 5 <li>Item 2</li> 6 <li>Item 3</li> 7 </ul> 8 </div>
对于div而言,它的innerText属性会返回下列字符串
This is a paragraph
Item 1
Item 2
Item 3
不同的浏览器处理空白符的方式不同,可能输出的文本可能不会包含原始HTML代码中的缩进
1 div.innerText = "Hello world";
执行这段代码后,页面就会变成如下所示:
1 <div id="content">Hello world!</div>
注意:Firefox虽然不支持innerText,但支持作用类似的textContent属性
2、outerText属性
除了作用范围扩大到了包含调用它的节点之外,outerText与innerText基本上没有多大区别。在读取文本值时,outerText与innerText的结果完全一样。但在写模式下,outerText就完全不同了;outerText不只是替换调用它的元素的子节点,而是会替换整个元素。