防止 AJAX 中的滚动重置

Posted

技术标签:

【中文标题】防止 AJAX 中的滚动重置【英文标题】:Prevent scroll reset in AJAX 【发布时间】:2012-03-27 04:21:14 【问题描述】:

我有一个 div 容器,它通过一个 javascript 函数每 3 秒修改一次它的内容。该函数最初由body标签的onload事件调用。

function showNow()

    if (window.XMLHttpRequest)  // code for IE7+, Firefox, Chrome, Opera, Safari
       xmlhttp=new XMLHttpRequest();
     else  // code for IE6, IE5
      xmlhttp=new ActiveXObject("Microsoft.XMLHTTP");
    

    xmlhttp.onreadystatechange = function() 
        if (xmlhttp.readyState == 4 && xmlhttp.status == 200) 
            document.getElementById("txtHint").innerhtml = xmlhttp.responseText;
        
   ;

   xmlhttp.open("GET", "tab.php", true);
   xmlhttp.send();

   setTimeout(showNow, 3000);

内容每 3 秒刷新一次。唯一的问题是滚动位置被重置,因此我的页面跳回到开头。这极大地影响了可用性。

谁能提出解决方案?

【问题讨论】:

我不太确定何时重置卷轴。无论如何我可以检查这个吗? 我找到了罪魁祸首。问题是当代码被交换时, div 标签中没有内容。因此,卷轴向后移动。设置 div 标签的 height 属性是解决此问题的快速方法。 @Jeffrey 的解决方案“应该”在技术上有效。但它不是。也许有人可以对此有所了解! :) 【参考方案1】:

我是法国人,请原谅我的英语不好

我的页面上出现了同样的情况:当我点击链接时,XHR 请求将我的滚动重置为完全顶部。我发现了我的错误……一个非常愚蠢的错误…… 检查您的 HTML,如果您的“onClick”在 <a> 标记中,请检查您没有编写 <a href="#" onClick="myFunction()">... 那是我的错误,只是 <a onClick="myFunction()"> 不要重置滚动 x)

希望对你有所帮助

【讨论】:

一般推荐onclick事件处理器为“myfunction(); return false;”。 href 链接仍然可以是“#”【参考方案2】:

您可以使用window.scrollTo(x, y)设置滚动的位置,例如:

if (xmlhttp.readyState==4 && xmlhttp.status==200)

   document.getElementById("txtHint").innerHTML=xmlhttp.responseText;
   window.scrollTo(0, 0); //stay on the top

【讨论】:

+1 我忘了scrollTo 函数。除非,这可能仅适用于 window 对象。 感谢您的回答。我已经尝试过了,但它不起作用! :( 对不起,代码错误,你应该设置window.scrollTo(0, 0);但如果你解决了问题,那就太好了! :)【参考方案3】:

在设置 innerHTML 之前,您可以获得txtHint 元素的scrollTop 属性。然后,在添加文本后,再次将该变量设置为 scrollTop

if (xmlhttp.readyState==4 && xmlhttp.status==200)
  
    var scroll = document.body.scrollTop;
    document.getElementById("txtHint").innerHTML=xmlhttp.responseText;
    document.body.scrollTop = scroll;
 

【讨论】:

整个页面回到顶部。页面内没有可滚动的元素。 不,仍然没有快乐。顺便说一句,您刚才建议的方式与下面的felipeoriani建议的方式非常相似。 @Gowtham 是的。我只是假设您想要在内部弹出元素或其他东西上产生滚动效果。无论如何,该代码对我有用。您正在替换旧的if (xmlhttp.readyState==4 && xmlhttp.status==200) 块,对吗?另外,你用的是什么浏览器? 让我们continue this discussion in chat 我正在更换块。我在 IE 9、opera 和 chrome 上尝试了代码。【参考方案4】:

尝试添加

return false;

在 ajax 请求结束时

【讨论】:

【参考方案5】:

不确定是否已完全回答。

我遇到了同样的问题,尝试了以上所有解决方案都没有解决。我发现刷新innerHTML实际上使滚动条消失了很短的时间(因为随着内容的刷新,整个页面的高度变得更小了),随后当内容重新出现(和滚动条)时,浏览器有无法知道他在通话之前在哪里,因此一直向上滚动。

我自己的解决方案非常简单,不涉及捕获事件等...,我添加了一个我用 spacer.gif 填充的列,我打算刷新的 div 的高度。这样整个页面布局本身就不会真正被扭曲,滚动条即使在很短的时间内也不会消失。

<table  border="0" align="center" cellpadding="0" cellspacing="0">
  <tr>
    <td>
    <img src="/images/spacer.gif"  />   <-- adding the extra column to keep the height always the same.
    </td>
    <td>
      <div id="content">
        <script>loadnewusermenu()</script> <-- content getting refreshed
      </div>
    </td>
  </tr>
</table>

希望这是有道理的。 DjYoy

【讨论】:

以上是关于防止 AJAX 中的滚动重置的主要内容,如果未能解决你的问题,请参考以下文章

防止重复无限滚动ajax加载器

是否可以为特定的 jQuery Ajax 调用禁用 Turbolinks 以防止页面刷新和滚动?

UITableViewCell 内的 UITextField - 防止文本重置的方法

使用javascript重置元标记以防止其刷新页面

防止表视图被重用(MVVM)

如何防止AJAX服务器端传输?