前端BOM基础

899 阅读9分钟

BOM浏览器对象模型,提供了独立于内容、可以与浏览器窗口进行互动的对象结构。使用BOM可以进行刷新浏览器、后退、前进、在浏览器中输入URL...

不同的浏览器会有不同的API,需要做适配处理

window对象

是使用js开发web应用的核心。BOM的核心是Window对象,该对象双重身份

  • ECMAScript中的Global对象
  • 浏览器窗口的JavaScript接口
moveTo(位置); // 可把窗口的左上角移动到一个指定的坐标
moveBy(左右,上下);
window.resizeTo(7,8);
window.resizeBy(300,300);

实际运行结果依据浏览器,以上方法很有可能被部分或全部禁用。

坐标:

  • clientX:在水平方向上,鼠标指针距离浏览器左侧边缘的距离。距离当前body可视区域
  • pageX:在水平方向上,鼠标指针距离网页文档X轴左侧边缘的距离。整个页面来说,包括了被卷去的body部分的长度
  • offsetX:在水平方向上,相对于带有定位的父盒子的左侧边缘的距离。
  • X、screenX:在水平方向上,鼠标指针距离电脑屏幕左侧边缘的距离。

页面没有滚动的时候:pageX==clientX


系统对话框 同步的模态对话框,即在他们显示的时候,代码会停止执行

alert();
confirm(“向用户提问”);//用户选择决定返回值yes
prompt(“提示输入的信息”,“输入框的初始值”);//用户行为决定返回值

异步的对话框:不会返回用户在对话框中的操作信息,对话框计数器不会涉及他们

window.print();
window.find();

网页结构与窗口

导航与打开新窗口

函数返回一个新建的window对象,可以保存对象对其操作,且该对象有一个opener属性,指向他的打开者

浏览器可能会对弹窗加以限制,现在所有的浏览器都内置了屏蔽弹窗的程序,被屏蔽时返回null

window.open("URL","frameName",特性字符串,布尔值);
//当frameName已存在时,忽略后面参数对视口大小、工具栏、状态栏、地址栏等的配置
//等同于点击以下超链接
<a href="URL",target="frameName" />
特殊值:_self、_parent、_top、_blank
  • 窗口 windows 指的是浏览器窗体
  • 标签页 tabs 指的是 window 窗体内的各个网页标签
  • 一个标签内部的 iframe/top frame 等,称之为frames

如果文档包含框架(frame 或 iframe 标签),浏览器会为 HTML 文档创建一个 window 对象,并为每个框架创建一个额外的 window 对象

对应框架元素也有contentDocument属性和contentWindow属性

  • window.frames 返回窗口中所有命名的框架
  • parent是父窗口(如果窗口是顶级窗口,那么parent、self、top三者等同)
  • top是最顶级父窗口(有的窗口中套了好几层frameset或者iframe)
  • self是当前窗口(等价window)
  • opener是用open方法打开当前窗口的那个窗口

window.document

document对象是DOM(Document Object Model)模型的根节点

BOM的window对象的document属性,通过document属性就可以访问、检索、修改XHTML文档内容与结构

  • 浏览器会在文档变得可见/不可见【切换标签页】时候,在document对象上触发visibilitychange事件,document.visibilityState属性值:visible/hidden
  • 一个document 的 Document.readyState 属性描述了文档的加载状态: uninitialized、loading、loaded、interactive、complete
  • readystatechange事件绑定测出含有三个状态,分别为loading、interactive、complete。
  1. loading(正在加载)document 仍在加载。
  2. interactive(可交互)文档已被解析,诸如图像,样式表和框架之类的子资源仍在加载。
  3. complete(完成)文档和所有子资源已完成加载。表示 load 状态的事件即将被触发。 用法:模拟load、DOMContentLoaded事件,在DOMContentLoaded之前插入修改DOM 当初始的 HTML 文档被完全加载和解析完成之后,DOMContentLoaded 事件被触发,而无需等待样式表、图像和子框架的完全加载。
document.onreadystatechange = function () {
  console.log(document.readyState)
}
//interactive、complete

if (document.readyState === "interactive") {
    DOMContentLoad();
    //代表HTML Dom结构完成,相当于jquery.ready。
  }
 if (document.readyState === "complete") {
    load();
    //所有加载资源与js脚本执行完毕,相当于jquery.load
  }

事件

  1. window.onload
  2. window.onbeforeunload
  3. window.onunload
  4. window.online、window.offline网络连接变化

location对象

提供当前窗口中加载文档的信息,以及通常的导航功能

console.log(document.location===window.location)//true,指向同一个对象

location对象属性

http://foouser:barpassword@ww.wx.com:80/wigD/?q=Javascript&num=10#contents
属性说明举例
href返回完整的URL,也是location.toString()返回值http ://foouser:barpassword@ww.wx.com:80/wigD/?q=Javascript#contents
origin返回URL的源地址,不包括端口号只读http ://ww.wx.com
protocol返回一个URL协议http:
host返回一个URL的主机名和端口ww.wx.com:80
hostname返回URL的主机名ww.wx.com
port返回一个URL服务器使用的端口号80
pathname返回的URL中的路径名。/wigD/
hash返回一个URL的锚部分#contents
search返回一个URL的查询部分,当多键值需要解析处理?q=Javascript&num=10
username域名前指定的用户名foouser
password域名前指定的密码barpassword
  • popstate: 每次地址改变时触发
  • pushSate和replaceState的时候不会触发该事件。只有当用户点击回退或前进按钮或者调用back , forward, go方法才会触发这个事件
window.addEventListener('popstate', (event) => {
  console.log("location: " + document.location + ", state: " + JSON.stringify(event.state));
});
history.pushState(state, title, url);
history.pushState({page: 1}, "title 1", "?page=1");
history.pushState({page: 2}, "title 2", "?page=2");
history.replaceState({page: 3}, "title 3", "?page=3");
history.back(); // Logs "location: http://example.com/example.html?page=1, state: {"page":1}"
history.back(); // Logs "location: http://example.com/example.html, state: null
history.go(2);  // Logs "location: http://example.com/example.html?page=3, state: {"page":3}
  • 除了hash以外的所有属性被修改,都会导致页面重新加载新的URL
  • 改变hash值:如果某个DOM元素恰好有hash对应的字符串ID,那么浏览器就会滚动到DOM元素出现在视口顶部,并在浏览历史中创建一条新记录
  • hashchange: 地址栏中hash值改变的时候会触发
  • pushState() 不会造成 hashchange 事件调用, 即使新的URL和之前的URL只是锚的数据不同。
window.addEventListener('hashchange', function() {
  console.log('The hash has changed!')
}, false);

location对象方法-请求网页

给window.location、location.href赋值等同于调用assign方法

location.assign("url");//设置当前文档的URL,启动导航到新的网页
location.replace();//相比assign,旧的URL不会出现在history对象的地址列表
location.reload(); 重载当前页面,传参true的时候直接请求服务器,跳过缓存

history对象

window.history 提供了操控浏览器历史记录的能力,可以确定历史记录中包含多少条目,并以编程实现在历史记录中导航,而且也可以修改历史记录


		history.back()---回退一个页面,相当于浏览器左上角的回退箭头
		history.forward()---前进一个页面,相当于浏览器左上角的前进箭头
		history.go():传一个整数位参数
		          1.正整数:向前跳指定页面的个数
				  2.负整数:向后跳指定页面的个数
 

历史状态管理

h5中提供了

  • pushState(添加浏览历史)
  • replaceState(修改当前浏览历史)
  • popState事件,加载的文档变化时,即在用户返回或前进进会被出发触发
history.pushState({page:1},"","hhh.html");//https://www.baidu.com/hhh.html
  • 首参state:一个与指定网址相关的状态对象,popstate事件触发时,该对象会传入回调函数中。如果不需要这个对象,此处可以填null
  • 状态对象可以是任何可以序列化的对象,采用html结构化克隆算法保存
  • Firefox将状态对象保存到用户的磁盘上,以便用户重新启动浏览器后可以将其还原
  • 状态对象的序列化存在640k个字符的大小限制,如果将序列化表示形式大于此状态的状态对象传递给pushState(),则该方法将引发异常。

  • 第二个参数 url:新的网址,浏览器的地址栏将显示这个网址。
  • 新的URL不必是绝对的。 如果是相对的,则相对于当前URL进行解析
  • 浏览器不会在调用pushState() 、replaceState()之后尝试加载此URL,而是在用户刷新、重新启动浏览器之后加载new URL。
  • 同源限制:新网址必须与当前网址相同 origin,否则pushState()将引发异常。【异常是因为origin只读】
  • 本质就是修改location的属性,同时拦截修改引起的页面重加载 在这里插入图片描述

对比修改hash值进行历史状态管理

调用 pushState() 和 window.location = "#foo" 基本上一样, 他们都会在当前的document中创建和激活一个新的历史记录。

  • pushState() 不会造成 hashchange 事件调用, 即使新的URL和之前的URL只是锚的数据不同。 pushState() 有以下优势:
  1. 新的URL可以是任何和当前URL同源的URL。设置 window.location 只会在你只设置锚的时候才会使当前的URL。
  2. 非强制修改URL。相反,设置 window.location = "#foo"; 仅仅会在锚的值不是#foo情况下创建一条新的历史记录。
  3. 可以在新的历史记录中通过首参关联任何数据,而window.location = "#foo"形式的操作,你只可以将所需数据写入锚的字符串中。

navigator对象

描述客户端

navigator对象属性

有很多,列举一i部分

  • appCodeName 返回浏览器的代码名
  • appName 返回浏览器的名称
  • appVersion 返回浏览器的平台和版本信息,包括操作系统
  • cookieEnabled 返回指明浏览器中是否启用 cookie 的布尔值
  • platform 返回运行浏览器的操作系统平台
  • userAgent 返回由客户机发送服务器的user-agent 头部的值
  • plugins 常用的插件检测 navigator.plugins

通过以下代码,自行查看

for (const pro in window.navigator){
    console.log(pro);//属性名
    console.log(window.navigator[pro]);//属性值
 }

在这里插入图片描述

注册处理程序

:把一个网站注册成处理某种特定类型信息应用程序

navigator.registerProtocolHandler(scheme, url, title);

让 web 站点为自身注册用于打开或处理特定 URL 方案(又名协议)的能力。通过此API可以允许Web邮件站点打开 mailto: URL,或让 VoIP 站点打开 tel: URL。

screen对象

客户端显示器的信息,信息通常用于评估浏览网站的设备信息 像素宽度、高度

availHeight	返回屏幕的高度(不包括Windows任务栏)
availWidth	返回屏幕的宽度(不包括Windows任务栏)
colorDepth	返回目标设备或缓冲器上的调色板的比特深度
height	返回屏幕的总高度
pixelDepth	返回屏幕的颜色分辨率(每象素的位数)
width	返回屏幕的总宽度

客户端检测

能力检测(特性检测)

检测浏览器是都支持某特性 e.g:IE5之前的版本没有document.getElementById()这个DOM方法

//除了 IE8 以及之前的版本,其他浏览器都会返回 true
function hasCreateElement(){
    return typeof document.createElement == "function";
}

用户代理检测

大部分开发者会分析window.navigator.userAgent返回的字符串,推断相关环境信息

  • 浏览器及其版本
  • 浏览器渲染引擎
  • 设备类型(桌面或者移动)
  • 设备生产商及其型号
  • 操作系统及其版本

GitHub上有维护频繁的第三方用户代理解析程序

使用pushState管理历史状态的例子