(二)文檔對象模型(DOM),你只需知道這些就夠了!


官方定義——應用程序編程接口(API)

文檔對象模型是用於HTML和XML文檔的應用程序編程接口,它定義文檔的邏輯結構,以及訪問和操作文檔的方式

"The Document Object Model (DOM) is an application programming interface (API) for HTML and XML documents. It defines the logical structure of documents and the way a document is accessed and manipulated." —— W3C DOM

“文檔對象模型是用於HTML和XML文檔的應用程序編程接口”

應用程序編程接口(Application Program Interface,簡稱API),就是“提供商”將一個功能的具體實現(業務邏輯)封裝起來,只暴露給“客戶”可供調用的編程接口。如果客戶想使用某一功能,則只需調用該功能對應的編程接口,而無需關注於具體實現。打個比方,海爾生產空調,你購買空調后按照說明書操作空調就好,不需要知道空調是根據什么原理造出來的。

對於DOM而言,“提供商”指的就是實現DOM的開發者(比如,開發JavaScript引擎V8的工程師),“客戶”指的就是使用DOM的開發者(比如,開發網站的前端工程師)。他們之間共同遵守的就是DOM規范。

因此,DOM規范同時約束它的實現者和使用者。DOM實現者必須實現規范中定義的所有接口,DOM使用者應該調用規范中相應的接口實現相應的功能。

如果你是實現者,需要關注如何實現DOM API;如果你是使用者,則只需關注如何使用DOM API。

它定義文檔的邏輯結構,以及訪問和操作文檔的方式

上面這句話對 DOM API 作了更具體的解釋,包括三層意思:

  • 定義文檔的結構
  • 訪問文檔的方式
  • 操作文檔的方式

HTML DOM 是對 DOM Core 的擴展,添加了專門針對 HTML 文檔的特定對象和方法,它與現有的文檔對象模型一致。下面我們就來討論如何使用 HTML DOM API 的問題。

一、如何定義文檔的邏輯結構?——節點對象樹

DOM規范,將網頁中的HTML文檔抽象為內存中的節點對象樹(DOM Tree)。樹中的每一個節點對象對應HTML文檔中的一個元素。

節點對象樹

 

二、如何訪問文檔?——訪問節點對象

(0) Document 接口作為文檔入口

Document 接口代表整個文檔。JavaScript 中的全局對象 document 是對 Document 接口的實現。

(1) 直接訪問文檔中的節點對象。

方法 描述
document.getElementsById("id"); 通過 id 屬性獲取節點對象
document.getElementsByName("name"); 通過 name 屬性獲取節點對象
document/element.getElementsByTagName("tag"); 通過 tag 屬性獲取節點對象
document/element.getElementsByClassName("class1[ class2]"); 通過 class 屬性獲取節點對象
document/element.querySelector("selector"); 通過 css 選擇器 獲取首個節點對象
document/element.querySelectorAll("selector"); 通過 css 選擇器 獲取所有節點對象

(2) 通過節點關系訪問一個節點周圍的節點對象。

關系 屬性 描述
父節點(parent node) parentNode/parentElement 獲取所屬父節點對象
  ownerDocument 獲取節點所屬文檔節點(根節點)對象
兄弟節點(sibling nodes) nextSibling
nextElementSibling
獲取前一個兄弟節點對象
獲取前一個兄弟元素節點對象
  previousSibling
previousElementSibling
獲取后一個兄弟節點對象
獲取后一個兄弟元素節點對象
子節點(child nodes) childNodes
children
獲取所有子節點對象
獲取所有子元素節點對象
  hasChildNodes(); 判斷是否包含子節點對象
  childElementCount 獲取子元素節點對象數量
  firstChild
firstElementChild
獲取第一個子節點對象
獲取第一個子元素節點對象
  lastChild
lastElementChild
獲取最后一個子節點對象
獲取最后一個子元素節點對象

 

三、如何操作文檔?——操作節點對象

思路一:【節點對象】首先是一個【對象】,只要是對象就具有【屬性】和【行為】。

元素節點p作為對象,id,class,style(該屬性是一個對象)等作為對象的屬性,onclick,onfocus,oninput 等作為對象的行為,具體的動作由 JavaScript 代碼控制。

思路二:節點對象只包含屬性 —— 特性屬性樣式屬性行為(事件)屬性

2018-01-03_101557

將【行為】看作對象的一種屬性,以下實例印證了這一觀點:

捕獲1

我們獲取節點對象的目的,就是為了操作節點對象本身以及節點對象的屬性

(0) 操作節點對象本身

操作 方法 描述
創建節點 document.createElement("TAG");
document.createTextNode("#文本");
document.createComment("#注釋");
document.createDocumentFragment();
document.createAttribute("myAttrName");
創建一個元素節點
創建一個文本節點
創建一個注釋節點
創建一個空白的文檔片段節點
創建一個屬性節點
插入節點 parentNode.appendChild(newChild);
parentNode.insertBefore(newChild,refChild);
插入子節點(作為最后子節點)
插入子節點(在指定子節點之前)
刪除節點 parentNode.removeChild(oldChild); 刪除指定的子節點
替換節點 parentNode.replaceChild(newChild,oldChild); 替換一個子節點
克隆節點 node.cloneNode(deep); 克隆一個節點

(1) 操作節點對象的特性屬性

方法 描述
e.特性名稱[="value"]; 獲取/設置特性值
e.getAttributeNames(); 獲取已設置的全部屬性名稱(非IE內核)
e.getAttribute("特性名稱"); 獲取特性值
e.getAttributeNode("特性名稱"); 獲取特性節點[特性名稱=特性值]
e.setAttribute("特性名稱","特性值"); 設置特性值(不存在時新建該屬性)
e.setAttributeNode(Attr); 設置特性節點

(2) 操作節點對象的樣式屬性

方法 描述
e.style.color[ ="顏色值"] 獲取/設置標簽內樣式(內嵌樣式)
window.getComputedStyle(e).color;
document.defaultView.getComputedStyle(e).color;
獲取包括內嵌樣式、<style>、<link>在內的最終樣式(非IE內核 或 IE>8)
e.currentStyle.color 獲取包括內嵌樣式、<style>、<link>在內的最終樣式(IE內核)

(3) 操作節點對象的行為(事件)屬性

方法 描述
e.onclick[ =fun()];
e.onclick();
獲取/設置事件
觸發事件
e.addEventListener("type",listener,[useCapture]); 注冊事件(非IE內核 或 IE>8)
e.attachEvent("ontype",listener); 注冊事件(IE內核<11)
e.removeEventListener("type",listener,[useCapture]); 移除事件(非IE內核 或 IE>8)
e.detachEvent("ontype",listener); 移除事件(IE內核<11)
e.dispatchEvent(event) 調度(觸發)事件

(4) 操作節點對象的內容(屬性)

節點對象的內容,實際上是節點對象的子節點。傳統的方法是使用新創建的子節點替換需要修改的舊子節點。

<html>
    <body>
        <div>
            <p>第一個段落</p>
            <p>第二個段落</p>
        </div>
    </body>
</html>
<script>
    //獲取父節點
    var d = document.querySelector("div");
    //獲取需要替換的舊子節點
    var oldChild = d.firstChild;
    //創建新子節點
    var newChild = document.createTextNode("新的文本");
    //替換
    d.replaceChild(newChild ,oldChild );
</script>

如此常用的操作,卻有如此繁瑣的操作過程,況且一次只能替換一個子節點,這也太坑了吧!別急,DOM 規范為我們提供了更加簡便的操作。

轉換一下思路,我們將節點對象的內容看作是節點對象的一個屬性。那么方法 e.innerHTML 屬性將以字符串的形式返回所有節點對象的內容。 e.innerHTML = newStr 將替換該內容。newStr 可以包含tag,替換的內容會自動轉換為節點對象(其實簡單的文本字符串,也會轉換成一個文本節點)。

<script>
    //獲取節點
    var d = document.querySelector("div");
    //修改節點內容
    var str = "新的文本";
    d.innerHTML= str;
</script>

最終的節點對象應該是下面這張圖:

無標題

【The End】


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM