DOM 變化
-
如何確認(rèn)瀏覽器是否支持 DOM 2 和 DOM 3 新增的模塊:
var supportsDOM2Core = document.implementation.hasFeature('Core', '2.0') var supportsDOM3Core = document.implementation.hasFeature('Core', '3.0') var supportsDOM2HTML = document.implementation.hasFeature('HTML', '2.0') var supportsDOM2Views = document.implementation.hasFeature('Views', '2.0') var supportsDOM2XML = document.implementation.hasFeature('XML', '2.0')
-
針對(duì) XML 命名空間的變化
-
混合命名空間
<html xmlns="http://www.w3.org/1999/xhtml"> <head> <title> Example XHTML page </title> </head> <body> <svg xmlns="http://www/w3.org/2000/svg" version="1.1" viewBox="0 0 100 100" style="width: 100%; height: 100%"> <rect x="0" y="0" width="100" height="100" style="fill: red" /> </svg> </body> </html>
-
在 DOM 2 中,Node 類型包含下列特定于命名空間的屬性:
-
localName
:不帶命名空間前綴的節(jié)點(diǎn)名稱 -
namespaceURI
:命名空間 URI 或者(在未指定的情況下)null
-
prefix
:命名空間前綴或者(在未指定的情況下)null
-
-
DOM 3 引入了下列與命名空間有關(guān)的方法:
-
isDefaultNamespace(namespaceURI)
:在指定的namespaceURI
是當(dāng)前節(jié)點(diǎn)的默認(rèn)命名空間時(shí)返回true
-
lookupNamespaceURI(prefix)
:返回給定prefix
的命名空間。 -
lookupPrefix(namespaceURI)
:返回給定namespace
的前綴。
-
-
DOM 2 的 Document 也發(fā)生了變化基括,包含了下列與命名空間有關(guān)的方法:
-
createElementNS(namespaceURI, tagName)
:使用給定的tagName
創(chuàng)建一個(gè)屬于命名空間namespace
的新元素乳蓄。 -
createAttributeNS(namespaceURI, attributeName)
:使用給定的attributeName
創(chuàng)建一個(gè)屬于命名空間namespaceURI
的新特性恬吕。 -
getElementsByTagNameNS(namespaceURI, tagName)
:返回屬于命名空間namespaceURI
的tagName
元素的NodeList
故黑。
-
-
DOM 2 也為 Element 新增了一些方法:
-
getAttributeNS(namespaceURI, localName)
:取得屬于命名空間namespaceURI
且名為localName
的特性。 -
getAttributeNodeNS(namespaceURI, localName)
:取得屬于命名空間namespaceURI
且名為localName
的特性節(jié)點(diǎn)颁独。 -
getElementsByTagNameNS(namespaceURI, tagName)
:返回屬于命名空間namespaceURI
的tagName
元素的NodeList
。 -
hasAttributeNS(namespaceURI, localName)
:確定當(dāng)前元素是否有一個(gè)名為localName
的特性伪冰,而且該特性的命名空間是namespaceURI
誓酒。 -
removeAttributeNS(namespaceURI, localName)
:刪除屬于命名空間namespaceURI
且名為localName
的特性。 -
setAttributeNS(namespaceURI, qualifiedName, value)
:設(shè)置屬于命名空間namespaceURI
且名為qualifiedName
的特性值為value
贮聂。 -
setAttributeNodeNS(attNode)
:設(shè)置屬于命名空間namespaceURI
的特性節(jié)點(diǎn)靠柑。
-
-
NamedNodeMap 類型也新增了下列與命名空間有關(guān)的方法。由于特性是通過(guò) NamedNodeMap 表示的吓懈,因此這些方法多數(shù)情況下只針對(duì)特性使用:
-
getNamedItemNS(namespaceURI, localName)
:取得屬于命名空間namespaceURI
且名為localName
的項(xiàng)歼冰。 -
removeNamedItemNS(namespaceURI, localName)
:移除屬于命名空間namespaceURI
且名為localName
的項(xiàng)。 -
setNamedItemNS(node)
?:添加node
耻警。這個(gè)節(jié)點(diǎn)已經(jīng)事先指定了命名空間信息隔嫡。
-
-
-
其他方面的變化
- DocumentType 新增了三個(gè)屬性:
-
publicId
:文檔類型聲明中的信息段之一(- //W3C//DTD HTML 4.0.1//EN
) -
systemId
:文檔類型聲明中的信息段之一(http://www.w3.org/TR/html4/strict.dtd
) -
internalSubset
:訪問(wèn)包含在文檔類型聲明中的額外定義。
-
- Document 類型的變化:
-
新增
importNode()
用來(lái)從一個(gè)文檔中獲取一個(gè)節(jié)點(diǎn)甘穿,然后將其導(dǎo)入到另一個(gè)文檔中腮恩,使其成為這個(gè)文檔結(jié)構(gòu)的一部分。- 每個(gè)節(jié)點(diǎn)都有一個(gè)
ownerDocument
屬性扒磁,表示所屬的文檔庆揪。如果調(diào)用appendChild()
時(shí)傳入的節(jié)點(diǎn)屬于不同的文檔,會(huì)導(dǎo)致錯(cuò)誤妨托。但是在調(diào)用importNode()
的時(shí)候回返回一個(gè)歸當(dāng)前文檔所有的新的節(jié)點(diǎn)缸榛。
- 每個(gè)節(jié)點(diǎn)都有一個(gè)
-
新增
defaultView
屬性,保存一個(gè)指針兰伤,指向擁有給定文檔的窗口(或框架)内颗。IE 不支持這個(gè)屬性,但有一個(gè)等價(jià)的屬性名叫parentWindow
敦腔。因此均澳,要確定文檔窗口,可以使用以下代碼:var parentWindow = document.defaultView || document.parentWindow
-
DOM 2 Core 為
document.implementation
對(duì)象規(guī)定了兩個(gè)新方法:-
createDocumentType()
:創(chuàng)建一個(gè)新的 DocumentType 節(jié)點(diǎn)。接收三個(gè)參數(shù):文檔類型名稱找前、publicId
糟袁、systemId
。這個(gè)方法只在創(chuàng)建新文檔時(shí)有用躺盛。var doctype = document.implementation.createDocumentType("html", "-//W3C//DTD HTML 4.01//EN", "http://www.w3.org/TR/html4/strict.dtd")
-
createDocument()
:創(chuàng)建新文檔项戴。接收三個(gè)參數(shù):接受文檔中元素的namespaceURI
、文檔元素的標(biāo)簽名槽惫、新文檔的文檔類型周叮。var doc = document.implementation.createDocument("http://www.w3.org/1999/xhtml", "html", doctype)
-
DOM 2 HTML 為
document.implementation
新增了一個(gè)方法:createHTMLDocument()
。這個(gè)方法的用途是創(chuàng)建一個(gè)完整的 HTML 文檔界斜,包括html, head, title, body
元素仿耽。它只接受一個(gè)參數(shù),即新創(chuàng)建的文檔的標(biāo)題(放在title
里)各薇,返回新的 HTML 文檔项贺。只有 Opera 和 Safari 支持這個(gè)方法。
-
- Node 類型的變化
-
添加了
isSupported()
方法:用于確定當(dāng)前節(jié)點(diǎn)具有什么能力得糜。接收兩個(gè)參數(shù):特性名敬扛、特性版本號(hào)。如果瀏覽器實(shí)現(xiàn)了相應(yīng)特性朝抖,而且能夠基于給定節(jié)點(diǎn)執(zhí)行該特性啥箭,就返回true
。document.body.isSupported("HTML", "2.0")
-
DOM 3 引入了兩個(gè)輔助比較節(jié)點(diǎn)的方法:
-
isSameNode()
:接收一個(gè)節(jié)點(diǎn)參數(shù)治宣,并在傳入節(jié)點(diǎn)與引用的節(jié)點(diǎn)相同(即同一個(gè)對(duì)象)時(shí)返回true
急侥。 -
isEqualNode()
:接收一個(gè)節(jié)點(diǎn)參數(shù),并在傳入節(jié)點(diǎn)與引用的節(jié)點(diǎn)相等(即類型相同)時(shí)返回true
。
-
-
DOM 3 針對(duì)為 DOM 節(jié)點(diǎn)添加額外數(shù)據(jù)引入了新方法:
-
setUserData()
:將數(shù)據(jù)指定給節(jié)點(diǎn)侮邀。接收三個(gè)參數(shù):要設(shè)置的鍵坏怪、實(shí)際的數(shù)據(jù)(可以是任何數(shù)據(jù)類型)、處理函數(shù)绊茧。 -
getUserData()
:接收相同的三個(gè)參數(shù)铝宵,獲取數(shù)據(jù)。 - 傳入
setUserData()
中的處理函數(shù)會(huì)在帶有數(shù)據(jù)的節(jié)點(diǎn)被復(fù)制华畏、刪除鹏秋、重命名或引入一個(gè)文檔時(shí)調(diào)用。處理函數(shù)接收五個(gè)參數(shù):表示操作類型的數(shù)值(1 - 復(fù)制亡笑,2 - 導(dǎo)入侣夷,3 - 刪除,4 - 重命名)仑乌,數(shù)據(jù)鍵百拓、數(shù)據(jù)值琴锭、源節(jié)點(diǎn)和目標(biāo)節(jié)點(diǎn)。刪除時(shí)源節(jié)點(diǎn)是null
衙传;除復(fù)制外目標(biāo)節(jié)點(diǎn)是null
决帖。
-
-
- 框架的變化
- HTMLFrameElement 和 HTMLIFrameElement 在 DOM 2 中都有了一個(gè)新屬性:
contentDocument
。它包含一個(gè)指針蓖捶,指向表示框架內(nèi)容的文檔對(duì)象古瓤。在此之前,無(wú)法直接通過(guò)元素取得這個(gè)文檔對(duì)象(只能使用 frames 集合)腺阳。-
contentDocument
屬性是 Document 類型的實(shí)例,因此可以像使用其他 HTML 文檔一樣使用它穿香,包括所有屬性和方法亭引。IE 8 之前不支持這個(gè)屬性,但是支持一個(gè)名叫contentWindow
的屬性皮获。var iframe = document.getElementById('myIframe') var iframeDoc = iframe.contentDocument || iframe.contentWindow.document
-
- HTMLFrameElement 和 HTMLIFrameElement 在 DOM 2 中都有了一個(gè)新屬性:
- DocumentType 新增了三個(gè)屬性:
樣式
-
確定瀏覽器是否支持 DOM 2 級(jí)定義的 CSS 能力:
var supportsDOM2CSS = document.implementation.hasFeature('CSS', '2.0') var supportsDOM2CSS2 = document.implementation.hasFeature('CSS2', '2.0')
-
訪問(wèn)元素的樣式:
- 任何支持
style
特性的 HTML 元素在 JavaScript 中都有一個(gè)對(duì)應(yīng)的style
屬性焙蚓。這個(gè)style
對(duì)象是 CSSStyleDeclaration 的實(shí)例,包含著通過(guò) HTML 的style
特性指定的所有樣式信息洒宝,但不包含與外部樣式表或嵌入樣式表經(jīng)層疊而來(lái)的樣式购公。在style
特性中指定的任何 CSS 屬性都將表現(xiàn)為這個(gè)style
對(duì)象的相應(yīng)屬性。對(duì)于使用短劃線的 CSS 屬性名雁歌,必須將其轉(zhuǎn)換成駝峰大小寫形式宏浩,才能通過(guò) JavaScript 來(lái)訪問(wèn)。- 多數(shù)情況下靠瞎,都可以通過(guò)簡(jiǎn)單地轉(zhuǎn)換屬性名的格式來(lái)實(shí)現(xiàn)轉(zhuǎn)換比庄。其中一個(gè)不能轉(zhuǎn)換的 CSS 屬性就是
float
。DOM 2 Style 規(guī)范規(guī)定樣式對(duì)象上相應(yīng)的屬性名應(yīng)該是cssFloat
乏盐,在 IE 上是styleFloat
佳窑。 - 在混雜模式下,沒(méi)有給出度量單位的值父能,將默認(rèn)為 px 神凑,但是在標(biāo)準(zhǔn)模式下,這樣的值會(huì)被忽略何吝。
- 多數(shù)情況下靠瞎,都可以通過(guò)簡(jiǎn)單地轉(zhuǎn)換屬性名的格式來(lái)實(shí)現(xiàn)轉(zhuǎn)換比庄。其中一個(gè)不能轉(zhuǎn)換的 CSS 屬性就是
- DOM 2 Style 規(guī)范為
style
對(duì)象定義了一些屬性和方法溉委。這些屬性和方法在提供元素的style
特性值的同時(shí),也可以修改樣式:-
cssText
:訪問(wèn)style
特性中的 CSS 代碼(可讀可寫)岔霸。 -
length
:應(yīng)用給元素的 CSS 屬性的數(shù)量 -
parentRule
:表示 CSS 信息的 CSSRule 對(duì)象薛躬。 -
getPropertyCSSValue(propertyName)
:返回包含給定屬性值的 CSSValue 對(duì)象。- CSSValue 包含兩個(gè)屬性:
cssText
和cssValueType
呆细;cssValueType
是一個(gè)數(shù)值常量型宝,表示值的類型:0 - 繼承的值八匠,1 - 基本的值,2 - 值列表趴酣, 3 - 自定義的值梨树。
- CSSValue 包含兩個(gè)屬性:
-
getPropertyPriority(propertyName)
:如果給定的屬性使用了!important
設(shè)置,則返回important
岖寞,否則返回空字符串抡四。 -
getPropertyValue(propertyName)
:返回給定屬性的字符串值。 -
item(index)
:返回給定位置的 CSS 屬性的名稱仗谆。 -
removeProperty(propertyName)
:從樣式中刪除給定屬性指巡。 -
setProperty(propertyName, value, priority)
:將給定屬性設(shè)置為相應(yīng)的值,并加上優(yōu)先權(quán)標(biāo)志(important
或者一個(gè)空字符串)隶垮。
-
- DOM 2 Style 增強(qiáng)了
document.defaultView
藻雪,提供了getComputedStyle()
方法。這個(gè)方法接受兩個(gè)參數(shù):要取得計(jì)算樣式的元素和一個(gè)偽元素字符串(例如::after
)狸吞。如果不需要偽元素信息可以傳入null
勉耀。這個(gè)方法返回一個(gè) CSSStyleDeclaration 對(duì)象,其中包含當(dāng)前元素的所有計(jì)算后的樣式蹋偏。- 由于瀏覽器解釋綜合( rollup )屬性的方式不同便斥,所以類似
border
這樣的綜合屬性,不會(huì)在所有瀏覽器中都有返回值威始,但是可以通過(guò)分別訪問(wèn)四個(gè)邊的屬性(例如.borderLeftWidth
)得到值枢纠。 - IE 不支持
getComputedStyle()
方法,但它有一種類似的概念黎棠。在 IE 中京郑,每個(gè)具有style
屬性的元素還有一個(gè)currentStyle
屬性。這個(gè)屬性是 CSSStyleDeclaration 的實(shí)例葫掉,包含當(dāng)前元素全部計(jì)算后的樣式些举。
- 由于瀏覽器解釋綜合( rollup )屬性的方式不同便斥,所以類似
- 不能指望某個(gè) CSS 屬性的默認(rèn)值在不同瀏覽器中是相同的,比如
visibility
屬性在有些瀏覽器中默認(rèn)值是visible
俭厚,有些是inherit
户魏。如果你需要元素具有某個(gè)特定的默認(rèn)值,應(yīng)該手工在樣式表中指定該值挪挤。
- 任何支持
-
操作樣式表
-
CSSStyleSheet 類型表示的是樣式表叼丑,包括通過(guò)
<link>
元素包含的樣式表和在<style>
元素中定義的樣式表。它只表示樣式表扛门,不管這些樣式表在 HTML 中是如何定義的鸠信。此外,這個(gè)對(duì)象是一套只讀接口(有一個(gè)屬性例外)论寨。使用下列代碼確認(rèn)瀏覽器是否支持 DOM2 StyleSheet:var supportsDOM2StyleSheet = document.implementation.hasFeature('StyleSheets', '2.0')
-
CSSStyleSheet 繼承自 StyleSheet 星立,所以我們可以使用后者作為基礎(chǔ)接口來(lái)定義非 CSS 樣式表爽茴。從 StyleSheet 接口繼承而來(lái)的屬性如下:
-
disabled
:表示樣式表是否被禁用。這個(gè)屬性是可讀 / 可寫的绰垂,將這個(gè)屬性設(shè)置為true
可以禁用樣式表室奏。 -
href
:如果樣式表是通過(guò)<link>
包含的,則是樣式表的 URL 劲装,否則胧沫,是null
。 -
media
:當(dāng)前樣式表支持的所有媒體類型(MIME Type)的集合占业。如果集合是空列表绒怨,表示樣式表適用于所有媒體。在 IE 中谦疾,media
是一個(gè)反映<link>
和<style>
元素media
特性值的字符串窖逗。 -
ownerNode
:指向擁有當(dāng)前樣式表的節(jié)點(diǎn)的指針,樣式表可能是在 HTML 中通過(guò)<link>
或<style />
引入的(在 XML 中可能是通過(guò)處理指令引入的)餐蔬。如果當(dāng)前樣式表是通過(guò)其他樣式表通過(guò)@import
導(dǎo)入的,則這個(gè)屬性值為null
佑附。IE 不支持這個(gè)屬性樊诺。 -
parentStyleSheet
:在當(dāng)前樣式表是通過(guò)@import
導(dǎo)入的情況下,這個(gè)屬性是一個(gè)指向?qū)胨臉邮奖淼闹羔槨?/li> -
title
:ownerNode
中title
屬性的值音同。 -
type
:表示樣式表類型的字符串词爬。CSS 是type/css
。
以上屬性权均,除了
disabled
之外顿膨,都是只讀的。同時(shí)叽赊,CSSStyleSheet 還支持下列屬性和方法:-
cssRules
:樣式表中包含的樣式規(guī)則的合集恋沃。IE 不支持這個(gè)屬性,但是提供了一個(gè)類似的rules
屬性必指。 -
ownerRules
:如果樣式表是通過(guò)@import
導(dǎo)入的囊咏,這個(gè)屬性就是一個(gè)指針,指向表示導(dǎo)入的規(guī)則塔橡;否則梅割,值為null
。IE 不支持這個(gè)屬性葛家。 -
deleteRule(index)
:刪除cssRules
集合中指定位置的規(guī)則户辞。IE 不支持,但提供了一個(gè)類似的removeRule()
方法癞谒。 -
insertRule(rule, index)
:向cssRules
集合中指定的位置插入rule
字符串底燎。IE 不支持刃榨,但提供了一個(gè)類似的addRule()
方法。
for (let i = 0; i < document.styleSheets.length; i++) { const sheet = document.styleSheets[i] console.log(sheet.href) }
-
-
可以直接通過(guò)
<link>
或<style>
元素取得 CSSStyleSheet 對(duì)象书蚪。DOM 規(guī)定了一個(gè)包含 CSSStyleSheet 對(duì)象的屬性喇澡,叫sheet
。除了 IE 殊校,其他瀏覽器都支持這個(gè)屬性晴玖。IE 支持的是styleSheet
屬性。要想在不同瀏覽器中都能取得樣式表對(duì)象为流,可以使用如下代碼:function getStyleSheet (element) { return element.sheet || element.styleSheet } const link = document.getElementsByTagName('link')[0] const sheet = getStyleSheet(link)
-
-
CSSRule 對(duì)象表示樣式表中的每一條規(guī)則呕屎。實(shí)際上,CSSRule 是一個(gè)供其他多種類繼承的基類型敬察,其中最常見的是 CSSStyleRule 類型秀睛,表示樣式表信息(其他規(guī)則還有
@import
、@font-face
莲祸、@page
和@charset
蹂安,但這些規(guī)則很少有必要通過(guò)腳本來(lái)訪問(wèn)。)CSSStyleRule 對(duì)象包含以下屬性:-
cssText
:返回整條規(guī)則對(duì)應(yīng)的文本锐帜。由于瀏覽器對(duì)樣式表的內(nèi)部處理方式不同田盈,返回的文本可能會(huì)與樣式表中實(shí)際的文本不一樣。Safari 會(huì)全部轉(zhuǎn)換為小寫缴阎,IE 不支持這個(gè)屬性允瞧。-
cssText
包含選擇符文本和圍繞樣式信息的花括號(hào)且只讀,style.cssText
只包含樣式信息且可被修改蛮拔。
-
-
parentRule
:如果當(dāng)前規(guī)則是導(dǎo)入規(guī)則述暂,這個(gè)屬性引用的就是導(dǎo)入規(guī)則;否則建炫,這個(gè)值為null
畦韭。IE 不支持這個(gè)屬性。 -
parentStyleSheet
:當(dāng)前規(guī)則所屬的樣式表肛跌。IE 不支持這個(gè)屬性廊驼。 -
?selectorText
:返回當(dāng)前規(guī)則的選擇符文本。由于瀏覽器對(duì)樣式表的內(nèi)部處理方式不同惋砂,返回的文本可能會(huì)與樣式表中實(shí)際的文本不一樣妒挎。 -
style
:一個(gè) CSSStyleDeclaration 對(duì)象,可以通過(guò)它設(shè)置和取得規(guī)則中特定的樣式值西饵。 -
type
:表示規(guī)則類型的常量值酝掩。對(duì)于樣式規(guī)則,這個(gè)值是 1眷柔。IE 不支持這個(gè)屬性期虾。
const sheet = document.styleSheets[0] const rules = sheet.cssRules || sheet.rules const rule = rules[0] console.log(rule.cssText) console.log(rule.style.cssText)
-
-
DOM 規(guī)定原朝,要向現(xiàn)有樣式表中添加新規(guī)則,需要使用
insertRule()
方法镶苞。這個(gè)方法接受兩個(gè)參數(shù):規(guī)則文本和表示在哪里插入規(guī)則的索引:sheet.insertRule('body { background-color: #fff }', 0)
上述語(yǔ)句的插入的規(guī)則將成為樣式表中的第一條規(guī)則(插入到了位置 0)喳坠。
IE 8 及更早的版本支持一個(gè)類似的方法,名叫addRule()
茂蚓,也接受兩個(gè)必選參數(shù):選擇符文本和 CSS 樣式信息振定;一個(gè)可選參數(shù):插入規(guī)則的位置:sheet.addRule('body', 'background-color: #fff', 0)
最多只能使用這個(gè)方法插入 4095 條樣式規(guī)則毕籽。
使用
deleteRule()
刪除規(guī)則劫笙。這個(gè)方法接受一個(gè)參數(shù):要?jiǎng)h除的規(guī)則的位置溉躲。IE 支持的類似方法叫removeRule()
,使用方法相同牍白。
-
-
元素大小
DOM 中沒(méi)有規(guī)定如何確定頁(yè)面中元素的大小脊凰,所以下邊的內(nèi)容并不屬于 DOM 2 Style 規(guī)范。IE 最早引入了一些屬性茂腥,目前狸涌,所有主要瀏覽器都支持這些屬性。
-
偏移量( offset dimension ):包括元素在屏幕上占用的所有可見空間最岗。元素的可見大小由其高度帕胆、寬度決定,包括所有內(nèi)邊距仑性、滾動(dòng)條和邊框大小(不包括外邊距)右蹦。通過(guò)下列四個(gè)屬性可以取得元素的偏移量:
-
offsetHeight
:元素在垂直方向上占用的空間大小诊杆,以像素計(jì)。 -
offsetWidth
:元素在水平方向占用的空間大小何陆。 -
offsetLeft
:元素的左外邊框至包含元素的左內(nèi)邊框之間的像素距離晨汹。 -
offsetTop
:元素的上外邊框至包含元素的上內(nèi)邊框之間的像素距離。-
offsetLeft
和offsetTop
與包含元素有關(guān)贷盲。包含元素的引用保存在offsetParent
屬性中淘这。這個(gè)屬性不一定與parentNode
的值相等。例如:<td>
元素的offsetParent
是作為其祖先元素的<table>
元素巩剖,因?yàn)?<table>
是在 DOM 層次中距<td>
最近的一個(gè)具有大小的元素铝穷。 - 要想知道某個(gè)元素在頁(yè)面上的偏移量,將這個(gè)元素的
offsetLeft
和offsetTop
與其offsetParent
的相同屬性相加佳魔,如此循環(huán)直至根元素曙聂,就可以得到一個(gè)基本準(zhǔn)確的值。
-
所有這些偏移量屬性都是只讀的鞠鲜,并且每次訪問(wèn)時(shí)都要重新計(jì)算宁脊。為了減少內(nèi)存開銷断国,我們可以將這些偏移量保存在局部變量中。
-
-
客戶區(qū)大杏馨( client dimension ):元素內(nèi)容及其內(nèi)邊距所占據(jù)的空間大小稳衬。包含兩個(gè)屬性:
-
clientWidth
:元素內(nèi)容區(qū)寬度加上左右內(nèi)邊距寬度。 -
clientHeight
:元素內(nèi)容區(qū)高度加上上下內(nèi)邊距高度坐漏。
確定瀏覽器視口大斜【巍:
function getViewport () { if (document.compatMode == 'BackCompat') { // 是否運(yùn)行在混雜模式 return { width: document.body.clientWidth, height: document.body.clientHeight } } else { return { width: document.documentElement.clientWidth, height: document.documentElement.clientHeight } } }
客戶區(qū)大小也是只讀的,也需要重新計(jì)算仙畦。
-
-
滾動(dòng)大惺涮椤( scroll dimension ):包含滾動(dòng)內(nèi)容的元素的大小。包含以下四個(gè)屬性:
-
scrollHeight
:在沒(méi)有滾動(dòng)條的情況下慨畸,元素內(nèi)容的總高度莱坎。 -
?scrollWidth
:在沒(méi)有滾動(dòng)條的情況下,元素內(nèi)容的總寬度寸士。 -
scrollLeft
:被隱藏在內(nèi)容區(qū)域左側(cè)的像素?cái)?shù)檐什。通過(guò)設(shè)置該屬性可以改變?cè)氐臐L動(dòng)位置。 -
scrollTop
:被隱藏在內(nèi)容區(qū)域上方的像素?cái)?shù)弱卡。通過(guò)設(shè)置該屬性可以改變?cè)氐臐L動(dòng)位置乃正。
由于一些兼容性差異,在確定文檔的總高度時(shí)(包括基于視口的最小高度時(shí))婶博,必須取得scrollWidth / clientWidth
和scrollHeight / clientHeight
中的最大值瓮具,才能保證在跨瀏覽器的環(huán)境下得到精確的結(jié)果。對(duì)于運(yùn)行在混雜模式下的 IE 凡人,要使用document.body
代替document.documentElement
名党。
-
-
所有的瀏覽器都提供了
getBoundingClientRect()
方法用來(lái)確定元素大小。這個(gè)方法會(huì)返回一個(gè)矩形對(duì)象挠轴,包含四個(gè)屬性:left
传睹、top
、right
岸晦、bottom
欧啤。這些屬性給出了元素在頁(yè)面中相對(duì)于視口的位置。在 IE 及更早版本的瀏覽器中启上,文檔左上角的起點(diǎn)坐標(biāo)是 (2, 2) 而其他瀏覽器是 (0, 0) 邢隧。所以需要檢查一下位于 (0, 0) 處元素的位置:function getBoundingClientRect (element) { if (typeof arguments.callee.offset !== 'number') { var scrollTop = document.documentElement.scrollTop var temp = document.createElement('div') temp.style.cssText = 'position: absolute; left: 0; top: 0;' document.body.appendChild(temp) arguments.callee.offset = - temp.getBoundingClientRect().top - scrollTop document.body.removeChild(temp) temp = null } var rect = element.getBoundingClientRect() var offset = arguments.callee.offset return { left: rect.left + offset right: rect.right + offset top: rect.top + offset bottom: rect.bottom + offset
Poly Fill: Custom
getBoundingClientRect()
method [詳見書 P326]
遍歷
-
DOM 2 Traversal 定義了兩個(gè)用于輔助完成順序遍歷 DOM 結(jié)構(gòu)的類型:NodeIterator 和 TreeWalker 。這兩個(gè)屬性能夠基于給定的起點(diǎn)對(duì) DOM 結(jié)構(gòu)進(jìn)行深度優(yōu)先遍歷操作冈在。IE 不支持 DOM 遍歷府框。使用下列代碼檢測(cè):
var supportsTraversals = document.implementation.hasFeature('Traversal', '2.0') var supportsNodeIterator = (typeof document.createNodeIterator === 'function') var supportsTreeWalker = (typeof document.createTreeWalker === 'function')
-
NodeIterator 類型是兩者中比較簡(jiǎn)單的一個(gè),可以使用
document.createNodeIterator()
方法創(chuàng)建它的新實(shí)例。它接收以下四個(gè)參數(shù):-
root
:想要作為搜索起點(diǎn)的樹中的節(jié)點(diǎn)迫靖。 -
whatToShow
:表示要訪問(wèn)哪些節(jié)點(diǎn)的數(shù)字代碼院峡。-
它的參數(shù)是一個(gè)位掩碼,通過(guò)應(yīng)用一個(gè)或多個(gè)過(guò)濾器(
filter
)來(lái)確定要訪問(wèn)哪些節(jié)點(diǎn)系宜。這個(gè)參數(shù)的值以常量形式在 NodeFilter 類型中定義照激,如下所示:-
NodeFilter.SHOW_ALL
:顯示所有類型的節(jié)點(diǎn)。 -
NodeFilter.SHOW_ELEMENT
:顯示元素節(jié)點(diǎn)盹牧。 -
NodeFilter.SHOW_ATTRIBUTE
:顯示特性節(jié)點(diǎn)俩垃。由于 DOM 結(jié)構(gòu)原因,實(shí)際上不能使用這個(gè)值汰寓。 -
NodeFilter.SHOW_TEXT
:顯示文本節(jié)點(diǎn)口柳。 -
NodeFilter.SHOW_CDATA_SECTION
:顯示 CDATA 節(jié)點(diǎn)。對(duì) HTML 頁(yè)面沒(méi)有作用有滑。 -
NodeFilter.SHOW_ENTITY_REFERENCE
:顯示實(shí)體引用節(jié)點(diǎn)跃闹。對(duì) HTML 頁(yè)面沒(méi)有作用。 -
NodeFilter.SHOW_ENTITY
:顯示實(shí)體節(jié)點(diǎn)毛好。對(duì) HTML 頁(yè)面沒(méi)有作用望艺。 -
NodeFilter.SHOW_PROCESSING_INSTRUCTION
:顯示處理指令節(jié)點(diǎn)。對(duì) HTML 頁(yè)面沒(méi)有作用肌访。 -
NodeFilter.SHOW_COMMENT
:顯示注釋節(jié)點(diǎn)找默。 -
NodeFilter.SHOW_DOCUMENT
:顯示文檔節(jié)點(diǎn)。 -
NodeFilter.SHOW_DOCUMENT_TYPE
:顯示文檔類型節(jié)點(diǎn)吼驶。 -
NodeFilter.SHOW_DOCUMENT_FRAGMENT
:顯示文檔片段節(jié)點(diǎn)惩激。對(duì) HTML 頁(yè)面沒(méi)有作用。 -
NodeFilter.SHOW_NOTATION
:顯示符號(hào)節(jié)點(diǎn)蟹演。對(duì) HTML 頁(yè)面沒(méi)有作用风钻。
除了
SHOW_ALL
之外,可以用|
運(yùn)算符組合多個(gè)選項(xiàng)轨帜。 -
-
-
filter
:一個(gè) NodeFilter 對(duì)象魄咕,或者一個(gè)表示應(yīng)該接受還是拒絕某種特定節(jié)點(diǎn)的函數(shù)衩椒。- 每個(gè) FilterNode 對(duì)象只有一個(gè)方法蚌父,即
acceptNode()
。如果應(yīng)該訪問(wèn)給定的節(jié)點(diǎn)毛萌,該方法返回NodeFilter.FILTER_ACCEPT
苟弛,如果不應(yīng)該則返回NodeFilter.FILTER_SKIP
。這是一個(gè)抽象類型阁将,不能直接創(chuàng)建它的實(shí)例膏秫。在必要時(shí),只要?jiǎng)?chuàng)建一個(gè)包含acceptNode()
方法的對(duì)象做盅,然后將這個(gè)對(duì)象傳入createNodeIterator()
中即可缤削。
- 每個(gè) FilterNode 對(duì)象只有一個(gè)方法蚌父,即
-
entityReferenceExpansion
:布爾值窘哈,表示是否要擴(kuò)展實(shí)體引用。這個(gè)參數(shù)在 HTML 頁(yè)面中沒(méi)有用亭敢,因?yàn)槠渲械膶?shí)體引用不能擴(kuò)展滚婉。
NodeIterator 類型的兩個(gè)主要方法:
-
nextNode()
:向后前進(jìn)一步,當(dāng)遍歷到最后一個(gè)節(jié)點(diǎn)時(shí)帅刀,返回null
让腹。 -
previousNode()
:向前倒退一步,當(dāng)遍歷到根節(jié)點(diǎn)時(shí)扣溺,返回null
骇窍。
例子:返回遍歷中遇到的
<li>
元素var div = document.getElementById('div1') var filter = function (node) { return node.tagName.toLowerCase() === 'li' ? NodeFilter.FILTER_ACCEPT : NodeFilter.FILTER_SKIP } var iterator = document.createNodeIterator(div, NodeFilter.SHOW_ELEMENT, filter, false) var node = iterator.nextNode() while(node !== null) { console.log(node.tagName) node = iterator.nextNode() }
-
-
TreeWalker 是 NodeIterator 的一個(gè)更高級(jí)的版本。除了包括
nextNode()
和previousNode()
在內(nèi)的相同功能之外锥余,這個(gè)類型還提供了下列用于在不同方向上遍歷 DOM 結(jié)構(gòu)的方法腹纳。-
parentNode()
:遍歷到當(dāng)前節(jié)點(diǎn)的父節(jié)點(diǎn)。 -
firstChild()
:遍歷到當(dāng)前節(jié)點(diǎn)的第一個(gè)子節(jié)點(diǎn)哈恰。 -
lastChild()
:遍歷到當(dāng)前節(jié)點(diǎn)的最后一個(gè)子節(jié)點(diǎn)只估。 -
nextSibling()
:遍歷到當(dāng)前節(jié)點(diǎn)的下一個(gè)同輩節(jié)點(diǎn)。 -
previousSibling()
:遍歷到當(dāng)前節(jié)點(diǎn)的上一個(gè)同輩節(jié)點(diǎn)着绷。
創(chuàng)建 TreeWalker 對(duì)象要使用
document.createTreeWalker()
方法蛔钙,這個(gè)方法接受四個(gè)參數(shù),與document.createNodeIterator
相同荠医。-
filter
的返回值吁脱,除了FILTER_ACCEPT
和FILTER_SKIP
之外,還可以使用FILTER_REJECT
彬向,在 NodeIterator 中兼贡,NodeFilter.FILTER_SKIP
與NodeFilter.FILTER_REJECT
作用相同:跳過(guò)指定節(jié)點(diǎn)。但在 TreeWalker 中娃胆,FILTER_SKIP
會(huì)跳過(guò)相應(yīng)節(jié)點(diǎn)繼續(xù)前進(jìn)到子樹中的下一個(gè)節(jié)點(diǎn)遍希,而FILTER_REJECT
會(huì)跳過(guò)相應(yīng)節(jié)點(diǎn)及該節(jié)點(diǎn)的整個(gè)子樹。
-
范圍
DOM 2 Traversal & Range 模塊定義了范圍( range )接口里烦。通過(guò)范圍可以選擇文檔中的一個(gè)區(qū)域凿蒜,而不必考慮節(jié)點(diǎn)的界限(選擇在后臺(tái)完成,對(duì)用戶是不可見的胁黑。)IE 實(shí)現(xiàn)范圍特性的方式不同废封。
-
DOM 2 在 Document 類型中定義了
createRange()
方法。在兼容 DOM 的瀏覽器中丧蘸,這個(gè)方法屬于document
對(duì)象漂洋。檢測(cè)方法:var supportsRange = document.implementation.hasFeature('Range', '2.0') var alsoSupportsRange = (typeof document.createRange === 'function')
-
可以使用
document.createRange()
創(chuàng)建一個(gè) Range 類型的實(shí)例。該實(shí)例包含以下屬性,他們提供了當(dāng)前范圍在文檔中的位置信息:-
startContainer
:包含范圍起點(diǎn)的節(jié)點(diǎn)(即選中區(qū)第一個(gè)節(jié)點(diǎn)的父節(jié)點(diǎn)) -
startOffset
:范圍在startContainer
中起點(diǎn)的偏移量刽漂。如果startContainer
是文本節(jié)點(diǎn)演训、注釋節(jié)點(diǎn)或 CDATA 節(jié)點(diǎn),那么startOffset
就是范圍起點(diǎn)之前跳過(guò)的字符數(shù)量贝咙,否則仇祭,就是范圍中第一個(gè)子節(jié)點(diǎn)的索引。 -
endContainer
:包含范圍終點(diǎn)的節(jié)點(diǎn)(即選區(qū)中最后一個(gè)節(jié)點(diǎn)的父節(jié)點(diǎn))颈畸。 -
endOffset
:范圍在endContainer
中終點(diǎn)的偏移量(與startOffset
遵循相同的取值規(guī)則)乌奇。 -
commonAncestorContainer
:startContainer
和endContainer
共同的祖先節(jié)點(diǎn)在文檔樹中位置最深的那個(gè)。
-
-
用 DOM 范圍實(shí)現(xiàn)簡(jiǎn)單選擇:
selectNode()
和selectNodeContents()
眯娱。它們都接收一個(gè)參數(shù)礁苗,即一個(gè) DOM 節(jié)點(diǎn)。然后使用該節(jié)點(diǎn)中的信息來(lái)填充范圍徙缴。其中试伙,selectNode()
方法選擇整個(gè)節(jié)點(diǎn),包括子節(jié)點(diǎn)于样;selectNodeContents()
只選擇節(jié)點(diǎn)的子節(jié)點(diǎn)疏叨。var range = document.createRange() range.selectNode(document.getElementById('test')
為了更精細(xì)的控制將哪些節(jié)點(diǎn)包含在范圍中,還可以使用下列方法:
-
setStartBefore(refNode)
:將范圍起點(diǎn)設(shè)置在refNode
之前穿剖,即refNode
是范圍選區(qū)中的第一個(gè)子節(jié)點(diǎn)蚤蔓。 -
setStartAfter(refNode)
:將范圍起點(diǎn)設(shè)置在refNode
之后,即refNode
的下一個(gè)同輩節(jié)點(diǎn)是范圍選區(qū)中的第一個(gè)子節(jié)點(diǎn)糊余。 -
?setEndBefore(refNode)
:將范圍終點(diǎn)設(shè)置在refNode
之前秀又,即refNode
的上一個(gè)同輩節(jié)點(diǎn)是范圍選區(qū)中的最后一個(gè)子節(jié)點(diǎn)。 -
?setEndAfter(refNode)
:將范圍終點(diǎn)設(shè)置在refNode
之后贬芥,即refNode
是范圍選區(qū)中的最后一個(gè)子節(jié)點(diǎn)吐辙。
-
用 DOM 范圍實(shí)現(xiàn)復(fù)雜選擇:
setStart()
和setEnd()
。這兩個(gè)方法都接受兩個(gè)參數(shù):參照節(jié)點(diǎn)和偏移量蘸劈,分別對(duì)應(yīng)startContainer
/endContainer
和startOffset
/endOffset
昏苏。-
操作 DOM 范圍中的內(nèi)容:創(chuàng)建范圍時(shí),內(nèi)部會(huì)為這個(gè)范圍創(chuàng)建一個(gè)文檔片段威沫,范圍所屬的全部節(jié)點(diǎn)都被添加到了這個(gè)文檔片段中贤惯。范圍會(huì)自動(dòng)完善 DOM 結(jié)構(gòu),變成一個(gè)有效的 DOM 壹甥。于是救巷,就可以使用下列方法進(jìn)行操作了:
-
deleteContents
:從文檔中刪除范圍所包含的內(nèi)容壶熏。 -
extractContents
:從文檔中移除范圍選區(qū)(返回范圍的文檔片段)句柠。 -
cloneContents
:返回范圍中節(jié)點(diǎn)的副本作為文檔片段。
-
插入 DOM 范圍中的內(nèi)容:
insertNode()
折疊 DOM 范圍:
collapse()
比較 DOM 范圍:
compareBoundaryPoints()
比較是否有公共邊界(起點(diǎn)或終點(diǎn))復(fù)制 DOM 范圍:
range.cloneRange()
-
清理 DOM 范圍:
range.detach() range = null
IE 8 及更早版本的范圍
[詳見書 P340]