隨筆 - 44  文章 - 78  trackbacks - 0
          <2008年3月>
          2425262728291
          2345678
          9101112131415
          16171819202122
          23242526272829
          303112345

           Happy 牛 Year
          一、一周至少寫(xiě)一篇博文;
          二、每天至少學(xué)習(xí)半個(gè)小時(shí)。
          三、奔向小牛!

          常用鏈接

          留言簿(6)

          我參與的團(tuán)隊(duì)

          隨筆分類

          隨筆檔案

          文章檔案

          搜索

          •  

          最新評(píng)論

          閱讀排行榜

          評(píng)論排行榜

           

          節(jié)點(diǎn)的屬性

          使用 DOM 節(jié)點(diǎn)時(shí)需要一些屬性和方法,因此我們首先來(lái)討論節(jié)點(diǎn)的屬性和方法。DOM 節(jié)點(diǎn)的屬性主要有:

          • nodeName報(bào)告節(jié)點(diǎn)的名稱(詳見(jiàn)下述)。
          • nodeValue提供節(jié)點(diǎn)的(詳見(jiàn)后述)。
          • parentNode返回節(jié)點(diǎn)的父節(jié)點(diǎn)。記住,每個(gè)元素、屬性和文本都有一個(gè)父節(jié)點(diǎn)。
          • childNodes是節(jié)點(diǎn)的孩子節(jié)點(diǎn)列表。對(duì)于 HTML,該列表僅對(duì)元素有意義,文本節(jié)點(diǎn)和屬性節(jié)點(diǎn)都沒(méi)有孩子。
          • firstChild僅僅是childNodes列表中第一個(gè)節(jié)點(diǎn)的快捷方式。
          • lastChild是另一種快捷方式,表示childNodes列表中的最后一個(gè)節(jié)點(diǎn)。
          • previousSibling返回當(dāng)前節(jié)點(diǎn)之前的節(jié)點(diǎn)。換句話說(shuō),它返回當(dāng)前節(jié)點(diǎn)的父節(jié)點(diǎn)的childNodes列表中位于該節(jié)點(diǎn)前面的那個(gè)節(jié)點(diǎn)(如果感到迷惑,重新讀前面一句)。
          • nextSibling類似于previousSibling屬性,返回父節(jié)點(diǎn)的childNodes列表中的下一個(gè)節(jié)點(diǎn)。
          • attributes僅用于元素節(jié)點(diǎn),返回元素的屬性列表。

          其他少數(shù)幾種屬性實(shí)際上僅用于更一般的 XML 文檔,在處理基于 HTML 的網(wǎng)頁(yè)時(shí)沒(méi)有多少用處。

          不常用的屬性

          上述大部分屬性的意義都很明確,除了nodeNamenodeValue屬性以外。我們不是簡(jiǎn)單地解釋這兩個(gè)屬性,而是提出兩個(gè)奇怪的問(wèn)題:文本節(jié)點(diǎn)的nodeName應(yīng)該是什么?類似地,元素的nodeValue應(yīng)該是什么

          如果這些問(wèn)題難住了您,那么您就已經(jīng)了解了這些屬性固有的含糊性。nodeNamenodeValue實(shí)際上并非適用于所有節(jié)點(diǎn)類型(節(jié)點(diǎn)的其他少數(shù)幾個(gè)屬性也是如此)。這就說(shuō)明了一個(gè)重要概念:任何這些屬性都可能返回空值(有時(shí)候在 JavaScript 中稱為未定義)。比方說(shuō),文本節(jié)點(diǎn)的nodeName屬性是空值(或者在一些瀏覽器中稱為未定義),因?yàn)槲谋竟?jié)點(diǎn)沒(méi)有名稱。如您所料,nodeValue返回節(jié)點(diǎn)的文本。

          類似地,元素有nodeName,即元素名,但元素的nodeValue屬性值總是空。屬性同時(shí)具有nodeNamenodeValue。下一節(jié)我還將討論這些單獨(dú)的類型,但是因?yàn)檫@些屬性是每個(gè)節(jié)點(diǎn)的一部分,因此在這里有必要提一提。

          節(jié)點(diǎn)方法

          接下來(lái)看看所有節(jié)點(diǎn)都具有的方法(與節(jié)點(diǎn)屬性一樣,我省略了實(shí)際上不適用于多數(shù) HTML DOM 操作的少數(shù)方法):

          • insertBefore(newChild, referenceNode)newChild節(jié)點(diǎn)插入到referenceNode之前。記住,應(yīng)該對(duì)newChild的目標(biāo)父節(jié)點(diǎn)調(diào)用該方法。
          • replaceChild(newChild, oldChild)newChild節(jié)點(diǎn)替換oldChild節(jié)點(diǎn)。
          • removeChild(oldChild)從運(yùn)行該方法的節(jié)點(diǎn)中刪除oldChild節(jié)點(diǎn)。
          • appendChild(newChild)newChild添加到運(yùn)行該函數(shù)的節(jié)點(diǎn)之中。newChild被添加到目標(biāo)節(jié)點(diǎn)孩子列表中的末端
          • hasChildNodes()在調(diào)用該方法的節(jié)點(diǎn)有孩子時(shí)則返回 true,否則返回 false
          • hasAttributes()在調(diào)用該方法的節(jié)點(diǎn)有屬性時(shí)則返回 true,否則返回 false

          注意,大部分情況下所有這些方法處理的都是節(jié)點(diǎn)的孩子。這是它們的主要用途。如果僅僅想獲取文本節(jié)點(diǎn)值或者元素名,則不需要調(diào)用這些方法,使用節(jié)點(diǎn)屬性就可以了。

          通用節(jié)點(diǎn)類型

          現(xiàn)在已經(jīng)介紹了 DOM 節(jié)點(diǎn)的一些特性和屬性(以及一些奇特的地方),下面開(kāi)始講述您將用到的一些特殊節(jié)點(diǎn)類型。多數(shù) Web 應(yīng)用程序中只用到四種節(jié)點(diǎn)類型:

          • 文檔節(jié)點(diǎn)表示整個(gè) HTML 文檔。
          • 元素節(jié)點(diǎn)表示 HTML 元素,如aimg
          • 屬性節(jié)點(diǎn)表示 HTML 元素的屬性,如hrefa元素)或srcimg元素)。
          • 文本節(jié)點(diǎn)表示 HTML 文檔中的文本,如 “Click on the link below for a complete set list”。這是出現(xiàn)在pah2這些元素中的文字。

          處理 HTML 時(shí),95% 的時(shí)間是跟這些節(jié)點(diǎn)類型打交道。因此本文的其余部分將詳細(xì)討論這些節(jié)點(diǎn)。(將來(lái)討論 XML 的時(shí)候?qū)⒔榻B其他一些節(jié)點(diǎn)類型。)

          文檔節(jié)點(diǎn)

          基本上所有基于 DOM 的代碼中都要用到的第一個(gè)節(jié)點(diǎn)類型是文檔節(jié)點(diǎn)。文檔節(jié)點(diǎn)實(shí)際上并不是 HTML(或 XML)頁(yè)面中的一個(gè)元素而是頁(yè)面本身。因此在 HTML Web 頁(yè)面中,文檔節(jié)點(diǎn)就是整個(gè) DOM 樹(shù)。在 JavaScript 中,可以使用關(guān)鍵字document訪問(wèn)文檔節(jié)點(diǎn):

          // These first two lines get the DOM tree for the current Web page,

          //   and then the <html> element for that DOM tree

          var myDocument = document;

          var htmlElement = myDocument.documentElement;

          JavaScript 中的document關(guān)鍵字返回當(dāng)前網(wǎng)頁(yè)的 DOM 樹(shù)。從這里可以開(kāi)始處理樹(shù)中的所有節(jié)點(diǎn)。

          也可使用document對(duì)象創(chuàng)建新節(jié)點(diǎn),如下所示:

          • createElement(elementName)使用給定的名稱創(chuàng)建一個(gè)元素。
          • createTextNode(text)使用提供的文本創(chuàng)建一個(gè)新的文本節(jié)點(diǎn)。
          • createAttribute(attributeName)用提供的名稱創(chuàng)建一個(gè)新屬性。

          這里的關(guān)鍵在于這些方法創(chuàng)建節(jié)點(diǎn),但是并沒(méi)有將其附加或者插入到特定的文檔中。因此,必須使用前面所述的方法如insertBefore()appendChild()來(lái)完成這一步。因此,可使用下面的代碼創(chuàng)建新元素并將其添加到文檔中:

          var pElement = myDocument.createElement("p");

          var text = myDocument.createTextNode("Here's some text in a p element.");

          pElement.appendChild(text);

          bodyElement.appendChild(pElement);

          一旦使用document元素獲得對(duì) Web 頁(yè)面 DOM 樹(shù)的訪問(wèn),就可以直接使用元素、屬性和文本了。

          元素節(jié)點(diǎn)

          雖然會(huì)大量使用元素節(jié)點(diǎn),但很多需要對(duì)元素執(zhí)行的操作都是所有節(jié)點(diǎn)共有的方法和屬性,而不是元素特有的方法和屬性。元素只有兩組專有的方法:

          1. 與屬性處理有關(guān)的方法
            • getAttribute(name)返回名為name的屬性值。
            • removeAttribute(name)刪除名為name的屬性。
            • setAttribute(name, value)創(chuàng)建一個(gè)名為name的屬性并將其值設(shè)為value
            • getAttributeNode(name)返回名為name的屬性節(jié)點(diǎn)(屬性節(jié)點(diǎn)在 下一節(jié) 介紹)。
            • removeAttributeNode(node)刪除與指定節(jié)點(diǎn)匹配的屬性節(jié)點(diǎn)。
          2. 與查找嵌套元素有關(guān)的方法
            • getElementsByTagName(elementName)返回具有指定名稱的元素節(jié)點(diǎn)列表。

          這些方法意義都很清楚,但還是來(lái)看幾個(gè)例子吧。

          處理屬性

          處理元素很簡(jiǎn)單,比如可用document對(duì)象和上述方法創(chuàng)建一個(gè)新的img元素:

          var imgElement = document.createElement("img");

          imgElement.setAttribute("src", "http://www.headfirstlabs.com/Images/hraj_cover-150.jpg");

          imgElement.setAttribute("width", "130");

          imgElement.setAttribute("height", "150");

          bodyElement.appendChild(imgElement);

          現(xiàn)在看起來(lái)應(yīng)該非常簡(jiǎn)單了。實(shí)際上,只要理解了節(jié)點(diǎn)的概念并知道有哪些方法可用,就會(huì)發(fā)現(xiàn)在 Web 頁(yè)面和 JavaScript 代碼中處理 DOM 非常簡(jiǎn)單。在上述代碼中,JavaScript 創(chuàng)建了一個(gè)新的img元素,設(shè)置了一些屬性然后添加到 HTML 頁(yè)面的 body 元素中。

          查找嵌套元素

          發(fā)現(xiàn)嵌套的元素很容易。比如,下面的代碼用于發(fā)現(xiàn)和刪除 清單 3 所示 HTML 頁(yè)面中的所有img元素:

                // Remove all the top-level <img> elements in the body

                if (bodyElement.hasChildNodes()) {

                  for (i=0; i<bodyElement.childNodes.length; i++) {

                    var currentNode = bodyElement.childNodes[i];

                    if (currentNode.nodeName.toLowerCase() == "img") {

                      bodyElement.removeChild(currentNode);

                    }

                  }

                }

          也可以使用getElementsByTagName()完成類似的功能:

               

          // Remove all the top-level <img> elements in the body

                var imgElements = bodyElement.getElementsByTagName("img");

                for (i=0; i<imgElements.length; i++) {

                  var imgElement = imgElements.item[i];

                  bodyElement.removeChild(imgElement);

                }

          屬性節(jié)點(diǎn)

          DOM 將屬性表示成節(jié)點(diǎn),可以通過(guò)元素的attributes來(lái)訪問(wèn)元素的屬性,如下所示:

               

          // Remove all the top-level <img> elements in the body

                var imgElements = bodyElement.getElementsByTagName("img");

                for (i=0; i<imgElements.length; i++) {

                  var imgElement = imgElements.item[i];

                  // Print out some information about this element

                  var msg = "Found an img element!";

                  var atts = imgElement.attributes;

                  for (j=0; j<atts.length; j++) {

                    var att = atts.item(j);

                    msg = msg + ""n " + att.nodeName + ": '" + att.nodeValue + "'";

                  }

                  alert(msg);

                  bodyElement.removeChild(imgElement);

                }

          屬性的奇特之處

          對(duì)于 DOM 來(lái)說(shuō)屬性有一些特殊的地方。一方面,屬性實(shí)際上并不像其他元素或文本那樣是元素的孩子,換句話說(shuō),屬性并不出現(xiàn)在元素之下。同時(shí),屬性顯然和元素有一定的關(guān)系,元素擁有屬性。DOM 使用節(jié)點(diǎn)表示屬性,并允許通過(guò)元素的專門(mén)列表來(lái)訪問(wèn)屬性。因此屬性是 DOM 樹(shù)的一部分,但通常不出現(xiàn)在樹(shù)中。有理由說(shuō),屬性和 DOM 樹(shù)結(jié)構(gòu)其他部分之間的關(guān)系有點(diǎn)模糊。

          需要指出的是,attributes屬性實(shí)際上是對(duì)節(jié)點(diǎn)類型而非局限于元素類型來(lái)說(shuō)的。有點(diǎn)古怪,不影響您編寫(xiě)代碼,但是仍然有必要知道這一點(diǎn)。

          雖然也能使用屬性節(jié)點(diǎn),但通常使用元素類的方法處理屬性更簡(jiǎn)單。其中包括:

          • getAttribute(name)返回名為name的屬性值。
          • removeAttribute(name)刪除名為name的屬性。
          • setAttribute(name, value)創(chuàng)建一個(gè)名為name的屬性并將其值設(shè)為value

          這三個(gè)方法不需要直接處理屬性節(jié)點(diǎn)。但允許使用簡(jiǎn)單的字符串屬性設(shè)置和刪除屬性及其值。

          文本節(jié)點(diǎn)

          需要考慮的最后一種節(jié)點(diǎn)是文本節(jié)點(diǎn)(至少在處理 HTML DOM 樹(shù)的時(shí)候如此)。基本上通常用于處理文本節(jié)點(diǎn)的所有屬性都屬于節(jié)點(diǎn)對(duì)象。實(shí)際上,一般使用nodeValue屬性來(lái)訪問(wèn)文本節(jié)點(diǎn)的文本,如下所示:

          var pElements = bodyElement.getElementsByTagName("p");

          for (i=0; i<pElements.length; i++) {

           var pElement = pElements.item(i);

           var text = pElement.firstChild.nodeValue;

           alert(text);

          }

          少數(shù)其他幾種方法是專門(mén)用于文本節(jié)點(diǎn)的。這些方法用于增加或分解節(jié)點(diǎn)中的數(shù)據(jù):

          • appendData(text)將提供的文本追加到文本節(jié)點(diǎn)的已有內(nèi)容之后。
          • insertData(position, text)允許在文本節(jié)點(diǎn)的中間插入數(shù)據(jù)。在指定的位置插入提供的文本。
          • replaceData(position, length, text)從指定位置開(kāi)始刪除指定長(zhǎng)度的字符,用提供的文本代替刪除的文本。

          什么節(jié)點(diǎn)類型?

          到目前為止看到的多數(shù)代碼都假設(shè)已經(jīng)知道處理的節(jié)點(diǎn)是什么類型,但情況并非總是如此。比方說(shuō),如果在 DOM 樹(shù)中導(dǎo)航并處理一般的節(jié)點(diǎn)類型,可能就不知道您遇到了元素還是文本。也許獲得了p元素的所有孩子,但是不能確定處理的是文本、b元素還是img元素。這種情況下,在進(jìn)一步的處理之前需要確定是什么類型的節(jié)點(diǎn)。

          所幸的是很容易就能做到。DOM 節(jié)點(diǎn)類型定義了一些常量,比如:

          1. Node.ELEMENT_NODE是表示元素節(jié)點(diǎn)類型的常量。
          2. Node.ATTRIBUTE_NODE是表示屬性節(jié)點(diǎn)類型的常量。
          3. Node.TEXT_NODE是表示文本節(jié)點(diǎn)類型的常量。
          4. Node.DOCUMENT_NODE是表示文檔節(jié)點(diǎn)類型的常量。

          還有其他一些節(jié)點(diǎn)類型,但是對(duì)于 HTML 除了這四種以外很少用到。我有意沒(méi)有給出這些常量的值,雖然 DOM 規(guī)范中定義了這些值,永遠(yuǎn)不要直接使用那些值,因?yàn)檫@正是常量的目的!

          nodeType 屬性

          可使用nodeType屬性比較節(jié)點(diǎn)和上述常量 —— 該屬性定義在 DOM node 類型上因此可用于所有節(jié)點(diǎn),如下所示:

          var someNode = document.documentElement.firstChild;

          if (someNode.nodeType == Node.ELEMENT_NODE) {

           alert("We've found an element node named " + someNode.nodeName);

          } else if (someNode.nodeType == Node.TEXT_NODE) {

           alert("It's a text node; the text is " + someNode.nodeValue);

          } else if (someNode.nodeType == Node.ATTRIBUTE_NODE) {

           alert("It's an attribute named " + someNode.nodeName

                                  + " with a value of '" + someNode.nodeValue + "'");

          }

          這個(gè)例子非常簡(jiǎn)單,但說(shuō)明了一個(gè)大問(wèn)題:得到節(jié)點(diǎn)的類型非常簡(jiǎn)單。更有挑戰(zhàn)性的是知道節(jié)點(diǎn)的類型之后確定能做什么,只要掌握了節(jié)點(diǎn)、文本、屬性和元素類型提供了什么屬性和方法,就可以自己進(jìn)行 DOM 編程了。

          實(shí)踐中的挫折

          nodeType屬性似乎是使用節(jié)點(diǎn)的一個(gè)入場(chǎng)卷 —— 允許確定要處理的節(jié)點(diǎn)類型然后編寫(xiě)處理該節(jié)點(diǎn)的代碼。問(wèn)題在于上述Node常量定義不能正確地用于 Internet Explorer。因此如果在代碼中使用Node.ELEMENT_NODENode.TEXT_NODE或其他任何常量,Internet Explorer 都將返回如 4 所示的錯(cuò)誤。


          4. Internet Explorer 報(bào)告錯(cuò)誤

          任何時(shí)候在 JavaScript 中使用Node常量,Internet Explorer 都會(huì)報(bào)錯(cuò)。因?yàn)槎鄶?shù)人仍然在使用 Internet Explorer,應(yīng)該避免在代碼中使用Node.ELEMENT_NODENode.TEXT_NODE這樣的構(gòu)造。盡管據(jù)說(shuō)即將發(fā)布的新版本 Internet Explorer 7.0 將解決這個(gè)問(wèn)題,但是在 Internet Explorer 6.x 退出舞臺(tái)之前仍然要很多年。因此應(yīng)避免使用Node,要想讓您的 DOM 代碼(和 Ajax 應(yīng)用程序)能用于所有主要瀏覽器,這一點(diǎn)很重要。


          摘自:http://www.ibm.com/developerworks/cn/xml/wa-ajaxintro5/?S_TACT=105AGX52&S_CMP=techcsdn

          posted on 2008-03-11 11:32 Tiger1102 閱讀(1855) 評(píng)論(0)  編輯  收藏 所屬分類: 每日進(jìn)階
          主站蜘蛛池模板: 贵南县| 上思县| 新蔡县| 昌吉市| 紫云| 凉城县| 钟山县| 柯坪县| 磐石市| 澄迈县| 修文县| 涟源市| 彭阳县| 区。| 瑞金市| 休宁县| 克山县| 南通市| 卓资县| 个旧市| 望城县| 元氏县| 嵩明县| 恩施市| 山西省| 资中县| 耒阳市| 朝阳市| 略阳县| 河津市| 习水县| 曲周县| 长汀县| 汕尾市| 古浪县| 通化市| 海城市| 通辽市| 枞阳县| 托克托县| 青岛市|