一、dom对象的innerText和innerHTML有什么区别?
-
innerText
设置或获取位于对象起始和结束标签内的文本 。如果有HTML标签,它会过滤掉HTML标签,并且在多层次的时候会按照元素由浅到深的顺序拼接其内容。 -
innerHTML
属性返回该元素包含的 HTML 代码(包括元素、注释和文本节点)。该属性可读写,常用来设置某个节点的内容。
如果将innerHTML
属性设为空,等于删除所有它包含的所有节点。
<div id="text">
<p>
abc
<span>def</span>
</p>
</div>
<script>console.log(text.innerText)</script> // 输出 : "abc def"
<script>console.log(text.innerHTML)</script>
//输出 :" <p> abc <span>def</span> </p> "
<script>text.innerHTML='';console.log(text.innerHTML)</script>//输出: 空节点
二、elem.children和elem.childNodes的区别?
-
elem.children
属性返回一个HTMLCollection对象(包含了元素的通用集合,还提供了用来从该集合中选择元素的方法和属性。),包括当前元素节点的所有子元素。它是一个类似数组的动态对象(实时反映网页元素的变化)。这个属性与Node.childNodes
属性的区别是,它只包括HTML元素类型的子节点,不包括其他类型的子节点。
例子
三、查询元素有几种常见的方法?
1.document.querySelector
、document.querySelectorAll
-
ocument.querySelector
方法接受一个CSS选择器作为参数,返回匹配该选择器的元素节点。 -
document.querySelectorAll
方法返回一个NodeList
对象,包含所有匹配给定选择器的节点。
document.querySelectorAll('DIV:not(.ignore)');选中div元素,那些class含ignore的除外
但是,它们不支持CSS伪元素的选择器和伪类的选择器(比如:link
和:visited
)。
并且这两种方法在HTML文档上和HTML元素上都能调用。
2.document.getElementsByTagName()
-
document.getElementsByTagName
方法返回所有指定HTML标签的元素,返回值是一个类似数组的HTMLCollection对象,可以实时反映HTML文档的变化。该方法在HTML文档上和HTML元素上都能调用。
ar paras = document.getElementsByTagName('p');
paras instanceof HTMLCollection // true
3.document.getElementsByClassName()
-
document.getElementsByClassName
方法返回一个类似数组的对象,包括了所有class
名字符合指定条件的元素,元素的变化实时反映在返回结果中。由于class
是保留字,所以JavaScript一律使用className
表示CSS的class
。如果参数是一个空格分隔的字符串,元素的class
必须符合所有字符串之中所有的class
才会返回。
var elements = document.getElementsByClassName('foo bar');
上面代码返回同时具有foo和bar两个class的元素,foo和bar的顺序不重要。
4.document.getElementsByName()
-
document.getElementsByName
方法用于选择拥有name
属性的HTML元素(比如<form>
、<radio>
、<img>
、<frame>
、<embed>
和<object>
等),返回一个类似数组的的对象(NodeList对象的实例),因为name
属性相同的元素可能不止一个。
// 表单为 <form name="a"></form>
var forms = document.getElementsByName('a');
forms[0].tagName // "FORM"
5.getElementById()
-
getElementById
方法返回匹配指定id
属性的元素节点。如果没有发现匹配的节点,则返回null
。
该方法只能在HTML文档上调用,不能在HTML元素上调用。
6.document.elementFromPoint()
-
document.elementFromPoint
方法返回位于页面指定位置最上层的Element
子节点。
var element = document.elementFromPoint(50, 50);
两个参数,依次是相对于当前视口左上角的横坐标和纵坐标,单位是像素。
四、如何创建一个元素?如何给元素设置属性?
- 创建元素:
-
createElement
方法用来生成网页元素节点。参数为元素的标签名。 -
createTextNode
方法用来生成文本节点,参数为所要生成的文本节点的内容。
-
- 设置属性:
-
element.setAttribute(name, value);
接收的2个参数分别是需要设置的属性名和属性值。如果指定的属性已经存在,则其值变为传递的值。
-
- 元素的添加:
-
Node.appendChild()
方法将一个节点添加到指定父节点的子节点列表末尾。
语法:var child = node.appendChild(child);
-
Node.insertBefore()
方法,在当前节点的某个子节点之前再插入一个子节点。
语法:var insertedElement = parentElement.insertBefore(newElement, referenceElement);
语法解析:1.新元素:你想插入的元素(newElement
)
2.目标元素:你想把这个新元素插入到哪个元素(targetElement
)之前。
3.父元素:目标元素的父元素(parentElement
)
-
- 元素的删除:
-
Node.removeChild()
方法从DOM中删除一个子节点。返回删除的节点。
举例:
-
<body>
<div id="test">世界
<div id="nested">hello</div>
</div>
<script>
var a=document.getElementById("test");
var p=document.createElement('p')
var text=document.createTextNode('你好')
var b=document.createElement('p')
p.appendChild(text)
a.appendChild(p) //世界 hello 你好
// b.appendChild(text)
// a.insertBefore(b,a.firstChild) // 你好 世界 hello
var d_nested = document.getElementById("nested");
var throwawayNode = a.removeChild(d_nested); // 世界 你好
</script>
</body>
六、DOM0事件和DOM2级在事件监听使用的方式上有什么区别?
- DOM 0级事件,通过javascript制定事件处理程序的传统方式。就是将一个函数赋值给一个事件处理属性。一个事件处理程序只能对应一个处理函数。这些属性通常全部小写。
例子:
var btn = document.getElementById("mybtn")
btn.onclick = function(){
alert(this.id); //"mybtn"
btn.onclick=null;//删除事件处理程序,单击按钮将不会有任何动作发生。
- 使用DOM0级方法指定的事件处理程序被认为是元素的办法。因此,这时候的事件处理程序是在元素的作用域中运行;换句话说,程序中的this
引用当前元素,正如上面的例子。 - DOM 2级事件,定义了两个方法,用于处理指定和删除事件处理程序的操作:addEventListener() 和 removeEventListener()。通过addEventListener()添加的事件只能通过removeEventListener()来删除。
所有DOM节点都包含这两个方法,并且都接受3个参数:
1.要处理的事件名
2.作为事件处理程序的函数
3.一个布尔值,布尔值如果是true,表示在捕获阶段调用事件处理程序,如果是flase,表示在冒泡阶段调用事件处理程序。
例子:
var body=document.body
body.addEventListener('click',function(){
document.body.appendChild(document.createTextNode('1'))
}) // aaa 1
body.removeEventListener('click',function(){
document.body.appendChild(document.createTextNode('1'))
})//aaa 1
//这样不能移除 上面的函数。
//如果 给函数添加一个名字如下:
var body=document.body
body.addEventListener('click',function a(){
document.body.appendChild(document.createTextNode('1'))
})
body.removeEventListener('click',a)
})
// 这样也没有办法移除,因为作用域的关系。
// //用以下方法:
var body=document.body
function a(){
document.body.appendChild(document.createTextNode('1'))
}
body.addEventListener('click',a)
body.removeEventListener('click',a)
- 使用DOM 2级方法添加事件处理程序的主要好处是可以添加多个事件处理程序,这也是与DOM 0级事件最主要的区别。
七、attachEvent
与addEventListener
的区别?
-
attachEvent
是早期IE浏览器(IE8及早期版本)的一个专有的替代性标准,替代EventTarget.addEventListener()
方法。该特性是非标准的。
语法:attached = target.attachEvent(eventNameWithOn, callback)
attachEvent
与addEventListener
的区别:- 接受的参数
attachEvent
接受2个参数:事件名称,事件处理函数。只支持冒泡。
addEventListener
接受3个参数:事件名称,事件处理函数,布尔值。冒泡、捕获都支持。 - 事件名称
attachEvent
事件名称前面要加“on”,如“onclick”,
addEventListener
不需要,如“click”。 - 作用域
attachEvent
会在全局作用域中运行,即this = window
。
addEventListener
是在元素作用域中运行,this
指的是当前元素。 - 删除方式
attachEvent
使用detachEvent
删除添加事件。
addEventListener
使用removeEventListener
删除添加事件。
- 接受的参数
八、解释IE事件冒泡和DOM2事件传播机制?
-
IE事件冒泡:事件开始时由最具体的元素接收,然后逐级向上传播到较为不具体的元素。如下图,当我们点击
div
里面文本的时候,click
会先在<div>
元素上发生,然后沿着DOM树向上传播,在每一级的节点都会发生直到传播到document
对象。
冒泡和捕获图解 -
DOM 2事件规定的事件包括三个阶段:事件捕获阶段、处于目标阶段和事件冒泡阶段。首先发生的是事件捕获阶段,为截获事件提供了机会。然后是实际的目标接收到事件。最后一个阶段是冒泡阶段,可以在这个阶段对事件作出响应。
DOM2事件传播机制
*在DOM事件流中,实际的目标(div
元素)在捕获阶段不会接收到事件。这意味着在捕获阶段事件从document
到<html>
再到<body>
后就停止了。下一个阶段是“处于目标”阶段,于是事件在<div>
上发生,并在事件处理中被看出冒泡阶段的一部分。然后冒泡阶段发生,事件又传播回文档。
但IE、Safari、Chrome、Firefox和opera9.5及更高版本都会再捕获阶段触发事件对象上的事件。结果,就是有两个机会在目标对象上面操作事件。
九、如何阻止事件冒泡?如何阻止默认事件?
-
stopPropagation()
方法可以阻止事件冒泡。例如:
<div id="test">
<input id="myBtn" type="button" value="点击我"/>
</div>
<script>
var oDiv = document.getElementById("test");
var oBtn = document.getElementById("myBtn");
oDiv.addEventListener("click",function(){
console.log(this.id+"我被冒泡了");
},false);
oBtn.addEventListener("click",function(){
console.log(this.id+"我被冒泡了");
},false); //当没有终止冒泡时的输出结果:"myBtn我被冒泡了" "test我被冒泡了"
oBtn.addEventListener("click",function(ev){
console.log(this.id);
ev.stopPropagation();
},false); // 输出结果:"myBtn我被冒泡了" "myBtn"
</script>
-
reventDefault()
方法用来取消事件默认行为。例如:
<body>
<div id="test">
<a id="myLink" href="http://www.baidu.com">百度</a>
</div>
</body>
<script>
var link = document.getElementById("myLink");
link.addEventListener("click",function(ev){
ev.preventDefault();//取消a链接点击转跳到指定的URL的默认行为。
},false);
</script>