【问题标题】:Detecting Back Button/Hash Change in URL检测 URL 中的后退按钮/哈希更改
【发布时间】:2010-09-15 10:28:09
【问题描述】:

我刚刚在http://ritter.vg 设置了我的新主页。我正在使用 jQuery,但非常少。
它使用 AJAX 加载所有页面 - 我将其设置为通过检测 URL 中的哈希来允许添加书签。

 //general functions
 function getUrl(u) {
      return u + '.html';
 }
 function loadURL(u)    {
      $.get(getUrl(u), function(r){
                $('#main').html(r);
           }
      );
 }
 //allows bookmarking
 var hash = new String(document.location).indexOf("#");
 if(hash > 0)
 {
      page = new String(document.location).substring(hash + 1);
      if(page.length > 1)
        loadURL(page);
      else
        loadURL('news');
 }
 else
      loadURL('news');

但我无法让后退和前进按钮工作。

有没有一种方法可以在不使用 setInterval 循环的情况下检测返回按钮何时被按下(或检测哈希何时更改)?当我尝试使用 0.2 秒和 1 秒的超时时,它与我的 CPU 挂钩。

【问题讨论】:

  • 而不是针对HTML4的hashchange事件;现在有 HTML5 History API 为其提供超级种子。 Here is a good reference.

标签: javascript ajax navigation fragment-identifier hashchange


【解决方案1】:

这里的答案都很老了。

在 HTML5 世界中,您应该使用 onpopstate 事件。

window.onpopstate = function(event)
{
    alert("location: " + document.location + ", state: " + JSON.stringify(event.state));
};

或者:

window.addEventListener('popstate', function(event)
{
    alert("location: " + document.location + ", state: " + JSON.stringify(event.state));
});

后者 sn-p 允许存在多个事件处理程序,而前者将替换任何可能导致难以发现的错误的现有处理程序。

【讨论】:

    【解决方案2】:

    改用jQuery hashchange event 插件。关于您的完整 ajax 导航,请尝试使用 SEO friendly ajax。否则,您的网页在有 JavaScript 限制的浏览器中不会显示任何内容。

    【讨论】:

    • 现在您可以使用 HTML5 API 来完成此操作。
    【解决方案3】:

    jQuery BBQ (Back Button & Query Library)

    一个高质量的基于哈希的浏览器历史插件和非常喜欢up-to-date (Jan 26, 2010) as of this writing (jQuery 1.4.1)

    【讨论】:

      【解决方案4】:

      HTML5 包含一个比使用 hashchange 更好的解决方案,它是 HTML5 状态管理 API - https://developer.mozilla.org/en/DOM/Manipulating_the_browser_history - 它们允许您更改页面的 url,而无需使用哈希!

      虽然 HTML5 状态功能仅适用于 HTML5 浏览器。因此,您可能想要使用类似 History.js 的东西,它为 HTML4 浏览器提供向后兼容的体验(通过哈希,但仍支持数据和标题以及 replaceState 功能)。

      您可以在此处阅读更多信息: https://github.com/browserstate/History.js

      【讨论】:

        【解决方案5】:

        另一个很棒的实现是 balupton 的 jQuery History,如果浏览器支持它,它将使用本机 onhashchange 事件,如果不支持,它将为浏览器使用适当的 iframe 或间隔,以确保成功模拟所有预期的功能。它还提供了一个很好的接口来绑定到某些状态。

        另一个值得注意的项目是jQuery Ajaxy,它几乎是 jQuery History 的一个扩展,用于添加 ajax。当您开始使用带有哈希的 ajax 时,它会得到 quite complicated!

        【讨论】:

          【解决方案6】:

          如果你想使用它,我会执行以下操作,然后将其粘贴到某个位置并将处理程序代码设置在 locationHashChanged(qs) 中的注释位置,然后在每次加载 ajax 请求时调用 changeHashValue(hashQuery)。 它不是一个快速修复的答案,也没有,所以你需要考虑它并将合理的 hashQuery 参数(即 a=1&b=2)传递给 changeHashValue(hashQuery),然后在你的 locationHashChanged 中满足所述参数的每个组合(qs) 回调 ...

          // Add code below ...
          function locationHashChanged(qs)
          {
            var q = parseQs(qs);
            // ADD SOME CODE HERE TO LOAD YOUR PAGE ELEMS AS PER q !!
            // YOU SHOULD CATER FOR EACH hashQuery ATTRS COMBINATION
            //  THAT IS PASSED TO changeHashValue(hashQuery)
          }
          
          // CALL THIS FROM YOUR AJAX LOAD CODE EACH LOAD ...
          function changeHashValue(hashQuery)
          {
            stopHashListener();
            hashValue     = hashQuery;
            location.hash = hashQuery;
            startHashListener();
          }
          
          // AND DONT WORRY ABOUT ANYTHING BELOW ...
          function checkIfHashChanged()
          {
            var hashQuery = getHashQuery();
            if (hashQuery == hashValue)
              return;
            hashValue = hashQuery;
            locationHashChanged(hashQuery);
          }
          
          function parseQs(qs)
          {
            var q = {};
            var pairs = qs.split('&');
            for (var idx in pairs) {
              var arg = pairs[idx].split('=');
              q[arg[0]] = arg[1];
            }
            return q;
          }
          
          function startHashListener()
          {
            hashListener = setInterval(checkIfHashChanged, 1000);
          }
          
          function stopHashListener()
          {
            if (hashListener != null)
              clearInterval(hashListener);
            hashListener = null;
          }
          
          function getHashQuery()
          {
            return location.hash.replace(/^#/, '');
          }
          
          var hashListener = null;
          var hashValue    = '';//getHashQuery();
          startHashListener();
          

          【讨论】:

          • 在使用锚点导航我的页面时,仅用于更改活动链接。
          【解决方案7】:

          尝试简单轻量级的PathJS lib。

          简单示例:

          Path.map("#/page").to(function(){
              alert('page!');
          });
          

          【讨论】:

            猜你喜欢
            • 2013-02-22
            • 1970-01-01
            • 2011-12-26
            • 1970-01-01
            • 2011-09-17
            • 1970-01-01
            • 2015-08-12
            • 1970-01-01
            相关资源
            最近更新 更多