How can I remove the location hash without causing the page to scroll?

主宰稳场 提交于 2019-11-27 17:09:24
scunliffe

I believe if you just put in a dummy hash it won't scroll as there is no match to scroll to.

<a href="#A4J2S9F7">No jumping</a>

or

<a href="#_">No jumping</a>

"#" by itself is equivalent to "_top" thus causes a scroll to the top of the page

I use the following on a few sites, NO PAGE JUMPS!

Nice clean address bar for HTML5 friendly browsers, and just a # for older browsers.

$('#logo a').click(function(e){
    window.location.hash = ''; // for older browsers, leaves a # behind
    history.pushState('', document.title, window.location.pathname); // nice and clean
    e.preventDefault(); // no page reload
});

window.location's hash property is stupid in a couple of ways. This is one of them; the other is that is has different get and set values:

window.location.hash = "hello";  // url now reads *.com#hello
alert(window.location.hash);   // shows "#hello", which is NOT what I set.
window.location.hash = window.location.hash; // url now reads *.com##hello

Note that setting the hash property to '' removes the hash mark too; that's what redirects the page. To set the value of the hash part of the url to '', leaving the hash mark and therefore not refreshing, write this:

window.location.href = window.location.href.replace(/#.*$/, '#');

There is no way to completely remove the hash mark once set without refreshing the page.

UPDATE 2012:

As Blazemonger and thinkdj have pointed out, technology has improved. Some browsers do allow you to clear that hashtag, but some do not. To support both, try something like:

if ( window.history && window.history.pushState ) { 
    window.history.pushState('', '', window.location.pathname) 
} else { 
    window.location.href = window.location.href.replace(/#.*$/, '#'); 
}

This is an old post but I wanted to share my solution All the links in my project that being handled by JS are having href="#_js" attribute (or whatever name you want to use for that purposes only), and on page initialization I do:

$('body').on('click.a[href="#_js"]', function() {
    return false;
});

That'll do the trick

Setting window.location.hash to empty or non-existing anchor name, will always force the page to jump to top. The only way to prevent this is to grab the scroll position of the window and set it to that position again after the hash change.

This will also force a repaint of the page (cant avoid it), though since it's executed in a single js process, it won't jump up/down (theoretically).

$('<a href="#123">').text('link').click(function(e) {
    e.preventDefault();
    window.location.hash = this.hash;
}).appendTo('body');

$('<a href="#">').text('unlink').click(function(e) {
    e.preventDefault();
    var pos = $(window).scrollTop(); // get scroll position
    window.location.hash = '';
    $(window).scrollTop(pos); // set scroll position back
}).appendTo('body');

Hope this helps.

I'm not sure if this produces the desired outcome, give it a shot:

$('<a href="#">').text('unlink').click(function(e) {
    e.preventDefault();
    var st = parseInt($(window).scrollTop())
    window.location.hash = '';
    $('html,body').css( { scrollTop: st });  
});

Basically save the scroll offset and restore it after assigning the empty hash.

Have you tried return false; in the event handler? jQuery does something special when you do that, similar to, but AFAIK more impactful, than e.preventDefault.

Hope this helps

html

<div class="tabs">
  <ul>
    <li><a href="#content1">Tab 1</a></li>
    <li><a href="#content2">Tab 2</a></li>
    <li><a href="#content3">Tab 3</a></li>
  </ul>
</div>
<div class="content content1">
    <p>1. Content goes here</p>
</div>
<div class="content content2">
    <p>2. Content goes here</p>
</div>
<div class="content content3">
    <p>3. Content goes here</p>
</div>

js

function tabs(){
  $(".content").hide();

  if (location.hash !== "") {
    $('.tabs ul li:has(a[href="' + location.hash + '"])').addClass("active");
    var hash = window.location.hash.substr(1);
    var contentClass = "." + hash;
    $(contentClass).fadeIn();
  } else {
    $(".tabs ul li").first().addClass("active");
    $('.tabs').next().css("display", "block");
  }
}
tabs();

$(".tabs ul li").click(function(e) {
  $(".tabs ul li").removeAttr("class");
  $(this).addClass("active");
  $(".content").hide();
  var contentClass = "." + $(this).find("a").attr("href").substr(1);
  $(contentClass).fadeIn();
  window.location.hash = $(this).find("a").attr("href");
  e.preventDefault();
  return false;
});

URL without any hash.
http://output.jsbin.com/tojeja

URL with hashtag that does not jumping to anchor.
http://output.jsbin.com/tojeja#content1

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!