如何在不刷新页面的情况下使用 JavaScript 从 window.location (URL) 中删除哈希?

IT技术 javascript window.location fragment-identifier
2021-01-16 17:14:58

我有这样的 URL:http://example.com#something,如何删除#something,而不会导致页面刷新?

我尝试了以下解决方案:

window.location.hash = '';

但是,这不会#从 URL 中删除哈希符号

6个回答

如今,解决这个问题变得更加触手可及。HTML5历史API可以让我们操纵地址栏当前域范围内显示任何URL。

function removeHash () { 
    history.pushState("", document.title, window.location.pathname
                                                       + window.location.search);
}

工作演示:http : //jsfiddle.net/AndyE/ycmPt/show/

这适用于 Chrome 9、Firefox 4、Safari 5、Opera 11.50IE 10。对于不受支持的浏览器,你总是可以编写一个优雅的降级脚本,在可用的地方使用它:

function removeHash () { 
    var scrollV, scrollH, loc = window.location;
    if ("pushState" in history)
        history.pushState("", document.title, loc.pathname + loc.search);
    else {
        // Prevent scrolling by storing the page's current scroll offset
        scrollV = document.body.scrollTop;
        scrollH = document.body.scrollLeft;

        loc.hash = "";

        // Restore the scroll offset, should be flicker free
        document.body.scrollTop = scrollV;
        document.body.scrollLeft = scrollH;
    }
}

所以你可以去掉哈希符号,只是不是在所有浏览器中——还没有。

注意:如果要替换浏览器历史记录中的当前页面,请使用replaceState()代替pushState()

对于旧版本的 IE,您似乎需要使用 document.documentElement 而不是 document.body。请参阅此答案stackoverflow.com/a/2717272/359048
2021-03-12 17:14:58
使用这一行确保您不会丢失查询字符串: history.pushState("", document.title, window.location.pathname + window.location.search);
2021-03-17 17:14:58
我建议使用 replaceState 而不是 pushState,以免在浏览器历史记录中创建额外的条目。
2021-03-19 17:14:58
@Phil:感谢您指出这一点,我已经相应地更新了答案。我太习惯使用漂亮的 URL。
2021-03-28 17:14:58
@santiagoarizti:你说得对,我刚刚得出了同样的结论。我没有正确检查我编写的代码(7 年前!),并且错过了在删除散列时我也在切换按钮的状态。由于您正在手动更改哈希,因此我想您总是可以自己触发事件。
2021-04-05 17:14:58

初始问题:

window.location.href.substr(0, window.location.href.indexOf('#'))

或者

window.location.href.split('#')[0]

两者都将返回不带哈希值或后面任何内容的 URL。

关于您的编辑:

对 的任何更改都window.location将触发页面刷新。您可以在window.location.hash不触发刷新的情况下进行更改(尽管如果您的哈希与页面上的 id 匹配,窗口会跳转),但您无法摆脱哈希符号。选择哪个更糟糕......

最新答案

关于如何在不牺牲(完全重新加载或将井号留在那里)的情况做到这一点的正确答案在这里把这个答案留在这里,尽管它是 2009 年的原始答案,而利用新浏览器 API 的正确答案是 1.5 年后给出的。

没有页面重新加载 - 这就是问题所在。这不是答案,因为它需要/强制重新加载页面!
2021-03-11 17:14:58
这不是 OP 问题的答案。
2021-03-12 17:14:58
这完全是错误的,您可以更改 window.location.hash 并且不会触发刷新。
2021-03-26 17:14:58
@Evgeny——这就是我的回答。我明确说更改 window.location.hash 不会触发刷新。“您可以在不触发刷新的情况下更改 window.location.hash(尽管如果您的哈希与页面上的 id 匹配,则窗口会跳转)”。
2021-03-28 17:14:58
也认为它不应该是✓answer
2021-04-05 17:14:58

(太多答案是多余和过时的。)现在最好的解决方案是:

history.replaceState(null, null, ' ');
这种行为是否记录在某处?所有浏览器/版本都支持它吗?
2021-03-14 17:14:58
使用history.pushState(null, null, ' '),如果你想保留历史来代替。
2021-03-22 17:14:58
与此有关的问题以及其余的问题是它不会触发 onhashchange,即使散列现在是空的,而以前不是。
2021-03-30 17:14:58
在 TypeScript 中,第二个参数不允许为 null,因为该命令需要一个字符串。Mozilla 推荐空字符串。
2021-03-30 17:14:58
这可能是有用的解释传递nullstatetitle最终做参数。
2021-04-02 17:14:58

简单而优雅:

history.replaceState({}, document.title, ".");  // replace / with . to keep url
如果您想留在同一目录中,请使用点而不是斜线
2021-03-12 17:14:58
请更新答案至于@vahanpwns笔记,使用.替代/使用/将 url 更改为根路径。
2021-03-19 17:14:58
感谢您的回答,我history.replaceState({}, document.title, location.href.substr(0, location.href.length-location.hash.length));针对我的用例进行了修改
2021-03-28 17:14:58
我的用例也是替换而不是推送,但这对我来说更有意义: history.replaceState(null, document.title, location.pathname + location.search);
2021-04-04 17:14:58
这不会保留 url 查询。
2021-04-08 17:14:58

你可以这样做:

history.replaceState({}, document.title, window.location.href.split('#')[0]);
在任何一种情况下,加星标的答案对我都不起作用,但这个答案对我有用。谢谢!
2021-03-16 17:14:58