JavaScript操作DOM的知識總結(jié)

基本概念

在講解操作DOM的api之前翔怎,首先我們來復(fù)習(xí)一下一些基本概念窃诉,這些概念是掌握api的關(guān)鍵,必須理解它們赤套。

Node類型

DOM1級定義了一個Node接口飘痛,該接口由DOM中所有節(jié)點(diǎn)類型實(shí)現(xiàn)。這個Node接口在JS中是作為Node類型實(shí)現(xiàn)的容握。在IE9以下版本無法訪問到這個類型宣脉,JS中所有節(jié)點(diǎn)都繼承自Node類型,都共享著相同的基本屬性和方法唯沮。
Node有一個屬性nodeType表示Node的類型脖旱,它是一個整數(shù),其數(shù)值分別表示相應(yīng)的Node類型介蛉,常見的如下:

常量 描述
Node.ELEMENT_NODE 1 一個 元素 節(jié)點(diǎn)萌庆,例如 <p><div>
Node.TEXT_NODE 3 Element 或者 Attr 中實(shí)際的 文字
Node.PROCESSING_INSTRUCTION_NODE 7 一個用于XML文檔的 ProcessingInstruction 币旧,例如 <?xml-stylesheet ... ?> 聲明践险。
Node.COMMENT_NODE 8 一個 Comment 節(jié)點(diǎn)。
Node.DOCUMENT_NODE 9 一個 Document 節(jié)點(diǎn)吹菱。

假設(shè)我們要判斷一個Node是不是元素巍虫,我們可以這樣判斷

if(someNode.nodeType == 1){
console.log("Node is a element");
}

這些Node類型中,我們最常用的就是element鳍刷,text占遥,attribute,comment输瓜,document瓦胎,document_fragment這幾種類型芬萍。
需要注意的就是:HTML中的節(jié)點(diǎn)并不只是包括元素節(jié)點(diǎn),它還包括文本節(jié)點(diǎn)搔啊,注釋節(jié)點(diǎn)等等

創(chuàng)建節(jié)點(diǎn)的常用api

  • createElement
    createElement通過傳入指定的一個標(biāo)簽名來創(chuàng)建一個元素柬祠,如果傳入的標(biāo)簽名是一個未知的,則會創(chuàng)建一個自定義的標(biāo)簽负芋,注意:IE8以下瀏覽器不支持自定義標(biāo)簽漫蛔。
    使用如下:
var div = document.createElement("div");

使用createElement要注意:通過createElement創(chuàng)建的元素并不屬于html文檔,它只是創(chuàng)建出來旧蛾,并未添加到html文檔中莽龟,要調(diào)用appendChild或insertBefore等方法將其添加到HTML文檔樹中。

頁面修改型常用API

  • appendChild
    appendChild我們在前面已經(jīng)提到蚜点,就是將指定的節(jié)點(diǎn)添加到調(diào)用該方法的節(jié)點(diǎn)的子元素的末尾轧房。調(diào)用方法如下:
parent.appendChild(child);

child節(jié)點(diǎn)將會作為parent節(jié)點(diǎn)的最后一個子節(jié)點(diǎn)。
appendChild這個方法很簡單绍绘,但是還有有一點(diǎn)需要注意:如果被添加的節(jié)點(diǎn)是一個頁面中存在的節(jié)點(diǎn)奶镶,則執(zhí)行后這個節(jié)點(diǎn)將會添加到指定位置,其原本所在的位置將移除該節(jié)點(diǎn)陪拘,也就是說不會同時存在兩個該節(jié)點(diǎn)在頁面上厂镇,相當(dāng)于把這個節(jié)點(diǎn)移動到另一個地方。
需要注意的是:如果child綁定了事件左刽,被移動時捺信,它依然綁定著該事件。

  • removeChild
    removeChild顧名思義欠痴,就是刪除指定的子節(jié)點(diǎn)并返回迄靠,用法如下:
var deletedChild = parent.removeChild(node);

deletedChild指向被刪除節(jié)點(diǎn)的引用,它等于node喇辽,被刪除的節(jié)點(diǎn)仍然存在于內(nèi)存中掌挚,可以對其進(jìn)行下一步操作。
注意:如果被刪除的節(jié)點(diǎn)不是其子節(jié)點(diǎn)菩咨,則程序?qū)?bào)錯吠式。我們可以通過下面的方式來確保可以刪除:

if(node.parentNode){
    node.parentNode.removeChild(node);
}

通過節(jié)點(diǎn)自己獲取節(jié)點(diǎn)的父節(jié)點(diǎn)抽米,然后將自身刪除特占。

  • replaceChild
    replaceChild用于使用一個節(jié)點(diǎn)替換另一個節(jié)點(diǎn),用法如下
parent.replaceChild(newChild,oldChild);

newChild是替換的節(jié)點(diǎn)云茸,可以是新的節(jié)點(diǎn)是目,也可以是頁面上的節(jié)點(diǎn),如果是頁面上的節(jié)點(diǎn)标捺,則其將被轉(zhuǎn)移到新的位置懊纳,oldChild是被替換的節(jié)點(diǎn)网持。
頁面修改型api要注意幾個特點(diǎn):
(1)不管是新增還是替換節(jié)點(diǎn),如果新增或替換的節(jié)點(diǎn)是原本存在頁面上的长踊,則其原來位置的節(jié)點(diǎn)將被移除,也就是說同一個節(jié)點(diǎn)不能存在于頁面的多個位置
(2)節(jié)點(diǎn)本身綁定的事件會不會消失萍倡,會一直保留著身弊。

節(jié)點(diǎn)查詢型API

節(jié)點(diǎn)查詢型API也是非常常用的api,下面我們分別說明一下每一個api的使用列敲。

  • document.getElementById
    這個接口很簡單阱佛,根據(jù)元素id返回元素,返回值是Element類型戴而,如果不存在該元素凑术,則返回null。
    使用這個接口有幾點(diǎn)要注意:
    (1)元素的Id是大小寫敏感的所意,一定要寫對元素的id
    (2)HTML文檔中可能存在多個id相同的元素淮逊,則返回第一個元素

  • document.getElementsByTagName
    這個接口根據(jù)元素標(biāo)簽名獲取元素,返回一個即時的HTMLCollection類型

  • document.getElementsByClassName
    這個API是根據(jù)元素的class返回一個即時的HTMLCollection扶踊,用法如下

var elements = document.getElementsByClassName(names);

這個接口有下面幾點(diǎn)要注意:
(1)返回結(jié)果是一個即時的HTMLCollection泄鹏,會隨時根據(jù)文檔結(jié)構(gòu)變化
(2)IE9以下瀏覽器不支持
(3)如果要獲取2個以上classname,可傳入多個classname秧耗,每個用空格相隔备籽,例如

var elements = document.getElementsByClassName("test1 test2");
  • document.querySelector和document.querySelectorAll

這兩個api很相似,通過css選擇器來查找元素分井,注意選擇器要符合CSS選擇器的規(guī)則车猬。
(1)document.querySelector返回第一個匹配的元素,如果沒有匹配的元素尺锚,則返回null珠闰。
(2)document.querySelectorAll的不同之處在于它返回的是所有匹配的元素,而且可以匹配多個選擇符

兼容性問題:querySelector和querySelectorAll在ie8以下的瀏覽器不支持缩麸。

節(jié)點(diǎn)關(guān)系型api

在html文檔中的每個節(jié)點(diǎn)之間的關(guān)系都可以看成是家譜關(guān)系铸磅,包含父子關(guān)系,兄弟關(guān)系等等杭朱,下面我們依次來看看每一種關(guān)系阅仔。

  • 父關(guān)系型api
  1. parentNode:每個節(jié)點(diǎn)都有一個parentNode屬性,它表示元素的父節(jié)點(diǎn)弧械。Element的父節(jié)點(diǎn)可能是Element八酒,Document或DocumentFragment。
  2. parentElement:返回元素的父元素節(jié)點(diǎn)刃唐,與parentNode的區(qū)別在于羞迷,其父節(jié)點(diǎn)必須是一個Element界轩,如果不是,則返回null
  • 兄弟關(guān)系型api
  1. previousSibling:節(jié)點(diǎn)的前一個節(jié)點(diǎn)衔瓮,如果該節(jié)點(diǎn)是第一個節(jié)點(diǎn)浊猾,則為null。注意有可能拿到的節(jié)點(diǎn)是文本節(jié)點(diǎn)或注釋節(jié)點(diǎn)热鞍,與預(yù)期的不符葫慎,要進(jìn)行處理一下。

  2. previousElementSibling:返回前一個元素節(jié)點(diǎn)薇宠,前一個節(jié)點(diǎn)必須是Element偷办,注意IE9以下瀏覽器不支持。

  3. nextSibling:節(jié)點(diǎn)的后一個節(jié)點(diǎn)澄港,如果該節(jié)點(diǎn)是最后一個節(jié)點(diǎn)椒涯,則為null。注意有可能拿到的節(jié)點(diǎn)是文本節(jié)點(diǎn)回梧,與預(yù)期的不符废岂,要進(jìn)行處理一下。

  4. nextElementSibling:返回后一個元素節(jié)點(diǎn)漂辐,后一個節(jié)點(diǎn)必須是Element泪喊,注意IE9以下瀏覽器不支持。

  • 子關(guān)系型api
  1. childNodes:返回一個即時的NodeList髓涯,表示元素的子節(jié)點(diǎn)列表袒啼,子節(jié)點(diǎn)可能會包含文本節(jié)點(diǎn),注釋節(jié)點(diǎn)等纬纪。
  2. children:一個即時的HTMLCollection蚓再,子節(jié)點(diǎn)都是Element,IE9以下瀏覽器不支持包各。
  3. firstNode:第一個子節(jié)點(diǎn)
  4. lastNode:最后一個子節(jié)點(diǎn)
  5. hasChildNodes方法:可以用來判斷是否包含子節(jié)點(diǎn)摘仅。

元素屬性型api

  1. setAttribute
    根據(jù)名稱和值修改元素的特性,用法如下问畅。
element.setAttribute(name, value);

其中name是特性名娃属,value是特性值。如果元素不包含該特性护姆,則會創(chuàng)建該特性并賦值矾端。
如果元素本身包含指定的特性名為屬性,則可以訪問屬性進(jìn)行賦值卵皂,比如下面兩條代碼是等價(jià)的:

element.setAttribute("id","test");

element.id = "test";
  1. getAttribute
    返回指定的特性名相應(yīng)的特性值秩铆,如果不存在,則返回null或空字符串。用法如下:
var value = element.getAttribute("id");

總結(jié)

本文主要總結(jié)了原生js中常用的操作DOM的api接口殴玛,主要為了復(fù)習(xí)基礎(chǔ)知識捅膘。平時開發(fā)用多了jQuery等類庫,對基礎(chǔ)知識的了解可能就漸漸地遺忘滚粟,但這些基礎(chǔ)知識才是我們立足的根本寻仗,只有掌握原生的js,才能真正做好js的開發(fā)凡壤。

參考資料:
1.Javascript操作DOM常用API總結(jié)
2.MDN文檔

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末弦赖,一起剝皮案震驚了整個濱河市褪那,隨后出現(xiàn)的幾起案子叹放,更是在濱河造成了極大的恐慌渴杆,老刑警劉巖林艘,帶你破解...
    沈念sama閱讀 216,692評論 6 501
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件盖奈,死亡現(xiàn)場離奇詭異,居然都是意外死亡狐援,警方通過查閱死者的電腦和手機(jī)钢坦,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,482評論 3 392
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來啥酱,“玉大人爹凹,你說我怎么就攤上這事∠庖螅” “怎么了禾酱?”我有些...
    開封第一講書人閱讀 162,995評論 0 353
  • 文/不壞的土叔 我叫張陵,是天一觀的道長绘趋。 經(jīng)常有香客問我颤陶,道長,這世上最難降的妖魔是什么陷遮? 我笑而不...
    開封第一講書人閱讀 58,223評論 1 292
  • 正文 為了忘掉前任滓走,我火速辦了婚禮,結(jié)果婚禮上帽馋,老公的妹妹穿的比我還像新娘搅方。我一直安慰自己,他們只是感情好绽族,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,245評論 6 388
  • 文/花漫 我一把揭開白布姨涡。 她就那樣靜靜地躺著,像睡著了一般项秉。 火紅的嫁衣襯著肌膚如雪绣溜。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 51,208評論 1 299
  • 那天娄蔼,我揣著相機(jī)與錄音怖喻,去河邊找鬼底哗。 笑死,一個胖子當(dāng)著我的面吹牛锚沸,可吹牛的內(nèi)容都是我干的跋选。 我是一名探鬼主播,決...
    沈念sama閱讀 40,091評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼哗蜈,長吁一口氣:“原來是場噩夢啊……” “哼前标!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起距潘,我...
    開封第一講書人閱讀 38,929評論 0 274
  • 序言:老撾萬榮一對情侶失蹤炼列,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后音比,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體俭尖,經(jīng)...
    沈念sama閱讀 45,346評論 1 311
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,570評論 2 333
  • 正文 我和宋清朗相戀三年洞翩,在試婚紗的時候發(fā)現(xiàn)自己被綠了稽犁。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 39,739評論 1 348
  • 序言:一個原本活蹦亂跳的男人離奇死亡骚亿,死狀恐怖已亥,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情来屠,我是刑警寧澤虑椎,帶...
    沈念sama閱讀 35,437評論 5 344
  • 正文 年R本政府宣布,位于F島的核電站俱笛,受9級特大地震影響绣檬,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜嫂粟,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,037評論 3 326
  • 文/蒙蒙 一娇未、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧星虹,春花似錦零抬、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,677評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至卸亮,卻和暖如春忽妒,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 32,833評論 1 269
  • 我被黑心中介騙來泰國打工段直, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留吃溅,地道東北人。 一個月前我還...
    沈念sama閱讀 47,760評論 2 369
  • 正文 我出身青樓鸯檬,卻偏偏與公主長得像决侈,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子喧务,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,647評論 2 354