一篇文章搞懂DOM

来源:http://www.cnblogs.com/thinkguo/archive/2017/09/08/7494830.html
-Advertisement-
Play Games

學習JavaScript肯定是會遇到DOM操作,那麼什麼是DOM?它又是幹嘛用的?這篇文章為你揭曉答案。 DOM是document object model的縮寫,簡稱文檔對象模型。 簡單的說DOM是一套對文檔的內容進行抽象和概念化的方法。我們可以把HTML文檔模型化,當作對象來處理。 基本概念: ...


學習JavaScript肯定是會遇到DOM操作,那麼什麼是DOM?它又是幹嘛用的?這篇文章為你揭曉答案。

DOMdocument object model的縮寫,簡稱文檔對象模型。

簡單的說DOM是一套對文檔的內容進行抽象和概念化的方法。我們可以把HTML文檔模型化,當作對象來處理。

基本概念:

文檔(document): HTMLXML文件。

節點(node):HTML文檔中的所有內容都可以稱之為節點,常見的節點有 元素節點 屬性節點 文本節點 註釋節點

元素(element): HTML文檔中的標簽可以稱為元素

我們可以把一個HTML文檔看做一個樹形結構的對象,每一個標簽會形成一個分支,這樣就很容易理解了,如下圖所示(圖片來自w3school)。

 

知道了什麼是DOM,肯定要問DOM有什麼用?

DOMHTML文檔抽象成一個對象,肯定是為了方便使用JavaScriptHTML文檔進行操作。DOM的作用就是為了對頁面的結構內容進行操作,增加頁面的動態特性。

好了,知道了DOM是幹嘛用的,那麼下麵我們就學習如何進行DOM操作。

DOM操作主要分四個部分:

1、獲取HTML節點及修改節點的屬性

2、修改節點的樣式

3、給節點綁定事件

4、節點操作

現在我們進行一一介紹

獲取HTML節點與修改節點屬性(包含表單元素)

DOM提供了三個獲取節點的方法

方法一:

getElementById()   //根據id屬性獲取一個DOM對象,區分大小寫,符合代碼規範

通過id尋找一個元素(找到的是一個元素對象) 該方法只能被document對象調用(同一個文檔中id不能重覆)

<div id="box"></div>

var box = document.getElementById(“box”);

 

方法二:

getElementsByTagName()    //根據標簽返回多個DOM對象

通過標簽名尋找一類元素(找到的是由元素對象組成的偽數組) 即可以被document調用,又可以被元素對象調用,被元素對象調用時表示在該元素對象內部執行查找

通常針對多個標簽,而且常會要用到for迴圈。

<div class="cl" id=“cl”>

    <div class="cl2"></div>

    <div class="cl2"></div>

</div>

<div class="cl"></div>

<div class="cl"></div>


var divs = document.getElementsByTagName("div");// 獲取頁面上所有div,divs是一個偽數組

var cl = document.getElementById("cl");// 獲取id為cl的元素

var cl2s = cl.getElementsByTagName("div");// 獲取cl元素下麵所有的div標簽,cl2s是一個偽數組

方法三:

getElementsByClassName()

通過類名尋找一類元素

<div class="cl" id=“cl”>

    <p class="cl"></div>

    <span class="cl"></div>

</div>

<a class="cl"></a>

var cls = document.getElementsByClassName("cl");//獲取到的是一個偽數組,裡面裝的是div p span a這四個元素對象

 

獲得到了節點元素後我們就可以對節點元素的屬性進行修改了。

DOM也提供了兩個方法供我們獲取和修改元素的屬性值。

getAttribute()

getAttribute是一個函數,用於獲取節點屬性。它只有一個參數,即所需要查詢的屬性的名字。getAttribute不屬於document對象,所有不能通過document對象調用,只能通過元素節點對象調用。

<div id="box" title=hello></div>
var box = document.getElementById(“box”); console.log(box.getAttribute(“title”));

通過這個方法我們可以獲取元素boxtitle屬性值為hello

setAttribute()

setAttribute也是一個函數,用於修改節點屬性。與getAttribute用法類似,不同的地方在於它有兩個參數,第一個為屬性名,第二個參數為設定的屬性值。

<div id="box" title=hello></div>


var box = document.getElementById(“box”);

console.log(box.setAttribute(“title”,”world”));

此時,box節點的title屬性值已經變為world

是不是感覺so easy.

其實還有更為簡便的方法來修改屬性值,直接使用點語法就可以了。

獲取屬性值

var 變數=box.title;

修改屬性值

box.屬性名 = “屬性值

是不是感覺更簡單呢。

在此我只舉例了title屬性,當然元素的屬性還有很多,比如img標簽的src屬性,我們可以更改src屬性來切換圖片。還可以設置表單元素的屬性

type可以設置input元素的類型

value可以設置input元素的值

checked可以設置input元素是否選中

selected 可以設置下拉列表select中的option是否被選中

disabled 可以設置input元素是否被禁用

好了,屬性的操作就到此為止。

獲取節點與控制樣式

關於節點的獲取,上面只用到了三個方法,但是實際的項目HTML文檔往往是很複雜的,

文檔中所有的節點之間都存在這樣或那樣的關係。節點間的各種關係可以用傳統的家族關係來描述,相當於把文檔樹比喻成家譜。在 HTML 中,可以將<body>元素看成是<html>元素的子元素;相應地,也就可以將<html>元素看成是<body>元素的父元素。而<head>元素,則可以看成是<body>元素的同胞元素,因為它們都是同一個父元素<html>的直接子元素。

首先我們來認識一下文檔的層級結構,都有那些關係。

childNodes //子節點

children //子元素 雖然不是早期DOM標準中的方法,但是所有瀏覽器都支持

 

nextSibling //下一個兄弟節點

nextElementSibling //下一個兄弟元素 有相容性問題

previousSibling//上一個兄弟節點

previousElementSibling //上一個兄弟元素 有相容性問題

 

firstChild //第一個節點

firstElementChild //第一個子元素 有相容性問題

lastChild //最後一個子節點

lastElementChild //最後一個子元素 有相容性問題

 

parentNode //父節點 (一定是元素節點,所以無需處理)

所有獲取節點相關屬性都沒有相容性問題

註意:節點和元素不是同一個概念,文章開頭說過,在此提醒一下。

獲取子節點&子元素

  • childNodes: 獲取指定元素的子節點,包括文本節點、元素節點等
  • children: 獲取知道元素的子元素,只會獲取元素節點。<ul id="list">
    <li><a href="javascript:void(0)">首頁</a></li>

    <li><a href="javascript:void(0)">播客</a></li>

    <li><a href="javascript:void(0)">博客</a></li>

    <li><a href="javascript:void(0)">相冊</a></li>

    <li><a href="javascript:void(0)">關於</a></li>

    <li><a href="javascript:void(0)">幫助</a></li>

</ul>
<script> var ul = document.getElementById("list"); var lis = ul.getElementsByTagName("li"); //不關心層級 只找指定標簽 //缺點: 如果內部還有li 也會找到 var nodes = ul.childNodes; //子節點 只找子級 //缺點: 除了我們想要的元素節點 還會獲取到其他節點 var children = ul.children;//子元素

</script>

childNodesDOM標準中規定的方法 獲取節點的方式所有瀏覽器都支持
children不是DOM標準中規定的方法 因為很常用所有瀏覽器也都支持

在實際應用中,基本都是用children。

獲取下一個兄弟節點

nextSibling:下一個兄弟節點

<input type="text" id="txtName">

<span></span>

<input type="text" id="txtPwd"><span></span>

<input type="button" id="btn" value="註冊">

 <script>

var txt = document.getElementById("txtName");

var next = txt.nextSibling;// 獲取到的是換行,空文本節點

var pwd = document.getElementById("txtPwd");

var next = pwd.nextSibling;// 獲取到的是span元素,因為兩個標簽間沒有其他節點

 </script>

獲取下一個兄弟元素

nextElementSibling: 下一個兄弟元素

<input type="text" id="txtName">

<span></span>

 <script>

var txt = document.getElementById("txtName");

var next = txt.nextElementSibling;// 可以獲取到span元素,只獲取下一個兄弟元素,忽略非元素類型的節點

 </script>

獲取父節點

parentNode: 獲取元素的父節點,父節點肯定是一個元素

<div id = "box">
    <img src="1.jpg" id="img"/>
</div>
<script>
var img = document.getElementById("img");
var parent = img.parentNode; //獲取到的就是id為box的div元素
 </script>

節點的獲取我就先介紹到這裡,關於相容性的問題我會再做補充。

下麵看一下如何進行節點的樣式操作。

獲取樣式

  • 通過style只能獲取行內樣式
  • 獲取的樣式如果有單位,獲取到的樣式中也會帶單位,類型是一個字元串

設置樣式

1通過style設置樣式

  • 通過style設置的是行內樣式
  • 如果樣式需要單位,設置時也需要把單位帶上
div{

    width:100px;

    height:100px;

}

<div id="box"></div>

var box = document.getElementById("box");

consloe.log(box.style.width);// 列印的是空字元串,因為只能獲取行內樣式

box.style.width = "300px";// 設置的是行內樣式,而且這裡必須帶單位

console.log(box.style.width);// 列印的是“300px“/

 

2通過類名設置樣式

.b{

    width:100px;

    height:100px;

    background-color:red;

}

<div id="box"></div>

var box = document.getElementById("box");

// 通過類名設置樣式 兩種方式

box.className = "b";

box.setAttribute("class","b");

下麵介紹事件綁定

綁定事件

事件三要素: 事件源 事件 事件處理程式

事件源.事件 = function(){

    // 事件處理程式

}

<img src="pic.jpg" id="img"/>

var img = document.getElementById("img");

img.onclick = function(){

   ...

}

img是事件源 事件是點擊onclick 事件處理程式是函數體中的內容

下麵為常用事件總結

屬性

描述

Onblur

元素失去焦點。

Onchange

域的內容被改變。

Onclick

當用戶點擊某個對象時調用的事件句柄。

ondblclick

當用戶雙擊某個對象時調用的事件句柄。

Onfocus

元素獲得焦點。

onkeydown

某個鍵盤按鍵被按下。

onkeypress

某個鍵盤按鍵被按下並鬆開。

Onkeyup

某個鍵盤按鍵被鬆開。

Onload

一張頁面或一幅圖像完成載入。

onmousedown

滑鼠按鈕被按下。

onmousemove

滑鼠被移動。

onmouseout

滑鼠從某元素移開。

onmouseover

滑鼠移到某元素之上。

onmouseup

滑鼠按鍵被鬆開。

Onreset

重置按鈕被點擊。

Onresize

視窗或框架被重新調整大小。

Onunload

用戶退出頁面。

 

節點操作

節點操作就5種形式,克隆節點、添加節點、插入節點、移除節點和創建節點。

克隆節點 - cloneNode()

element.cloneNode(): 複製element節點

參數:布爾值,

true代表深層克隆,把當前節點和內部所有節點都複製一份

false代表淺層克隆,只複製當前節點

<div id="father">

    <div id="son"><div/>

</div>

var father = document.getElementById("father");

var son = document.getElementById("son");

var clone = son.cloneNode(true);// 把son這個div複製一份 複製出來的clone和son沒有任何關係了

添加節點 - appendChild()

father.appendChild(son):son節點追加到father內部的最後位置

<div id="father">
    <div id="son"><div/>
</div>
<div id="demo"></div>

var father = document.getElementById("father");
var demo = document.getElementById("demo");
var clone = demo.cloneNode(true);// 將demo克隆一份

father.appendChild(clone);// 將克隆出來的clone追加到father中

// 此時頁面結構應該為

<div id="father">

    <div id="son"><div/>

    <div id="demo"></div>

</div>

<div id="demo"></div>

//追加克隆節點對原節點不會產生影響

//如果代碼如下 則會將demo節點直接移動到father節點下

father.appendChild(demo);// demo是頁面上存在的節點

// 此時頁面結構應該為

<div id="father">

    <div id="son"><div/>

    <div id="demo"></div>

</div>

 

插入節點 - insertBefore()

father.inserBefore(son1,son2): son1插入到father節點下的son2前面

<div id="father">

    <div id="son"><div/>

</div>

<div id="demo"></div>

var father = document.getElementById("father");

var son = document.getElementById("son");

var demo = document.getElementById("demo");

father.inserBefore(son,demo);//會直接將demo節點移動到father下的son前面       

插入克隆出來的節點也不會對原節點產生影響

 

移除節點 - removeChild()

father.removeChild(son): father下的son節點移除

<div id="father">

    <div id="son"><div/>

</div>

var father = document.getElementById("father");

var son = document.getElementById("son");

father.removeChild(son);// 直接將son節點刪除

創建節點

document.write()

特點:只能被document調用,而且會覆蓋頁面上原有內容

document.write("<a href="http://www.baidu.com">百度</a>")

// 可以在頁面上創建一個a標簽,而且會覆蓋頁面上原有的所有內容

innerHtml()

特點:往頁面添加html標簽,可以限定範圍

<div id="box"></div>

var box = document.getElementById("box");

box.innerHtml = "<a href="http://www.baidu.com">百度</a>";

// 追加後的結構為

<div id="box">

    <a href="http://www.baidu.com">百度</a>

</div>

createElement()

特點:動態創建標簽,添加到頁面需要配合appendChild使用。

<div id="box"></div>

var box = document.getElementById("box");
var input = document.createElement("input");

input.type = "text";
box.appendChild(input);

 

DOM的基本操作就到此為止了,如果對你有所幫助就給本文點個贊吧O(∩_∩)O

 


您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 說起日誌,大家都是耳熟能詳的,一大堆日誌插件映入眼帘,日誌收集的方式也歷歷在目,但是,今天我們的重點不僅僅是收集日誌了,今天我們主要說說怎麼管理日誌 收集日誌 日誌管理的第一件事,就是日誌的收集。日誌收集是開發者必備的技巧,不管是哪個開發語言,哪個開發平臺,日誌收集的插件都是有很多選擇的。例如: . ...
  • 為了發送一個請求,您的代碼需要知道服務實例的網路位置(IP 地址與埠)。在運行於物理硬體上的傳統應用中,服務實例的網路位置是相對靜態的。例如,您的代碼可以從偶爾更新的配置文件中讀取網路位置。服務實例具有動態分配的網路位置。此外,由於自動擴展、故障與升級,整組服務實例會動態變更。因此,您的客戶端代碼... ...
  • 哎呀,一不小心自己的博客也是HTTP/2.0了,前段時間對網站進行了https遷移並上了CDN,最終的結果是這醬紫的(重點小綠鎖,安全標示以及HTTP/2.0請求)。 科普 隨著互聯網的快速發展,HTTP1.x協議得到了迅猛發展,但當網站一個頁麵包含了數幾十個請求時,HTTP1.x協議的局限性便暴露 ...
  • 1. 寫在前面 當我們登錄了一個網站,在沒有退出登錄的情況下,我們關閉了這個網站 ,過一段時間,再次打開這個網站,依然還會是登錄狀態。這是因為,當我們登錄了一個網站,伺服器會保存我們的登錄狀態,直到我們退出登錄,或者保存的登錄狀態過期。那伺服器是通過什麼存儲我們的登錄狀態的呢? 答案就是 Sessi ...
  • background attachment 該屬性來定義背景圖片隨滾動軸的移動方式 取值: scroll | fixed | inherit scroll : 隨著頁面的滾動軸背景圖片將移動 fixed : 隨著頁面的滾動軸背景圖片不會移動 inherit : 繼承 ...
  • 在JS中,函數的調用大多數都是由用戶主動調用觸發,但是在有的事件中,比如mousemove、window.onresize、touchmove中,函數的調用次數會非常頻繁,從而消耗瀏覽器大量的記憶體空間,造成瀏覽器卡頓甚至假死的問題。所以函數節流的目的就是減少函數在這些事件中的調用次數,從不可控制到可 ...
  • 源代碼下方 由於本人喜愛html5,無聊所畫: 畫圖需要掌握; 1.畫布,畫筆,畫圓,給畫筆添加顏色。(註:掌握這幾點,你就可以稱霸畫圖界了。) 雖然沒有畫畫天賦,但代碼寫的也是溜溜滴!(註:此圖沒有上色完,想裝逼,自己補完!) 別忘了點個關註! <!DOCTYPE html><!-- saved ...
  • 用 js 畫工作日曆的時候,需要用 js 計算指定月份一共有多少天 在網上找了些方法,都比較繁瑣,後來靈機一動,想到一個偷懶的辦法,分享一下 一、原理分析 要想得到某月有多少天,只需要獲取到當月最後一天的日期就行了 圍繞這一思路,靈活調用 setMonth(),getMonth(),setDate( ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...