当页面高度在运行时增加时,防止浏览器视口粘到底部?

时间:2017-08-25 08:33:34

标签: javascript css

现代浏览器似乎有一个功能,当页面高度增加时视口会粘到底部。实际发生的是,当初始位置处于(或非常接近)页面底部时,浏览器以与增加高度相同的速率滚动视口。这导致外观好像页面向上扩展而不是向下扩展。

如何使用CSS或JS为某个页面禁用此功能,以便页面始终在视觉上向下展开?

当然,当添加元素的高度展开动画时也会发生这种情况。出于这个原因,如果可能的话,我希望避免之后重置滚动位置以防止可见的跳跃。这个"功能的演示" (这似乎只在极少数条件下发生)与视口交互和下拉动画可以在下面的gif中观察到。

enter image description here

我知道必须有办法,否则每个有无限滚动的网站都会受到无限循环的影响。反驳论点:对于超过特定高度限制的容器,Chrome似乎不会这样做。因此,无限滚动网站甚至不会在他们的网站中解决这个问题。

5 个答案:

答案 0 :(得分:1)

你的意思是当你滚动到底部,并添加一段内容时,你会留在底部吗?因为解决方案非常简单:

选项1

  • 将当前的scrolloffset存储到顶部(例如,您向下滚动了多少个px)
  • 添加新内容
  • 将scrolloffset设置为顶部的存储值

最后两个步骤可以快速完成,用户不会注意到。

选项2

不是100%确定这是有效的,但我猜它确实如此:

  • 当访问者滚动到底部时,总是将它们向后滚动3px。这样,它们就不会在添加新内容的位置处于最底层,因此浏览器会保持原状。

答案 1 :(得分:1)

检查fiddle。您可以观察到,在Chrome中,第一个容器会捕捉到底部,而其他div则相对于顶部滚动。在Firefox或IE 11中,您无法观察到此行为。

当滚动容器上最后一个元素的上限位于容器的上限之上时,会发生这种情况。浏览器决定最后一个元素是用户感兴趣的元素,并决定留在该位置。

最后一个div没有捕捉到底部,因为滚动是相对于最后一个元素的上限发生的,而最后一个元素正在增长。

如果你想要一个不同的行为,我不会建议用Javascript处理它,但我建议你考虑这些规则改变你的布局。例如,最后一个div应该是增长的,而不是之前的兄弟。

强制性代码:



var div = document.querySelectorAll('.growing');
var height = 500;

setInterval(function(){
	height += 100; 
	div[0].style.height = height + 'px';
	div[1].style.height = height + 'px';
  div[2].style.height = height + 'px';
},1000);

.start, .end{
  height: 110px;
}
.start{
  background: red;
}
.end{
  background: green;
}
.growing{
  background: yellow;
}
.cnt1,.cnt2,.cnt3{
  overflow: auto;
  border: 5px solid black;
  margin: 5px 0;
  scroll-snap-type: mandatory;
}
.cnt1{
  height: 100px;
}

.cnt2{
  height: 120px;
}

.cnt3{
  height: 100px;
}

<div class="cnt1">
  <div class="start"></div>
  <div class="growing"></div>
  <div class="end"></div>
</div>
<div class="cnt2">
  <div class="start"></div>
  <div class="growing"></div>
  <div class="end"></div>
</div>

<div class="cnt3">
  <div class="start"></div>
  <div class="end"></div>
  <div class="growing">
    Content
  </div>
</div>
&#13;
&#13;
&#13;

修改 如果增长div的边界在可见区域,则滚动相对于增长div的顶部。所以你可以破解CSS来显示不断增长的div,但实际上并没有显示它。

在这个fiddle中,我使用了两种不同的CSS黑客。第一个是添加负边距底部和正面填充底部相同的数量。第二个黑客是将一个:after元素添加到不断增长的div中但隐藏其可见性。

答案 2 :(得分:1)

对于点击事件,请使用blur,避免使用scrollTo

似乎此问题与焦点有关。我遇到了一个类似的错误,当触发高度变化的元素切换为不可聚焦的元素(如div)时,屏幕跳转消失了。这显然不是一个很好的解决方案,因为我们应该能够使用按钮! focus也牵涉到这种奇怪的行为。进一步的实验导致触发元素在高度变化之前变得模糊,从而在不移动视口的情况下解决了该问题。我只尝试过点击事件,所以不确定是否可以将其拖放。

codepen that showcases viewport jumping with accordions and a blur fix

function handleClick(e) {
  e.currentTarget.blur();
  // code to change height
}

答案 3 :(得分:0)

根据我对您的要求的理解,我提供了一份有效的jsfiddle样本。

希望它会对你有所帮助。

如果您期待更多内容,请随时添加评论。

酷!

$(function(){
		var height = 200;
		var pos = 0;
		setInterval(function(){
			if($(document).height() >= $(window).height()){
				var height = $('.container1').height();
				$('.container1').height(height + 20);
				pos = pos + 20;
				$(window).scrollTop(pos);
			}			
		}, 1000);
	});
.container1 {
	border: 1px solid #ccc;
	min-height: 200px;
	background: #ccc;
	height: auto;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class="container1">
  <p>11</p>
  <p>12</p>
  <p>13</p>
</div>

答案 4 :(得分:0)

所有可拖动元素都在一个没有自动溢出的容器中,当您拖放元素时,整个页面会因拖动而滚动。

而不是那样做:

<div class="container">
   <!-- Place all your draggable elements here -->
</div>

将容器类的max-height和overflow设置为:

.container {
   max-height: 400px;
   overflow: auto;
}

现在,当您拖放元素而不是整个页面时,唯一的容器将会滚动。

实施此解决方案后,它将如下所示。

在拖动之前。 enter image description here

拖动时。 enter image description here

希望这会对你有所帮助。