1.DOM
文档对象模型(Document Object Model,简称DOM ),是W3C组织推荐的处理可扩展标记语言(HTML或者XML)的标准编程接口。
W3C已经定义了一系列的DOM接口,通过这些DOM接口可以改变网页的内容、结构和样式。
DOM树
文档:一个页面就是一个文档,DOM中使用document表示
元素∶页面中的所有标签都是元素,DOM中使用element表示
节点∶网页中的所有内容都是节点(标签、属性、文本、注释等),DOM中使用node表示
1.1获取元素
ID获取
通过DOM获取页面元素,使用 document.getElementById() 获取,返回的是一个元素对象,可用console.dir打印返回的元素对象。
根据标签名获取
1、使用 document.getElementsByTagName() 方法可以返回带有指定标签名的对象的集合,以伪数组的形式存储
(1)因为得到的是一个对象的集合,所以我们想要操作里面的元素就需要遍历;
(2)得到元素对象是动态的;
(3)如果页面只有一个li元素,返回的还是伪数组形式;
(4)如果页面没有这个元素,返回的空的伪数组形式
2、还可以获取某个元素(父元素)内部所有指定标签名的子元素.
element.getElementsByTagName (‘标签名’);父元素必须是单个对象(必须指明是哪一个元素对象)
HTML5新增的方法获取
1.document.getElementsByClassName(‘类名’);//根据类名返回元素对象集合
var boxs = document.getElementsByClassName('box')
console.log('boxs');
2.document.querySelector(‘选择器’);//根据指定选择器返回第一个元素对象
var firstBox = document.querySelector('.box');
console.log(firstBox);
var nav = document.querySelector('#nav');
console.log(nav);
var li = document.querySelector('li');
console.log(li);
3、document .querySelectorAll(‘选择器’) ;//根据指定选择器返回
var al1Box = document.querySelectorAll('.box');
console.log(allBox);
var lis = document.querySelectorAll('li');
console.log(lis);
特殊元素
1、获取body元素
doucumnet.body //返回body元素对象
2、获取html元素
document.documentElement //返回html元素对象
1.2操作元素
改变元素的内容
element.innerText:从起始位置到终止位置的内容,但它去除html标签,同时空格和换行也会去掉
element.innerHTML:起始位置到终止位置的全部内容,包括html标签,同时保留空格和换行
修改表单属性
利用DOM可以操作如下表单元素的属性:type、value、checked、selected、disabled
修改样式属性
1、element.style 行内样式操作
2、element.className 类名样式操作
(1)JS里面的样式采取驼峰命名法比如fontsize、backgroundColor
(2)Js修改style样式操作,产生的是行内样式,css权重比较高
排他思想
如果有同一组元素,我们想要某一个元素实现某种样式,需要用到循环的排他思想算法︰
1、所有元素全部清除样式(干掉其他人)
2、给当前元素设置样式(留下我自己)
3、注意顺序不能颠倒,首先干掉其他人,再设置自己
自定义属性操作
1、获取属性值
(1)element.属性获取内置属性值(元素本身自带的属性)
(2)element.getAttribute(‘属性’);主要获得自定义的属性(标准)我们程序员自定义的属性
2、设置属性值
(1)element.属性设置内置属性值
(2)element.setAttribute(‘属性’);主要设置自定义的属性(标准)
3、移除属性:removeAttribute(‘属性’)
H5自定义属性
自定义属性目的∶是为了保存并使用数据。有些数据可以保存到页面中而不用保存到数据库中。
1、设置H5自定义属性
(1)H5规定自定义属性data-开头做为属性名并且赋值:
(2)使用JS设置:element.setAttribute(‘data-index’,2)
2、获取H5自定义属性
(1)兼容性获取element.getAttribute(‘data-index’);
(2)H5新增element.dataset.index或者element.dataset[‘index’],ie 11才开始支持
<div date-list-name="andy"></div>
//dateset是一个里面存放了所有以date开头的自定义属性 集合
console.log(div.getAttribute('date-list-name'));
console.log(div.dateset.listName);
console.log(div.dateset['listName']);//多个单词,采取驼峰命名法
1.3节点操作
节点概述
一般地,节点至少拥有nodeType(节点类型)、nodeName (节点名称)和nodeValue (节点值)这三个基本属性。
(1)元素节点nodeType 为 1
(2)属性节点nodeType 为 2
(3)文本节点nodeType 为 3 (文本节点包含文字、空格、换行等)
主要为元素节点
节点层级
1、父级节点(node.parentNode)
parentNode属性可返回某节点的父节点(最近的一个父节点)
如果指定的节点没有父节点则返回null
2、子级节点
(1)parentNode.childNodes 【标准】
parentNode.childNodes 返回包含指定节点的子节点的集合,该集合为即时更新的集合。
注意:返回值里面包含了所有的子节点,包括元素节点,文本节点等。
如果只想要获得里面的元素节点,则需要专门处理。所以我们一般不提倡使用childNodes
var ul = document.querySelector('ul');
for (var i = 0; i < ul.childNodes.length; i++) {
if (ul.childNodes[i].nodeType == 1) {
// ul.childNodes[i] 是元素节点
console.log(ul.childNodes[i]);
}
}
(2)parentNode.children【非标准】
parentNode.children 是一个只读属性,返回所有的子元素节点。它只返回子元素节点,其余节点不返回(重点,得到了各个浏览器的支持)。
(3)parentNode.firstElementChi1d
firstElementchild返回第一个子元素节点,找不到则返回null。
(4)parentNode.lastElementChild
lastElementchild返回最后一个子元素节点,找不到则返回null。
3、兄弟节点
(1)node.nextsibling
nextsibling返回当前元素的下一个兄弟节点,找不到则返回null。同样,也是包含所有的节点。
(2)node.previousSibling
previoussibling 返回当前元素上一个兄弟节点,找不到则返回null。同样,也是包含所有的节点。
(3)node.nextElementsibling
nextElementsibling返回当前元素下一个兄弟元素节点,找不到则返回null。
(4)node.previousElementsibling
previousElementsibling返回当前元素上一个兄弟节点,找不到则返回null。
节点创建与添加
1、创建节点–document.createElement (‘tagName’)
document.createElement()方法创建由tagName指定的HTM元素。因为这些元素原先不存在,是根据我们的需求动态生成的,所以我们也称为动态创建元素节点。
2、添加节点
(1)node.appendchild (child)
node.appendChild()方法将一个节点添加倒指定父节点的子节点列表末尾(追加元素)。类似于css里面的after伪元素,数组中的push。
(2)node.insertBefore (child,指定元素)
node.insertBefore()方法将一个节点添加到父节点的指定子节点前面。类似于css里面的 before伪元素。
3、删除节点–node.removeChild (child)
node.removeChild()方法从DOM中删除一个子节点,返回删除的节点。
4、复制节点–node.cloneNode()
node.cloneNode()方法返回调用该方法的节点的一个副本。也称为克隆节点/拷贝节点
注意∶1.如果括号参数为空或者为false,则是浅拷贝,即只克隆复制节点本身,不克隆里面的子节点。
2.如果括号参数为true,则是深度拷贝,会复制节点本身以及里面所有的子节点。
5、三种动态创建元素区别
document.write ()
element.innerHTML
document.createElement ()
区别
(1)document.write ()是直接将内容写入页面的内容流,但是文档流执行完毕,则它会导致页面全部重绘;
(2)element.innerHTML是将内容写入某个DOM节点,不会导致页面全部重绘;
(3)element.innerHTML创建多个元素效率更高(不要拼接字符串,采取数组形式拼接),结构稍微复杂;
(4)document.createElement ()创建多个元素效率稍低一点点,但是结构更清晰。
1.4事件基础
事件三要素
1.事件是有三部分组成事件源、事件类型、事件处理程序―我们也称为事件三要素(事件源.事件类型=事件处理程序)
(1)事件源:事件被触发的对象,如按钮
(2)事件类型:如何触发什么事件,比如鼠标点击(onclick)还是鼠标经过还是键盘按下
(3)事件处理程序:通过一个函数赋值的方式完成
常见鼠标事件
鼠标事件 触发条件 onclick 鼠标点击左键触发 onmouseover 鼠标经过触发(经过子盒子也会触发) mouseenter 鼠标经过自己的盒子才会出发 onmouseout 鼠标离开触发 onfocus 获得鼠标焦点触发 onblur 失去鼠标焦点触发 onmousemove 鼠标移动触发 onmouseup 鼠标弹起触发 onmousedown 鼠标按下触发 contextmenu 禁止鼠标右键菜单 selectstart 禁止鼠标选中
1.5事件高级
注册事件
1、传统注册方式
利用on开头的时间onclick等(注册事件的唯一性),最后注册的处理函数会覆盖前面注册的处理函数。
2、方法监听注册方式
addEventListener()是一个方法(同一个元素同一个事件可以注册多个监听器)
eventTarget.addEventListener(type,listener[, useCapture])
eventTarget.addEventListener()方法将指定的监听器注册到eventTarget(目标对象)上,当该对象触发指定的事件时,就会执行事件处理函数。
该方法接收三个参数︰
type:事件类型字符串,比如click、mouseover,注意这里不要带on;
listener:事件处理函数,事件发生时,会调用该监听函数;
useCapture:可选参数,是一个布尔值,默认是false。
删除事件
1、传统删除方式
eventTarget.onclick = null;
2.方法监听注册方式
eventTarget.removeEventListener(type, listener[, useCapture]);
divs[1].addEventListener('click',fn)//里面的fn 不需要调用加小括号
function fn() {
alert(22);
divs[1].removeEventListener('click',fn);
}
DOM事件流
事件流描述的是从页面中接收事件的顺序,事件发生时会在元素节点之间按照特定的顺序传播,这个传播过程即DOM事件流。
DOM事件流分为3个阶段∶
1.捕获阶段;2.当前目标阶段;3.冒泡阶段;
注意
1、 Js代码中只能执行捕获或者冒泡其中的一个阶段;
2、onclick和attachEvent只能得到冒泡阶段;
3、addEventListener(type,listener[,useCapture])第三个参数如果是true,表示在事件捕获阶段调用事件处理程序;如果是false (不写默认就是false),表示在事件冒泡阶段调用事件处理程序;
4、实际开发中我们很少使用事件捕获,我们更关注事件冒泡;
5、有些事件是没有冒泡的,比如onblur、onfocus、onmouseenter、onmouseleave;
6、事件冒泡有时候会带来麻烦,有时候又会帮助很巧妙的做某些事件。
事件对象
eventTarget.onclick = function (event) { }
eventTarget.addEventListener ('click',function(event) { })//这个event就是事件对象,我们还喜欢的写成e或者evt
官方解释: event对象代表事件的状态,比如键盘按键的状态、鼠标的位置、鼠标按钮的状态。
简单理解︰事件发生后,跟事件相关的一系列信息数据的集合都放到这个对象里面,这个对象就是事件对象event,它有很多属性和方法。
事件对象的常见属性和方法
事件对象属性方法 | 说明 |
---|---|
e.target | 返回触发事件的对象 标准 |
e.srcElement | 返回触发事件的对象 非标准 ie6-8使用 |
e.type | 返回事件的类型 比如click、mouseover不带on |
e.cancelBubble | 该属性阻止冒泡 非标准 ie6-8使用 |
e.returnValue | 该属性阻止默认事件(默认行为) 非标准ie6-8使用比如不让链接跳转 |
e.preventDefault() | 该方法阻止默认事件(默认行为) 标准比如不让链接跳转 |
e.stopPropagation() | 阻止冒泡 标准 |
事件委托(代理、委派)
事件委托的原理:不是每个子节点单独设置事件监听器,而是事件监听器设置在其父节点上,然后利用冒泡原理影响设置每个子节点。
以上案例:给ul注册点击事件,然后利用事件对象的target来找到当前点击的li,因为点击li,事件会冒泡到ul上,ul有注册事件,就会触发事件监听器。
事件委托的作用:我们只操作了一次DOM,提高了程序的性能。
常用的鼠标事件
鼠标事件对象 | 说明 |
---|---|
e.clientX | 返回鼠标相对于浏览器窗口可视区的X坐标 |
e.clientY | 返回鼠标相对于浏览器窗口可视区的Y坐标 |
e.pagex | 返回鼠标相对于文档页面的×坐标IE9+支持 |
e.pageY | 返回鼠标相对于文档页面的Y坐标IE9+支持 |
e.screenX | 返回鼠标相对于电脑屏幕的X坐标 |
e.screenY | 返回鼠标相对于电脑屏幕的Y坐标 |
常用的键盘事件
键盘事件 | 触发条件 |
---|---|
onkeyup | 某个键盘按键被松开时触发 |
onkeydown | 某个键盘按键被按下时触发 |
onkeypress | 某个键盘按键被按下时触发(但是它不识别功能键比如ctrl shift箭头等) |
三个事件的执行顺序:keydown–keypress–keyup |
2.BOM
BOM( BrowserObject Model )即浏览器对象模型,它提供了独立于内容而与浏览器窗口进行交互的对象,其核心对象是window。(window.name是一个特殊属性,别用来声明变量)
window包含document、location、navigation、screen、history。
2.1window 对象的常见事件
窗口加载事件
window.onload = function () {} 或者
window.addEventListener ("load" ,function () {});
window.onload是窗口(页面)加载事件,当文档内容完全加载完成会触发该事件(包括图像、脚本文件、CSS文件等),就调用的处理函数。
1、有了window.onload 就可以把JS代码写到页面元素的上方,因为onload是等页面内容全部加载完毕,再去执行处理函数;
2、window.onload传统注册事件方式只能写一次,如果有多个,会以最后一个window.onload为准;
3、如果使用addEventListener则没有限制。
document.addEventListener ('DOMContentLoaded',function(){})
DOMContentLoaded事件触发时,仅当DOM加载完成,不包括样式表,图片,flash等等。
如果页面的图片很多的话,从用户访问到onload触发可能需要较长的时间,交互效果就不能实现,必然影响用户的体验,此时用DOMContentLoaded事件比较合适。
调整窗口大小事件
window.onresize = function () { }
window.addEventListener ("resize" , function() {});
window.onresize是调整窗口大小加载事件,当触发时就调用的处理函数。
1.只要窗口大小发生像素变化,就会触发这个事件。
2.我们经常利用这个事件完成响应式布局。window.innerWidth当前屏幕的宽度
2.2定时器
setTimeout()定时器
window.setTimeout(调用函数,[延迟的亳秒数]);
setTimeout()方法用于设置一个定时器,该定时器在定时器到期后执行调用函数。
1、window可以省略。
2、这个调用函数可以直接写函数,或者写函数名或者采取字符串‘函数名()'三种形式,第三种不推荐。
3、延迟的毫秒数省略默认是0,如果写,必须是毫秒。
4、因为定时器可能有很多,所以我们经常给定时器赋值一个标识符。
停止setTimeout()定时器
window.clearTimeout (timeoutID)
clearTimeout()方法取消了先前通过调用setTimeout()建立的定时器
1、window可以省略。
2、里面的参数就是定时器的标识符。
setInterval()定时器
window.setInterval(回调函数,[间隔的毫秒数]);
setIlnterval()方法重复调用一个函数,每隔这个时间,就去调用一次回调函数
1、window可以省略。
2、这个调用函数可以直接写函数,或者写函数名或者采取字符串’函数名()'三种形式。
3、间隔的毫秒数省略默认是0,如果写,必须是毫秒,表示每隔多少毫秒就自动调用这个函数。
4、因为定时器可能有很多,所以我们经常给定时器赋值一个标识符。
停止setInterval()定时器
window.clearInterval (intervalID);
clearInterval()方法取消了先前通过调用setInterval()建立的定时器。
1、window可以省略。
2、里面的参数就是定时器的标识符。
this指向问题
this 指向问题一般情况下this的最终指向的是那个调用它的对象。
1、全局作用域或者普通函数中this指向全局对象window(注意定时器里面的this指向window)
console.log(this);
function fn() {
console.log(this);
}
fn();//window.fn();
window.setTimeout(function () {
console.log(this);
}, 1000);
2、方法调用中谁调用this指向谁
var o = {
sayHi: function () {
console.log(this); // this指向的是 o 这个对象
}
}
o.sayHi();
var btn = document.querySelector('button');
btn.onclick = function () {
console.log(this); // this指向的是btn这个按钮对象
}
btn3.addEventListener('click', function () {
console.log(this);
})
3、构造函数中this指向构造函数的实例
function Fun() {
console.log(this); //this指向的是fun 实例对象
}
var fun = new Fun();
2.3JS执行队列
同步和异步
同步:前一个任务结束后再执行后一个任务,程序的执行顺序与任务的排列顺序是一致的、同步的。
(比如做饭的同步做法:我们要烧水煮饭,等水开了( 10分钟之后),再去切菜,炒菜。)
异步:你在做一件事情时,因为这件事情会花费很长时间,在做这件事的同时,你还可以去处理其他事情。
(比如做饭的异步做法,我们在烧水的同时,利用这10分钟,去切菜,炒菜。)
同步任务:同步任务都在主线程上执行,形成一个执行栈。
异步任务:JS的异步是通过回调函数实现的。一般而言,异步任务有以下三种类型:
1、普通事件,如click、resize等
2、资源加载,如load、error等
3、定时器,包括setlnterval、setTimeout等
异步任务相关回调函数添加到任务队列中(任务队列也称为消息队列)。
执行机制
1、先执行执行栈中的同步任务。
2、异步任务(回调函数)放入任务队列中。
3、一旦执行栈中的所有同步任务执行完毕,系统就会按次序读取任务队列中的异步任务,于是被读取的异步任务结束等待状态,进入执行栈,开始执行。
由于主线程不断的重复获得任务、执行任务、再获取任务、再执行,所以这种机制被称为事件循环(eventloop)。
2.4location对象
location对象
window对象给我们提供了一个location属性用于获取或设置窗体的URL,并且可以用于解析URL。因为这个属性返回的是一个对象,所以我们将这个属性也称为location对象。
URL
统一资源定位符(Uniform Resource Locator, URL)是互联网上标准资源的地址。互联网上的每个文件都有一个唯一的URL,它包含的信息指出文件的位置以及浏览器应该怎么处理它。
URL的一般语法格式为∶
protocol://host[:port]/path/[?query]#fragment
http:// www.itcast. cn/index.html?name=andy&age=18#link
组成 | 说明 |
---|---|
protocol | 通信协议常用的http,ftp,maito等 |
host | 主机(域名) www.itheima.com |
port | 端口号可选,省略时使用方案的默认端口如http的默认端口为80 |
path | 路径由零或多个’/'符号隔开的字符串,一般用来表示主机上的一个目录或文件地址 |
query | 参数以键值对的形式,通过&符号分隔开来 |
fragment | 片段#后面内容常见于链接锚点 |
location对象的属性
location对象属性 | 返回值 |
---|---|
location.href | 获取或者设置整个URL |
location. host | 返回主机(域名)www.itheima.com |
location.port | 返回端口号如果未写返回空字符串 |
location.pathname | 返回路径 |
location. search | 返回参数 |
location.hash | 返回片段#后面内容常见于链接锚点 |
location对象的方法
location对象方法 | 返回值 |
---|---|
location.assign() | 跟href一样,可以跳转页面(也称为重定向页面) |
location.replace() | 替换当前页面,因为不记录历史,所以不能后退页面 |
location.reload() | 重新加载页面,相当于刷新按钮或者f5如果参数为true强制刷新ctrl+f5 |
2.5navigator对象
navigator对象包含有关浏览器的信息,它有很多属性,我们最常用的是userAgent,该属性可以返回由客户机发送服务器的user-agent头部的值。
下面前端代码可以判断用户那个终端打开页面,实现跳转
if ((navigator.userAgent.match(/(phone|pad|pod|iPhone|iPod|ios|iPad|Android|Mobile|BlackBerry|IEMobile|MQQBrowser|JUC|Fennec|wOSBrowser|BrowserNG| webosl symbian|windows Phone)/i))) {
window.location.href = "";//手机
} else {
window.location.href = "";//电脑
}
2.6history对象
window对象给我们提供了一个history对象,与浏览器历史记录进行交互。该对象包含用户(在浏览器窗口中)访问过的URL。
history对象方法 | 作用 |
---|---|
back() | 可以后退功能 |
forward() | 前进功能 |
go(参数) | 前进后退功能参数如果是1前进1个页面如果是-1后退1个页面 |