为什么 Chrome for Mobile 不会重绘我的固定 header?
Why won't Chrome for Mobile redraw my fixed header?
我有一个 header,我想在滚动时控制它的可见性。向下滚动页面时,header 应该像任何元素一样运行。向上滚动页面时,无论页面位置如何,我都想在页面上升时显示 header 。通过观察 simple example.
可以最好地理解这种行为
我正在侦听滚动事件并更新固定位置 div 具有负的最高值:
$(function()
{
var $header = $("#header");
var $window = $(window);
var headerHeight = $header.outerHeight();
var headerY = $header.outerHeight();
var scrollY = $window.scrollTop();
$window.on("scroll", function()
{
headerY += scrollY - $window.scrollTop();
if (headerY > headerHeight)
{
headerY = headerHeight;
}
else if (headerY < 0)
{
headerY = 0;
}
$header.css(
{
top: headerY - headerHeight,
});
scrollY = $window.scrollTop();
});
});
但是,移动版 Chrome 中的行为完全不是我所期望的。 header 通常不会动画,并且会在遇到边界时立即出现或消失。当它制作动画时,性能会断断续续地不规则,并且通常只绘制一到三帧。使用桌面 Chrome 的移动仿真时不会出现此行为;它只发生在实际设备上。
这似乎只发生在处理页面顶部的固定位置元素时。如果我尝试以不同的方式更改固定元素,例如将其从侧面或底部移入,一切都会更接近预期。事实上,如果我改变固定位置的顶部元素和固定位置的侧元素,顶部元素的行为会更统一,like so.
为什么 Chrome 移动版在页面顶部的固定位置元素如此不稳定?有什么方法可以简洁地解释它吗?
这里有很多事情要做。移动设备不如台式机强大,动画有时可能显得迟钝。特别是当页面中涉及 CSS 个阴影时。
我不确定是什么原因导致的,但我会在 window.requestAnimationFrame
功能受支持时试一试(您需要检查是否支持旧版浏览器,例如 IE9)。
想法是只要移动 GPU 准备重绘(通常每 16.6 毫秒)就重绘屏幕,而不是用无法及时处理的请求淹没它。
所以我会尝试这样的事情(未测试):
$(function()
{
var $header = $("#header");
var $window = $(window);
var headerHeight = $header.outerHeight();
var headerY = $header.outerHeight();
var scrollY = $window.scrollTop();
var requestId;
$window.on("scroll", function()
{
//run only when no request is pending.
if (requestId === undefined) {
requestId = window.requestAnimationFrame(animateHeader);
}
});
function animateHeader() {
requestId = undefined;
headerY += scrollY - $window.scrollTop();
if (headerY > headerHeight)
{
headerY = headerHeight;
}
else if (headerY < 0)
{
headerY = 0;
}
$header.css(
{
top: headerY - headerHeight,
});
scrollY = $window.scrollTop();
}
});
由于我不确定这是否能解决任何问题,如果您尝试过后能给我一些反馈就好了!
- 编辑条件requestAnimationFrame应该被调用。
尝试使用一些硬件加速 CSS3 转换。不要使用 top
来定位您的元素,请尝试使用 transform:translateY
.
也尝试在 header 元素上添加 transform:translateZ(0)
。
我有一个 header,我想在滚动时控制它的可见性。向下滚动页面时,header 应该像任何元素一样运行。向上滚动页面时,无论页面位置如何,我都想在页面上升时显示 header 。通过观察 simple example.
可以最好地理解这种行为我正在侦听滚动事件并更新固定位置 div 具有负的最高值:
$(function()
{
var $header = $("#header");
var $window = $(window);
var headerHeight = $header.outerHeight();
var headerY = $header.outerHeight();
var scrollY = $window.scrollTop();
$window.on("scroll", function()
{
headerY += scrollY - $window.scrollTop();
if (headerY > headerHeight)
{
headerY = headerHeight;
}
else if (headerY < 0)
{
headerY = 0;
}
$header.css(
{
top: headerY - headerHeight,
});
scrollY = $window.scrollTop();
});
});
但是,移动版 Chrome 中的行为完全不是我所期望的。 header 通常不会动画,并且会在遇到边界时立即出现或消失。当它制作动画时,性能会断断续续地不规则,并且通常只绘制一到三帧。使用桌面 Chrome 的移动仿真时不会出现此行为;它只发生在实际设备上。
这似乎只发生在处理页面顶部的固定位置元素时。如果我尝试以不同的方式更改固定元素,例如将其从侧面或底部移入,一切都会更接近预期。事实上,如果我改变固定位置的顶部元素和固定位置的侧元素,顶部元素的行为会更统一,like so.
为什么 Chrome 移动版在页面顶部的固定位置元素如此不稳定?有什么方法可以简洁地解释它吗?
这里有很多事情要做。移动设备不如台式机强大,动画有时可能显得迟钝。特别是当页面中涉及 CSS 个阴影时。
我不确定是什么原因导致的,但我会在 window.requestAnimationFrame
功能受支持时试一试(您需要检查是否支持旧版浏览器,例如 IE9)。
想法是只要移动 GPU 准备重绘(通常每 16.6 毫秒)就重绘屏幕,而不是用无法及时处理的请求淹没它。
所以我会尝试这样的事情(未测试):
$(function()
{
var $header = $("#header");
var $window = $(window);
var headerHeight = $header.outerHeight();
var headerY = $header.outerHeight();
var scrollY = $window.scrollTop();
var requestId;
$window.on("scroll", function()
{
//run only when no request is pending.
if (requestId === undefined) {
requestId = window.requestAnimationFrame(animateHeader);
}
});
function animateHeader() {
requestId = undefined;
headerY += scrollY - $window.scrollTop();
if (headerY > headerHeight)
{
headerY = headerHeight;
}
else if (headerY < 0)
{
headerY = 0;
}
$header.css(
{
top: headerY - headerHeight,
});
scrollY = $window.scrollTop();
}
});
由于我不确定这是否能解决任何问题,如果您尝试过后能给我一些反馈就好了!
- 编辑条件requestAnimationFrame应该被调用。
尝试使用一些硬件加速 CSS3 转换。不要使用 top
来定位您的元素,请尝试使用 transform:translateY
.
也尝试在 header 元素上添加 transform:translateZ(0)
。