add support for route state #1480
This commit is contained in:
parent
75e83ea565
commit
de07a54881
10 changed files with 367 additions and 196 deletions
|
|
@ -13,7 +13,7 @@ module.exports = function(options) {
|
|||
var search = ""
|
||||
var hash = ""
|
||||
|
||||
var past = [], future = []
|
||||
var past = [{url: getURL(), isNew: true, state: null, title: null}], future = []
|
||||
|
||||
function getURL() {
|
||||
if (protocol === "file:") return protocol + "//" + pathname + search + hash
|
||||
|
|
@ -42,7 +42,7 @@ module.exports = function(options) {
|
|||
if (typeof $window.onhashchange === "function") $window.onhashchange({type: "hashchange"})
|
||||
}
|
||||
function popstate() {
|
||||
if (typeof $window.onpopstate === "function") $window.onpopstate({type: "popstate"})
|
||||
if (typeof $window.onpopstate === "function") $window.onpopstate({type: "popstate", state: $window.history.state})
|
||||
}
|
||||
function unload() {
|
||||
if (typeof $window.onunload === "function") $window.onunload({type: "unload"})
|
||||
|
|
@ -135,20 +135,22 @@ module.exports = function(options) {
|
|||
},
|
||||
}
|
||||
$window.history = {
|
||||
pushState: function(data, title, url) {
|
||||
past.push({url: getURL(), isNew: false})
|
||||
pushState: function(state, title, url) {
|
||||
past.push({url: getURL(), isNew: false, state: state, title: title})
|
||||
future = []
|
||||
setURL(url)
|
||||
},
|
||||
replaceState: function(data, title, url) {
|
||||
future = []
|
||||
replaceState: function(state, title, url) {
|
||||
var entry = past[past.length - 1]
|
||||
entry.state = state
|
||||
entry.title = title
|
||||
setURL(url)
|
||||
},
|
||||
back: function() {
|
||||
var entry = past.pop()
|
||||
if (entry != null) {
|
||||
if (past.length > 1) {
|
||||
var entry = past.pop()
|
||||
if (entry.isNew) unload()
|
||||
future.push({url: getURL(), isNew: false})
|
||||
future.push({url: getURL(), isNew: false, state: entry.state, title: entry.title})
|
||||
setURL(entry.url)
|
||||
if (!entry.isNew) popstate()
|
||||
}
|
||||
|
|
@ -157,11 +159,14 @@ module.exports = function(options) {
|
|||
var entry = future.pop()
|
||||
if (entry != null) {
|
||||
if (entry.isNew) unload()
|
||||
past.push({url: getURL(), isNew: false})
|
||||
past.push({url: getURL(), isNew: false, state: entry.state, title: entry.title})
|
||||
setURL(entry.url)
|
||||
if (!entry.isNew) popstate()
|
||||
}
|
||||
},
|
||||
get state() {
|
||||
return past.length === 0 ? null : past[past.length - 1].state
|
||||
},
|
||||
}
|
||||
$window.onpopstate = null,
|
||||
$window.onhashchange = null,
|
||||
|
|
|
|||
|
|
@ -417,6 +417,71 @@ o.spec("pushStateMock", function() {
|
|||
$window.history.pushState(null, null, "b")
|
||||
$window.history.back()
|
||||
})
|
||||
o("replaceState does not break forward history", function() {
|
||||
$window.onpopstate = o.spy()
|
||||
|
||||
$window.history.pushState(null, null, "b")
|
||||
$window.history.back()
|
||||
|
||||
o($window.onpopstate.callCount).equals(1)
|
||||
o($window.location.href).equals("http://localhost/")
|
||||
|
||||
$window.history.replaceState(null, null, "a")
|
||||
|
||||
o($window.location.href).equals("http://localhost/a")
|
||||
|
||||
$window.history.forward()
|
||||
|
||||
o($window.onpopstate.callCount).equals(2)
|
||||
o($window.location.href).equals("http://localhost/b")
|
||||
})
|
||||
o("pushstate retains state", function() {
|
||||
$window.onpopstate = o.spy()
|
||||
|
||||
$window.history.pushState({a: 1}, null, "#a")
|
||||
$window.history.pushState({b: 2}, null, "#b")
|
||||
|
||||
o($window.onpopstate.callCount).equals(0)
|
||||
|
||||
$window.history.back()
|
||||
|
||||
o($window.onpopstate.callCount).equals(1)
|
||||
o($window.onpopstate.args[0].type).equals("popstate")
|
||||
o($window.onpopstate.args[0].state).deepEquals({a: 1})
|
||||
|
||||
$window.history.back()
|
||||
|
||||
o($window.onpopstate.callCount).equals(2)
|
||||
o($window.onpopstate.args[0].type).equals("popstate")
|
||||
o($window.onpopstate.args[0].state).equals(null)
|
||||
|
||||
$window.history.forward()
|
||||
|
||||
o($window.onpopstate.callCount).equals(3)
|
||||
o($window.onpopstate.args[0].type).equals("popstate")
|
||||
o($window.onpopstate.args[0].state).deepEquals({a: 1})
|
||||
|
||||
$window.history.forward()
|
||||
|
||||
o($window.onpopstate.callCount).equals(4)
|
||||
o($window.onpopstate.args[0].type).equals("popstate")
|
||||
o($window.onpopstate.args[0].state).deepEquals({b: 2})
|
||||
})
|
||||
o("replacestate replaces state", function() {
|
||||
$window.onpopstate = o.spy(pop)
|
||||
|
||||
$window.history.replaceState({a: 1}, null, "a")
|
||||
|
||||
o($window.history.state).deepEquals({a: 1})
|
||||
|
||||
$window.history.pushState(null, null, "a")
|
||||
$window.history.back()
|
||||
|
||||
function pop(e) {
|
||||
o(e.state).deepEquals({a: 1})
|
||||
o($window.history.state).deepEquals({a: 1})
|
||||
}
|
||||
})
|
||||
})
|
||||
o.spec("onhashchance", function() {
|
||||
o("onhashchange triggers on location.href change", function() {
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue