关于路由hash和history

一、Location

Location 接口表示其链接到的对象的位置(URL)。所做的修改反映在与之相关的对象上。 DocumentWindow 接口都有这样一个链接的Location,分别通过 Document.locationWindow.location 访问。

Location是在document和window上访问的是一致的。

1.1 document.location

其中,对于 document.location ,为只读属性,但能赋予url值改变链接。

document.location = 'http://www.example.com'
// Equivalent to:
document.location.href = 'http://www.example.com'。

如果只是想获取字符串形式的 URL,可以使用只读属性 document.URL

document.location.href
//"https://developer.mozilla.org/zh-cn/docs/Web/API/Location"
document.URL
//"https://developer.mozilla.org/zh-cn/docs/Web/API/Location"
//以上 is equivalent

1.2 属性

Location 对象属性

属性 描述
hash 返回一个URL的锚部分
host 返回一个URL的主机名和端口
hostname 返回URL的主机名
href 返回完整的URL
pathname 返回的URL路径名。
port 返回一个URL服务器使用的端口号
protocol 返回一个URL协议
search 返回一个URL的查询部分

Location 对象方法

方法 说明
assign() 载入一个新的文档
reload() 重新载入当前文档
replace() 用新的文档替换当前文档(无法返回前页)

1.3 锚点

HTML5中a标签的锚点使用

location的hash值,实际上就是锚点

锚点通过a链接实现,html5之前的版本,通过a链接上的name属性(只有a才能使用该属性,其他无效。)

eg:

<body>
  <a href="#d3">我在找OA系统</a><br/>
  <a name="d1">禅道项目管理软件</a>
  <a name="d2">蝉知企业门户系统</a>
  <a name="d3">然之协同办公系统</a>
</body>

html5不兼容name属性了,使用id,表示任何元素都可以作为锚点跳转了。

eg.

<body>
  <a href="#d3">我在找OA系统</a><br/>
  <a id="d1">禅道项目管理软件</a>
  <a id="d2">蝉知企业门户系统</a>
  <h3 id="d3">然之协同办公系统</h3>
</body>

1.4 window.onhashchange

hash变化不会刷新页面,也就不会向后端请求数据,因此可以通过window.onhashchange 来监听hash的变化。

二、history

History 接口允许操作浏览器的 曾经在标签页或者框架里访问的会话历史记录。

1.1 属性

History.length 只读

返回一个整数,该整数表示会话历史中元素的数目,包括当前加载的页。例如,在一个新的选项卡加载的一个页面中,这个属性返回1。

History.scrollRestoration

允许Web应用程序在历史导航上显式地设置默认滚动恢复行为。此属性可以是自动的(auto)或者手动的(manual)。

History.state 只读

返回一个表示历史堆栈顶部的状态的值。这是一种可以不必等待popstate 事件而查看状态的方式。

1.2 方法

在HTML4中,已经支持window.history对象来控制页面历史记录跳转,常用的方法包括:

  • history.forward(); //在历史记录中前进一步
  • history.back(); //在历史记录中后退一步
  • history.go(n): //在历史记录中跳转n步骤,n=0为刷新本页,n=-1为后退一页。

在HTML5中,window.history对象得到了扩展,新增的API包括:

  • history.pushState(data[,title[,url]);//向历史记录中追加一条记录
  • history.replaceState(data[,title[,url]);//替换当前页在历史记录中的信息。
  • history.state;//是一个属性,可以得到当前页的state信息。

注意:pushState和replaceState不会立刻刷新页面

1、pushState

HTML 文档中,history.pushState() 方法向当前浏览器会话的历史堆栈中添加一个状态(state)。

从某种程度来说, 调用 pushState()window.location = "#foo"基本上一样, 他们都会在当前的document中创建和激活一个新的历史记录。但是 pushState() 有以下优势:

  • 新的URL可以是任何和当前URL同源的URL。但是设置 window.location 只会在你只设置锚的时候才会使当前的URL。
  • 非强制修改URL。相反,设置 window.location = "#foo"; 仅仅会在锚的值不是#foo情况下创建一条新的历史记录。
  • 可以在新的历史记录中关联任何数据。window.location = "#foo"形式的操作,你只可以将所需数据写入锚的字符串中。

注意: pushState() 不会造成 hashchange 事件调用, 即使新的URL和之前的URL只是锚的数据不同。

2、replaceState

replaceState会用新的url替换当前的url,但不会刷新,即使新的url不存在。

eg:

假设 http://mozilla.org/foo.html 执行下面的 JavaScript 代码:

var stateObj = { foo: "bar" };
history.pushState(stateObj, "", "bar.html");

上面这两行的解释可以在 "Example of pushState() method"这个章节找到。然后假设 http://mozilla.org/bar.html 执行下面的 JavaScript 代码:

history.replaceState(stateObj, "", "bar2.html");

这会让URL栏显示 http://mozilla.org/bar2.html, 但是不会刷新 bar2.html 页面 甚至不会检查bar2.html 是否存在

假设用户跳转到 http://www.microsoft.com, 然后点击返回按钮.这时, URL 栏将会显示 http://mozilla.org/bar2.html 页面. 如果用户此时点击返回按钮, URL栏将会显示 http://mozilla.org/foo.html 页面, 最终绕过了 bar.html 页面.

1.3 window.onpopstate

在点击浏览器后退按钮或js调用forward()、back()、go()时触发。监听函数中可传入一个event对象,event.state即为通过pushState()或replaceState()方法传入的data参数

调用history.pushState()或者history.replaceState()不会触发popstate事件. popstate事件只会在浏览器某些行为下触发, 比如点击后退、前进按钮(或者在JavaScript中调用history.back()、history.forward()、history.go()方法),此外,a 标签的锚点也会触发该事件。

注意:锚点改变和pathname改变都会触发onpopstate方法,但是,改变path(replaceState和pushState)不会触发hashchange。

三、比较popstate 和 hashchange

四、hash模式和history模式

两种前端路由(hash模式和history模式)实现原理解析及区别

posted @ 2021-09-01 17:05  Little_lion  阅读(83)  评论(0)    收藏  举报