我想在不重新加载文档的情况下更新window.location.search
,然后根据window.location.search
中更新的值执行函数。
当用户单击某个按钮时,该按钮的onclick
事件将触发以下函数:
window.history.pushState({action : 'myAction'}, document.title, '?action=myAction');
目前为止,一切都好。window.location.search
会在浏览器 URL 栏中更新。
但是我找不到检测到此更新的常规后台事件侦听器 - 类似于onhashchange
但用于查询字符串。
我能想到的最好的是:
window.history.pushState({action : 'myAction'}, document.title, '?action=myAction');
window.history.pushState({action : 'myAction'}, document.title, '?action=myAction');
window.history.back();
window.addEventListener('popstate', () => console.log(event.state.action));
这行得通,但我相信必须有一种更优雅的方法。
最终答案:
我对下面的第二次尝试答案非常满意。
但我真的不喜欢:
history.back();
history.forward();
我采用它来手动触发popstate
事件。
在实践中,我发现这个黑客有时有效,有时很慢,有时完全失败。
在纸面上,感觉太临时了。
经过反复搜索和试验(这很难找到(,我终于找到了手动触发popstate
事件的正确语法。
就像dispatching
这样简单:
new Event('popstate')
喜欢这个:
let myEvent = new Event('popstate');
window.dispatchEvent(myEvent);
所以最终的代码是:
window.history.pushState({action : 'myAction'}, document.title, '?action=myAction');
let queryStringChange = new Event('popstate');
window.dispatchEvent(queryStringChange);
我能想出的最佳答案(第二次尝试(:
基于以下内容:
我确信查询字符串只需要检查:
当页面加载或重新加载时;
调用
window.history.pushstate
时;或者当(正如@Kaiido下面的评论中敏锐地指出的那样(通过前进和后退按钮访问页面时
我也知道:
window.load
事件侦听器涵盖第 1 点;window.popstate
事件侦听器涵盖第 3 点。
这只剩下第 2 点。
处理第 2 点
正如MDN报道的那样:
请注意,只需调用
history.pushState()
或history.replaceState()
不会触发流行状态事件。popstate 事件将通过执行浏览器操作(例如单击后退或前进(来触发按钮(或在 JavaScript 中调用history.back()
或history.forward()
(。来源:https://developer.mozilla.org/en-US/docs/Web/API/Window/popstate_event
但这意味着而不是使用(如我第一次尝试,如下(:
window.history.pushState({action : 'myAction'}, document.title, '?action=myAction');
checkQueryString(); // DIRECT INVOCATION OF FUNCTION
我可以改用:
window.history.pushState({action : 'myAction'}, document.title, '?action=myAction');
history.back();
history.forward();
这意味着我现在可以允许覆盖第 3 点的同一window.popstate
事件侦听器完成其工作,从而为我提供更干净、逻辑上更分离的代码,而不是直接调用函数。
注意我发现...奇怪。。。仅按转发按钮将触发window.popstate
事件侦听器,但调用window.history.pushState()
不会...(需要紧随其后的添加history.back(); history.forward();
以复制前进按钮的功能(。
但是,如上所述,这是我能想到的最好、最干净、最优化(就逻辑分离和未来代码维护而言(的解决方案。如果有人有更好的主意,我很乐意转移绿色勾号。
第一次尝试回答:
我初步得出结论,没有办法使用后台事件侦听器来实现这种效果,该侦听器可以检测查询字符串何时更新。
相反,因为我确定查询字符串只需要检查:
- 当页面加载或重新加载时
- 调用
window.history.pushstate
时
我可以使用以下内容:
window.addEventListener('load', checkQueryString);
和
window.history.pushState({action : 'myAction'}, document.title, '?action=myAction');
checkQueryString();