新葡亰496net Web前端 从原型链看DOM--Element类型

从原型链看DOM--Element类型



返本求源——DOM元素的表征与性格

2015/09/06 · HTML5,
JavaScript ·
DOM

原稿出处: 木的树   

投石问路

非常多前端类库(举个例子dojo与JQuery)在论及dom操作时都会见到多个模块:attr、prop。某天代码复查时,看见意气风发段为某节点设置文本的代码:

JavaScript

attr.set(node, ‘innerText’, ‘Hello World!’)

1
attr.set(node, ‘innerText’, ‘Hello World!’)

这段代码实践后并未有生效,虽说innerText不是业内属性,尚未被ff扶助,可用的是chrome,那个个性是被支持的。既然呈现的文本没变,那就翻开一下成分呢。
新葡亰496net 1

innerText被加多到了html标签上,而换到prop模块后,成功的为节点替换文本。

以上的那么些小案例就涉嫌到了DOM操作时常常被忽略的叁个难点:性情与质量的界别

返本求源

在DOM中,性格指的是html标签上的脾气,例如:

新葡亰496net 2

新葡亰496net,Property是对此某风华正茂项目特征的叙说。能够这么掌握,在DOM成分中能够因而点语法访谈,又不是行业内部性子的都能够成为属性。

DOM中保有的节点都贯彻了Node接口。Node接口是在DOM1级中定义的,当中定义了有个别用来说述DOM节点的习性和操作方法。

新葡亰496net 3

周围的nodeType、nodeValue、节点关系(parentNode、childNodes、firstChild、lastChild、previousSibling、nextSibling等)都归属Node接口定义的性质。对于Node接口的切切实实落到实处者,HTMLElement不仅仅世袭了这一个属性,还应该有所三个wac标准中的多少个正规性格:id、title、lang、dir、class和八特性能:attributes。

每一个成分都有叁个或三个特点,这一个特征的用处是付诸相应成分或其内容的增大消息。通过DOM成分间接操作性子的的方法有四个:

  • getAttribute(attrName)
  • setAttribute(attrName, value)
  • removeAttribute(name)

那多个情势都足以操作自定义天性。不过唯有公众感到的(非自定义)性子才会以属性的样式充裕到DOM对象中,以属性方式操作那些特征会被同步到html标签中。HTMLElement的三个特性都有照管属性与其对待:id、title、lang、dir、className。在DOM中以属性形式操作那些特征会协同到html标签中。

但是,HTML5标准对自定义天性做了升高,只要自定义特性以”data-attrName”的款式写入到html标签中,在DOM属性中就可以通过element.dataset.attrName的样式来访问自定义特性,如:

XHTML

<input type=​”text” name=​”as_q” class=​”box”
id=​”searched_content” title=​”在那输入搜索内容。” disabled=​”false”
data-ff=​”fsdf”>​ seh.dataset.ff

1
2
<input type=​"text" name=​"as_q" class=​"box" id=​"searched_content" title=​"在此输入搜索内容。" disabled=​"false" data-ff=​"fsdf">​
seh.dataset.ff

要素的性状在DOM中以Attr类型来代表,Attr类型也落到实处了Node接口。Attr对象有多个性情:name、value、specified。在那之中,name是特色的称号,value是特点值,specified是三个布尔值,用来提醒该个性是或不是被刚强设置。

document.createAttribute方法能够用来创立性子节点。例如,要为成分增添align天性可以选用如下方法:

JavaScript

ar attr = document.createAttribute(‘align’) attr.value = ‘left’
seh.setAttributeNode(attr)

1
2
3
ar attr = document.createAttribute(‘align’)
attr.value = ‘left’
seh.setAttributeNode(attr)

要将新创造的性状增添到成分上,必需采取要素的setAttributeNode方法。加多性格后,特性会反映在html标签上:

新葡亰496net 4

瞩目,就算性剧情点也落到实处了Node接口,但天性却不被感到是DOM文书档案树的一片段。

新葡亰,在全数的DOM节点中attributes属性是Element类型所唯有的的性质。从本领角度来讲,天性就是存在于成分的attributes属性中的节点。attributes属性归于NamedNodeMap类型的实例。成分的每壹本性剧情点都保存在NamedNodeMap对象中。NamedNodeMap类型拥好似下方法:

  • 澳门葡亰娱乐场手机版,getNamedItem(name卡塔尔(قطر‎:重回天性名叫name的性剧情点
  • removeNamedItem(name卡塔尔:删除天性名称为name的表征节点
  • setNamedItem(attr卡塔尔国:像成分中加多贰个特色节点
  • item(pos卡塔尔:再次来到坐落于数组pos处的节点

赢得、设置、删除成分节点能够如下方式:

JavaScript

element.attributes.getNamedItem(‘align’) //获取 var attr =
document.createAttribute(‘align’); attr.value = ‘right’;
element.attributes.setNamedItem(attr); //添加
element.attributes.removeNamedItem(‘align’); //删除

1
2
3
4
5
6
7
element.attributes.getNamedItem(‘align’) //获取
 
var attr = document.createAttribute(‘align’);
attr.value = ‘right’;
element.attributes.setNamedItem(attr); //添加
 
element.attributes.removeNamedItem(‘align’); //删除

事实上应用中并不提议使用天性节点的方式,而getAttribute、setAttribute、removeAttribute方法远比操作特性节点更方便。

DOM、attributes、Attr三者关系应该如此画:

新葡亰496net 5

选拔计算

基于以上DOM基本功知识和事实上中国人民解放军海军工程高校业作资历,小编将特色和总体性的区分联系总计如下:

  1. 品质以致公众承认性情能够通过点语法访谈;html5正式中,data-*花样的自定义天性可以通过element.dataset.*的样式来访谈,不然用getAttribute
  2. 特点值只可以是字符串,而属性值能够是大肆JavaScript协理的品类
  3. 多少个卓绝性状:
    1. style,通过getAttrbute和setAttribute来操作这么些性子只可以得到或设置字符串;而已属性格局来操作就是在操作CSSStyleDeclaration对象
    2. 事件管理程序,通过特色方式获得和传递的都只是函数字符串;而已属性格局操作的是函数对象
    3. value,对于支撑value的元素,最佳通过质量情势操作,並且操作不会反映在html标签上
    XHTML

    seh.value = 10 &lt;input type="text" name="as_q" class="box"
    id="searched_content" title="在此输入搜索内容。"
    disabled="false" data-ff="fsdf" align="left"&gt;

    <table>
    <colgroup>
    <col style="width: 50%" />
    <col style="width: 50%" />
    </colgroup>
    <tbody>
    <tr class="odd">
    <td><div class="crayon-nums-content" style="font-size: 13px !important; line-height: 15px !important;">
    <div class="crayon-num" data-line="crayon-5b8f379c97d12396477911-1">
    1
    </div>
    <div class="crayon-num crayon-striped-num" data-line="crayon-5b8f379c97d12396477911-2">
    2
    </div>
    </div></td>
    <td><div class="crayon-pre" style="font-size: 13px !important; line-height: 15px !important; -moz-tab-size:4; -o-tab-size:4; -webkit-tab-size:4; tab-size:4;">
    <div id="crayon-5b8f379c97d12396477911-1" class="crayon-line">
    seh.value = 10
    </div>
    <div id="crayon-5b8f379c97d12396477911-2" class="crayon-line crayon-striped-line">
    &lt;input type=&quot;text&quot; name=&quot;as_q&quot; class=&quot;box&quot; id=&quot;searched_content&quot; title=&quot;在此输入搜索内容。&quot; disabled=&quot;false&quot; data-ff=&quot;fsdf&quot; align=&quot;left&quot;&gt;
    </div>
    </div></td>
    </tr>
    </tbody>
    </table>

4.  href,通过属性方式设置可以反映到html标签上,但用过点语法和getAttribute能够取到的值并不一定相同


    XHTML

    &lt;a href="/jsref/prop_checkbox_tabindex.asp"
    id="tabI"&gt;tabIndex&lt;/a&gt; link.getAttribute('href') //
    "/jsref/prop_checkbox_tabindex.asp" link.href //
    "http://www.w3school.com.cn/jsref/prop_checkbox_tabindex.asp"

    <table>
    <colgroup>
    <col style="width: 50%" />
    <col style="width: 50%" />
    </colgroup>
    <tbody>
    <tr class="odd">
    <td><div class="crayon-nums-content" style="font-size: 13px !important; line-height: 15px !important;">
    <div class="crayon-num" data-line="crayon-5b8f379c97d15903857159-1">
    1
    </div>
    <div class="crayon-num crayon-striped-num" data-line="crayon-5b8f379c97d15903857159-2">
    2
    </div>
    <div class="crayon-num" data-line="crayon-5b8f379c97d15903857159-3">
    3
    </div>
    <div class="crayon-num crayon-striped-num" data-line="crayon-5b8f379c97d15903857159-4">
    4
    </div>
    <div class="crayon-num" data-line="crayon-5b8f379c97d15903857159-5">
    5
    </div>
    </div></td>
    <td><div class="crayon-pre" style="font-size: 13px !important; line-height: 15px !important; -moz-tab-size:4; -o-tab-size:4; -webkit-tab-size:4; tab-size:4;">
    <div id="crayon-5b8f379c97d15903857159-1" class="crayon-line">
    &lt;a href=&quot;/jsref/prop_checkbox_tabindex.asp&quot; id=&quot;tabI&quot;&gt;tabIndex&lt;/a&gt;
    </div>
    <div id="crayon-5b8f379c97d15903857159-2" class="crayon-line crayon-striped-line">
     
    </div>
    <div id="crayon-5b8f379c97d15903857159-3" class="crayon-line">
    link.getAttribute('href') // &quot;/jsref/prop_checkbox_tabindex.asp&quot;
    </div>
    <div id="crayon-5b8f379c97d15903857159-4" class="crayon-line crayon-striped-line">
     
    </div>
    <div id="crayon-5b8f379c97d15903857159-5" class="crayon-line">
    link.href // &quot;http://www.w3school.com.cn/jsref/prop_checkbox_tabindex.asp&quot;
    </div>
    </div></td>
    </tr>
    </tbody>
    </table>

5.  disabled和checked,对于支持这两个特性的元素来说,他们在html标签中都是无状态的,只要有独立的标签属性在以点语法访问时就返回true,如果html标签属性不存在,则以点语法访问时就是false


    XHTML

    &lt;input type=​"text" name=​"as_q" class=​"box"
    id=​"searched_content" title=​"在此输入搜索内容。"
    disabled=​"false" data-ff=​"fsdf" align=​"left"&gt;​
    seh.disabled // true seh.disabled = false &lt;input type=​"text"
    name=​"as_q" class=​"box" id=​"searched_content"
    title=​"在此输入搜索内容。" data-ff=​"fsdf" align=​"left"&gt;​

    <table>
    <colgroup>
    <col style="width: 50%" />
    <col style="width: 50%" />
    </colgroup>
    <tbody>
    <tr class="odd">
    <td><div class="crayon-nums-content" style="font-size: 13px !important; line-height: 15px !important;">
    <div class="crayon-num" data-line="crayon-5b8f379c97d19172676562-1">
    1
    </div>
    <div class="crayon-num crayon-striped-num" data-line="crayon-5b8f379c97d19172676562-2">
    2
    </div>
    <div class="crayon-num" data-line="crayon-5b8f379c97d19172676562-3">
    3
    </div>
    <div class="crayon-num crayon-striped-num" data-line="crayon-5b8f379c97d19172676562-4">
    4
    </div>
    <div class="crayon-num" data-line="crayon-5b8f379c97d19172676562-5">
    5
    </div>
    <div class="crayon-num crayon-striped-num" data-line="crayon-5b8f379c97d19172676562-6">
    6
    </div>
    </div></td>
    <td><div class="crayon-pre" style="font-size: 13px !important; line-height: 15px !important; -moz-tab-size:4; -o-tab-size:4; -webkit-tab-size:4; tab-size:4;">
    <div id="crayon-5b8f379c97d19172676562-1" class="crayon-line">
    &lt;input type=​&quot;text&quot; name=​&quot;as_q&quot; class=​&quot;box&quot; id=​&quot;searched_content&quot; title=​&quot;在此输入搜索内容。&quot; disabled=​&quot;false&quot; data-ff=​&quot;fsdf&quot; align=​&quot;left&quot;&gt;​
    </div>
    <div id="crayon-5b8f379c97d19172676562-2" class="crayon-line crayon-striped-line">
     
    </div>
    <div id="crayon-5b8f379c97d19172676562-3" class="crayon-line">
    seh.disabled // true
    </div>
    <div id="crayon-5b8f379c97d19172676562-4" class="crayon-line crayon-striped-line">
     
    </div>
    <div id="crayon-5b8f379c97d19172676562-5" class="crayon-line">
    seh.disabled = false
    </div>
    <div id="crayon-5b8f379c97d19172676562-6" class="crayon-line crayon-striped-line">
    &lt;input type=​&quot;text&quot; name=​&quot;as_q&quot; class=​&quot;box&quot; id=​&quot;searched_content&quot; title=​&quot;在此输入搜索内容。&quot; data-ff=​&quot;fsdf&quot; align=​&quot;left&quot;&gt;​
    </div>
    </div></td>
    </tr>
    </tbody>
    </table>

1 赞 1 收藏
评论

新葡亰496net 6

在急需将DOM构造序列化为XML或HTML字符串时,多数都会波及遍历成分脾性。以下代码浮现了什么迭代成分的每一个特色然后将它们组织成name=”value”那样的键值对方式

<div id="myID" class="bd" title="body" lang="en" dir="ltr">...</div>

(1卡塔尔(قطر‎.getNamedItem(nameState of Qatar:重返nodeName属性等于name的特色节点。

  • setAttribute(‘attr’,’value’)
  • getAttribute(‘attr’)
  • removeAttribute(‘attr’)

安装特色的值:先获得性情节点然后将其nodeValue设置为新值。
当你设置document.body.id=”test”时候JS引擎内部恐怕成功了之类操作

document.body.id="newid";

transAttr(document.body,'id');
function transAttr(ele,id){
var attrMap=ele.attributes;
for(var i in attrMap){
  if(attrMap.hasOwnProperty(i)){
        if(attrMap[i].nodeName=='id'){
             attrMap[i].nodeValue=ele.id;
       }
    }
 }
 delete document.body.id;
}

attributes属性

新葡亰496net 7

要素的childNodes属性(世袭自Node.prototype)满含了它全部子节点,那一个子节点只怕是因素,文本节点,注释,管理指令。差别浏览器在对待那几个节点方面存在区别。

在新成分上设置这个特色只是给它们授予了对应新闻,由于新因素还未有被增多到文书档案树中,由此设置那个特点不会耳闻则诵浏览器展现。要把新因素增多到文书档案树中,可使用appendChild(卡塔尔(قطر‎,insertBefore(State of Qatar,replaceChild(卡塔尔(قطر‎均三回九转自Node.prototype。大器晚成旦将成分加多到文书档案树,浏览器就能即时表现该因素。从此对这些成分所做的其它改进都会实时反映在浏览器中。
在<=IE第88中学以另生机勃勃种艺术接受createElement,即为这几个艺术传入完整的因素标签也能够蕴含属性,document.createElement(‘<div
id=”test”></div>’卡塔尔 。这种措施推进避开在IE7及更早版本中动态创立成分(document.createElement(‘div’State of Qatar然后插入叫动态创制)的某个难点,以前存在以下那几个主题材料:

ele.style.cssText:证明块的文本内容,改过这几个性子会平素将标签中的style性格内容更改。
ele.style.length:属性的多寡即有具体值的css申明的数据。window.getComputedStyle(State of Qatar再次回到值为262。
ele.style.parentRule:包含的CSSRule;
ele.style.getPropertyPriority(‘attr’卡塔尔(قطر‎:再次来到可选的初期级
ele.style.getPropertyValue(‘attr’卡塔尔国:重返属性值
ele.style.item(idxState of Qatar:再次回到属性名,有现实的值的归来属性名,未有具体值的归来””
ele.style.removeProperty(卡塔尔国:删除的习性,会平昔反映到HTML文书档案桐月素style个性节点。再次来到””
ele.style.setProperty(‘attr’,’value’,’priority’卡塔尔:设置属性,eg: document.body.style.setProperty(‘color’,’red’,’important’State of Qatar 
(b卡塔尔国.on事件性质:以onclick为例,在要素上行使时,onclick性子中蕴藏的是JavaScript代码,但通过getAttribute(卡塔尔(قطر‎访谈归来相应代码的字符串。在会见onclick属性时会重临四个JavaScript函数(当onclick属性上空头支票函数对象且未在要素标签中钦定相应特性(为何说不是性质是因为豆蔻梢头旦在ele上尚无找到onclick属性那就去标签中找onclick个性值卡塔尔(قطر‎再次回到null)。由于存在此些出入,在通过JavaScript以编程方式操作DOM时提议利用onclick属性值,独有在拿到自定义特性值的状态下才通过getAttribute(State of Qatar访谈。
当八个成分标签中既有onclick天性,同有的时候候给ele.onclick钦定函数(那操作并不会耳濡目染原来标签中onclick性格的值),则最后只实行ele.onclick属性的函数。
新葡亰496net 8
况且经过getAttribute访谈仍赢得的是标签上的特色值,且纵然在此以前已经给onclick属性赋值了但调整台显示成分自己并不曾这几个脾性。作者不了然怎么document.body自己上会未有onclick属性,那当访谈document.body.onclick时候去哪访谈onclick的值,按着原型链吗?假设函数是在原型链上的onclick属性上也不应该啊HTMLElement.prototype.onclick=function(卡塔尔国{console.log(2卡塔尔(قطر‎}那样不就使这一个点子成分享的了别样HTML成分实例都能访谈,那眼看不实际因为我们只想为某一元素设置某件事件函数。对于document.body自己上会未有onclick属性不亮堂是或不是JS引擎内部得以完结的,借使是那现实是怎么贯彻的?知道的盆友麻烦告知~

 

(c卡塔尔.在<=IE7通过getAttribute(卡塔尔国方法访谈style脾性和onclick那样的事件管理程序个性时,重回的值与品质的值相像。即getAttribute(‘style’State of Qatar重返的不是字符串而是对象,getAttribute(‘onclick’State of Qatar再次来到的不是字符串而是函数。尽管IE8已修复该bug但区别版本的不黄金时代致性依然提议使用性质访谈HTML特性。
风华正茂道面试题:下列关于IE,FF下边脚本的分别描述失实的是:感到那道怪怪的考的是最早扶持境况??
A.innerText IE扶持,FF不帮忙  FF开始的黄金时代段时期不帮衬
B.document.createElement FF支持,IE不支持 X
C.setAttribute(‘class’,’styleclass’卡塔尔(قطر‎FF协理,IE不援助   IE中期不扶助
D.用setAttribute设置事件FF不支持,IE帮助 X
IE:all扶助innerText  >IE8匡助setAttribute设置特色或事件
FF:新本子辅助,旧版本不接济outerHTML outerText
innerText;setAttribute扶持

赢得脾气

创产生分

安装特色

这三个方法都可操作自定义脾性,但唯有公认的脾气技能被应用以属性的花样增添到DOM对象中,以属性形式操作那个特征会被同台到html标签中。HTMLElement的5个特点都有照拂属性(意思是Element.prototype或HTMLElement.prototype上的脾性可平素通过.格局寻访State of Qatar与其对应:id,title,lang,dir,className。在DOM中以属性格局操作那几个特征会协同到html标签中。因为class天性是那5种特色之风度翩翩,能够通过className属性访问,xsf本性不在Element.prototype或HTMLElement.prototype对象中有对应属性所以经过质量访问格局赢得的值为undefiend。要想访谈xsf天性值能够透过getAttribute(‘xsf’卡塔尔(推荐)或getAttributeNode(‘xsf’卡塔尔(قطر‎.value或attributes[“xsf”].value访问。
新葡亰496net 9
(2State of Qatar.当然成分还可以由此持续HTML某成分Element.prototype上的部分性质,比方input成分的HTMLInputElement.prototype上的disabled能够经过inputele.disabled得到或设置值。inputele.disabled;//
false表示该因素未被安装disabled属性即未被禁止使用,inputele.disabled=true;//
代表为该因素设置不可用属性。

setAttribute(‘attr’,’value’卡塔尔(قطر‎:世袭自Element.prototype。参数为要安装的特征名和值,借使性子已经存在,setAttribute(卡塔尔会以钦命值替换现存值,固然天性不存在,setAttribute会创立该属性并设置相应值。
经过该办法能够操作HTML性子也得以操作自定义天性,通过这些点子设置的性情名会被合并退换为小写格局即”ID”转换为”id”。
因为兼具性子都以性质,所以直接给属性赋值就足以设置特色的值,但由此加多自定义属性并不会化为该因素的表征那样其实为因素本人增多了质量。

其少年老成函数使用了五个数组来保存名值对,最终再以空格分隔符将它们拼接起来(那是类别化长字符串时的常用技艺)。

Element类型用于表现XML或HTML成分,提供对元素标签字,子节点及特色的访谈。原型链的继续关系为
某节点成分.__proto__->(HTML某元素Element.prototype)->HTMLElement.prototype->Element.prototype->Node.prototype->EventTarget.prototype。
以HTML成分为例:document.documentElement.__proto__->HTMLHtmlElement.prototype->HTMLElement.prototype->Element.prototype->Node.prototype->EventTarget.prototype
新葡亰496net 10
新葡亰496net 11

新葡亰496net 12

function outputAttributes(ele){
   var pairs=new Array(),
         attrName,attrValue,i,len;
   for(i=0;i<ele.attributes.length;i++){
       attrName=ele.attributes[i].nodeName;
       attrValue=ele.attributes[i].nodeValue;
       pairs.push(attrName+"=""+attrValue+""");
   }
  return pairs.join(" ");
}
outputAttributes(document.body);// "id="cd" aria-hidden="true""

 

document.body.getAttribute('onclick');// "(function(){console.log(1)})()"
document.body.onclick;// function (){
  console.log(2)
}
document.body.hasOwnProperty('onclick');// false
var attr=document.createAttribute('class');
attr.value="as";
attr;// class=​"as"
document.body.attributes.setNamedItem(attr);
document.body.attributes;//NamedNodeMap {0: id, 1: style, 2: aria-hidden, 3: class, length: 4}
<ul id="myList">
<li>Item 1</li>
<li>Item 2</li>
<li>Item 3</li>
</ul>
var ul=document.getElementById('myList');
for(var i=0;i<ul.childNodes.length;i++){
    if(ul.childNodes[i].nodeType==1){
         //do else
    }
}

上述所反常都可通过在createElement(卡塔尔国中内定完整的HTML标签来缓和。

(4卡塔尔.item(posState of Qatar:重临位于数字pos地点处的特点节点。 

  • length:只读,重临映射(map卡塔尔国中目的的多寡。
var div=document.createElement('div');
div.id="myNewid";// "myNewid"
div.className="box";// "box"
  • HTML元素
  • 赢得特性
  • 安装特色
  • attributes属性
  • 创办成分
  • 要素的子节点
document.body.attributes.item(3);// class=​"as"

 

《JavaScript高端程序设计》
反本求源——DOM成分的风味与特性 MDN NamedNodeMap MDN
CSSStyleDeclaration 

并不是对具有属性的改造都能直观在页面上表现出来。
对id或lang的更改对顾客来说是晶莹不可以看见的;
对title的更改只会在鼠标移动到这些因素上时才显示出来;
对dir的改造会在品质被重写的那一刻立时影响页面中文本左右对齐方式;
纠正className时,即便新类关联了与早前不等的CSS样式那么就能够顿时接受该样式;
关于通晓全数HTML成分以至与之提到的原型类型的布局器可参谋高程三P263,有的成分是直接接轨自HTMLElement.prototype比如b元素,有的是世袭自HTML某成分Element.prototype,比方a成分,它的原型属性指向HTMLAnchorElement.prototype。
(6State of Qatar.attributes:世袭自Element.prototype。重回四个NamedNodeMap的实例对象。
那边扩展领悟一下NamedNodeMap接口,原型链世襲关系为:ele.attributes.__proto__->NamedNodeMap.prototype->Object.prototype。NamedNodeMap接口表示属性节点指标的聚合,就算NamedNodeMap里面包车型大巴靶子足以像数组同样通过索引实行访谈但它和NodeList分化等,对象的生龙活虎意气风发未有一点点名。NamedNodeMap群集是即时更新的,由此只要它里面含有的对象产生转移的话,该对象会自动更新到新型景况。
新葡亰496net 13

标签:

相关文章

发表评论

电子邮件地址不会被公开。 必填项已用*标注

网站地图xml地图