赞
踩
BOM :Browser Object Model(浏览器对象模型),浏览器模型提供了独⽴于内容的、可以与浏览器
窗⼝进⾏滑动的对象结构,就是浏览器提供的 API
其主要对象有:
window 对象——BOM 的核⼼,是 js 访问浏览器的接⼝,也是 ES 规定的 Global 对象
location 对象:提供当前窗⼝中的加载的⽂档有关的信息和⼀些导航功能。既是 window 对象属
性,也是 document 的对象属性
navigation 对象:获取浏览器的系统信息
screen 对象:⽤来表⽰浏览器窗⼝外部的显⽰器的信息等
history 对象:保存⽤⼾上⽹的历史信息
浏览器事件模型中过程分为三个阶段:捕获阶段、目标阶段、冒泡阶段,事件的流转顺序为捕获阶段 -> 目标阶段 ->冒泡阶段,捕获阶段为从外向内捕获,冒泡阶段为从内向外冒泡
通常有以下几种方式触发事件
<button onclick="buttonClick()">按钮</button>
<button id="button">按钮</button>
<script>
var btn = document.getElementById('button');
btn.onclick = function(){
//TODO 一些事情
};
</script>
<button id="button">按钮</button>
<script>
const btn = document.getElementById('button');
btn.addEventListener('click',function(e){
//TODO 一些事情
},false)
</script>
第三种就是事件监听,也就是我们所说的事件模型的捕获阶段,冒泡阶段,其中第三个参数true表示捕获阶段,false表示冒泡阶段,默认不传为false,下面来看个例子。
<div id="parent" class="flex-center"> parent <p id="child" class="flex-center"> child <span id='son' class="flex-center"> son </span> </p> </div> <script> const parent = document.getElementById("parent"); const child = document.getElementById("child"); const son = document.getElementById("son"); window.addEventListener("click", function (e) { // e.target.nodeName 指当前点击的元素, e.currentTarget.nodeName绑定监听事件的元素 console.log("window 捕获", e.target.nodeName, e.currentTarget.nodeName); }, true); parent.addEventListener("click", function (e) { // e.stopPropagation(); // e.target.nodeName 指当前点击的元素, e.currentTarget.nodeName绑定监听事件的元素 console.log("parent 捕获", e.target.nodeName, e.currentTarget.nodeName); }, true); child.addEventListener("click", function (e) { console.log("child 捕获", e.target.nodeName, e.currentTarget.nodeName); }, true); son.addEventListener("click", function (e) { console.log("son 捕获", e.target.nodeName, e.currentTarget.nodeName); }, true); window.addEventListener("click", function (e) { // e.target.nodeName 指当前点击的元素, e.currentTarget.nodeName绑定监听事件的元素 console.log("window 冒泡", e.target.nodeName, e.currentTarget.nodeName); }, false); parent.addEventListener("click", function (e) { console.log("parent 冒泡", e.target.nodeName, e.currentTarget.nodeName); }, false); child.addEventListener("click", function (e) { console.log("child 冒泡", e.target.nodeName, e.currentTarget.nodeName); }, false); son.addEventListener("click", function (e) { console.log("son 冒泡", e.target.nodeName, e.currentTarget.nodeName); }, false); </script>
当我点击son时候,上述的输出顺序依次为
window 捕获 SPAN undefined
parent 捕获 SPAN DIV
child 捕获 SPAN P
son 捕获 SPAN SPAN
son 冒泡 SPAN SPAN
child 冒泡 SPAN P
parent 冒泡 SPAN DIV
window 冒泡 SPAN undefined
target与currentTarget如备注描述,为什么要讲这两个,因为涉及到接下来的事件委托
运用事件模型的流转来写一个事件委托
<ul id="ul"> <li>1</li> <li>2</li> <li>3</li> <li>4</li> <li>5</li> <li>6</li> <li>7</li> <li>8</li> </ul> <script> const ul = document.querySelector('ul'); ul.addEventListener('click',function(e){ const target = e.target; if(target.tagName.toLowerCase() === "li") { const liList = document.querySelectorAll('li'); const index = Array.prototype.indexOf.call(liList,target); alert(`内容为${target.innerHTML},索引为${index}`); } }) </script>
ajax
底层使用的是XMLHttpRequest
,fetch
同XMLHttpRequest
非常类似,都是用来做网络请求。但是同复杂的XMLHttpRequest
的API相比,fetch
使用了Promise
,这让它使用起来更加简洁,从而避免陷入”回调地狱”。
1.使用XMLHttpRequest实现一个请求
let xhr = new XMLHttpRequest(); xhr.open('GET', 'http://localhost:3000/test'); xhr.onreadystatechange = function () { if(xhr.status !== 4) return; if(xhr.status === 200 || xhr.status === 304){ console.log(xhr.responseText); }else{ console.log('HTTP Request Error',xhr.status,xhr.statusText); } } xhr.timeout = 3000; xhr.ontimeout = function() { console.log('request timeout',xhr.responseURL); } xhr.send();
2.使用fetch实现一个请求
(1).fetch没有超时时间
(2).默认不带cookie
(3).错误不会reject
(4).需要借用AbortController中止fetch
fetch('http://localhost:3000/test',{method:'GET'})
.then(response=>response.json())
.then(json=>console.log(json))
.catch(error=>console.error('报错信息:',error));
3.为fetch设置超时设置,超时后中止请求
const fetchAbsortTimeout = (url,options,timeout=3000) => { const controller = new AbortController(); options.signal = controller.signal; return new Promise((resolve,reject)=>{ fetch(url,options) .then(response=>response.json) .then(resolve) .catch(reject) setTimeout(()=>{ controller.abort(); reject('超时!') },timeout) }) } const requestOptions = {method:'GET'}; fetchAbsortTimeout('http://localhost:3000/test',requestOptions,3000) .then(json=>{console.log(json)}) .catch(reason=>{console.log('报错信息:',reason)})
△4.衍生一下,写一个通用的异步函数超时处理
const asyncTimeout = (asyncFn,timeout = 3000) =>{
return new Promise((resolve,reject) => {
try{
asyncFn().then(res=>{resolve(res)})
} catch (e) {
throw e;
}
setTimeout(()=>{reject()},timeout);
})
}
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。