处理js中的URL锚更改事件


Answers:


126

Google自定义搜索引擎使用计时器来检查哈希值是否与之前的值相对应,而独立域中的子iframe会更新父级的位置哈希值,以包含iframe文档正文的大小。当计时器捕获到更改时,父级可以调整iframe的大小以匹配主体的iframe,以便不显示滚动条。

类似于以下内容可以达到相同目的:

var storedHash = window.location.hash;
window.setInterval(function () {
    if (window.location.hash != storedHash) {
        storedHash = window.location.hash;
        hashChanged(storedHash);
    }
}, 100); // Google uses 100ms intervals I think, might be lower

Google Chrome 5,Safari 5,Opera 10.60Firefox 3.6Internet Explorer 8 支持以下hashchange事件:

if ("onhashchange" in window) // does the browser support the hashchange event?
    window.onhashchange = function () {
        hashChanged(window.location.hash);
    }

并将其放在一起:

if ("onhashchange" in window) { // event supported?
    window.onhashchange = function () {
        hashChanged(window.location.hash);
    }
}
else { // event not supported:
    var storedHash = window.location.hash;
    window.setInterval(function () {
        if (window.location.hash != storedHash) {
            storedHash = window.location.hash;
            hashChanged(storedHash);
        }
    }, 100);
}

jQuery的也有一个插件,将检查hashchange事件,并提供了自己的如果需要的话- http://benalman.com/projects/jquery-hashchange-plugin/

编辑:更新了浏览器支持(再次)。


为了完整起见,请添加var storedHash = window.location.hash;到汇总汇总块中。顺便说一句:今天,我认为这就是polyfill。
Frank Nocke


@AndyE我确实读了答案,我错过了小纸条,而且我从未见过类似的事件hashChanged(storedHash);
Timo Huovinen 2013年

1
@TimoHuovinen:hashChanged在这种情况下,旨在成为开发人员使用此代码实现的功能。这里的答案仅说明了如何在onhashchange事件不可用的情况下如何监视哈希值的变化,并结合了基于事件和基于计时器的方法来提供一种通用解决方案。我的意思是,您链接到的答案在这里绝对没有添加任何答案;-)。它们提供了相同的基本信息,甚至提供了与Ben Alman的jQuery插件的链接。唯一的区别是,我在回答中提供了一个纯JS解决方案。
Andy E

1
我一直在寻找一些轻量级的JS路由器,但这做得很好。还消除了所有依赖关系:)
gskema 2014年

4

我建议使用addEventListener而不是覆盖window.onhashchange,否则您将阻止其他插件的事件。

window.addEventListener('hashchange', function() {
...
})

纵观当今全球浏览器的使用情况,不再需要回退。



2

根据我在其他SO问题中看到的,唯一可行的跨浏览器解决方案是计时器。例如查看此问题


1

(仅作记录。)YUI3“ hashchange”综合事件与接受的答案大致相同。

YUI().use('history-hash', function (Y) {
  Y.on('hashchange', function (e) {
    // Handle hashchange events on the current window.
  }, Y.config.win);
});

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.