如何使用响应大小的图像防止卡顿并减少布局偏移?

Posted

技术标签:

【中文标题】如何使用响应大小的图像防止卡顿并减少布局偏移?【英文标题】:How can I prevent jank and reduce layout shift with responsive sized images? 【发布时间】:2021-01-10 03:46:14 【问题描述】:

我的网站上有很多各种尺寸的图片。这些图像是响应式的,并且在从桌面到移动的所有浏览器宽度下都会改变大小。我在我的 Google Search Console 中看到我的 CLS(累积布局偏移)很差,只有 0.25 秒。我的网站布局会随着图片的加载而变化。

由于我的图像是响应式的,我无法指定图像的确切尺寸,也无法使用占位符来保留空间。

用响应式图像防止 CLS 的现代方法是什么?

此处布局:https://jsfiddle.net/exspwgab/


更新:我在互联网上尝试了一个建议,即在 img 标签中指定图像文件的宽度和高度,例如:

<img src="photo.jpg"  >

然后在 CSS 中你这样做:

width: 100%;
height: auto;

这似乎不适用于任何浏览器。加载图像时,我网页上的元素仍然到处移动。

如果有人有适用于所有浏览器的解决方案,请告诉我。我基本上需要占位符来在图像加载时保留空间,以防止页面卡顿问题。

我的响应式布局的 JSFiddle 在这里: https://jsfiddle.net/exspwgab/

【问题讨论】:

请在这里找到推荐:web.dev/optimize-cls 我尝试在图像标签中应用宽度和高度,然后在 CSS 中设置宽度:100% 和高度:自动,但由于某种原因会破坏 Safari 上的图像。目前我必须将宽度和高度设置为 100% 才不会破坏我的布局。 【参考方案1】:

我不确定这是否正是 CLS 问题的“现代解决方案”,但只是尽我所能提供帮助。

显然,为响应式图像元素放置固定大小的占位符在逻辑上是不可能的。如果我们为响应式内容使用固定大小的占位符/元素会怎样?

例如:

img.placeholder-image 
    width: 100%;
    height: 256px;
    object-fit: contain; 

使用固定高度,即使视口调整大小,此元素也不会对 CLS 策略产生任何负面影响,同时将整个图像内容保留在元素本身内。

我非常建议您考虑使用&lt;div&gt;s 而不是&lt;image&gt; 元素来显示图像内容(使用background 属性),但是,我不能保证这不是再次违反审计规则。

我的两分钱。

【讨论】:

【参考方案2】:

html

<img   src="300x450.jpg">

CSS:

    img 
        height: auto;
        aspect-ratio: 2/3;
        max-width: 100%;
    

目标浏览器:

铬 88+ Edge 88+

文章:

MDN Caniuse

【讨论】:

这需要解释一下【参考方案3】:

我遇到了同样的问题。 解决方案是将width: 100% 更改为max-width: 100%

https://web.dev/optimize-cls/ 上已隐含说明

img 
 width: 100%; /* or max-width: 100%; */
 height: auto;

【讨论】:

【参考方案4】:

如果你需要做你正在做的事……别担心。

识别您网站潜在问题的工具不了解上下文。例如,假设我的网站有一个巨大的 20 MB 图像,加载需要几秒钟。谷歌的工具无疑会将此标记为一个问题。但是,也许在我的示例中,我的网站正在托管科学图像或需要无损大图像大小的东西。我的用户很乐意花几秒钟时间加载他们需要的数据。

如果您的网站布局要求您加载然后动态调整大小的图像,那么这就是它所需要的,您不必担心。

【讨论】:

我喜欢你的回复。但是,我同意 Google 的观点,即“累积页面移位”不是一个很好的体验,我想以某种方式为图像设置占位符,这样我的页面就不会随着图像加载到页面上而发生大量移动。目前,图像的所有标题/说明会随着页面加载而变化,看起来很卡。 @javinladish 没有看到您的代码或具体示例,很难向您建议什么。没有单一的解决方案。 我会做一个JSFiddle @javinladish 听起来不错。可能还值得查看您的布局的屏幕截图。通常,您只需做一些根本不同的事情,但有时也有解决方法。 这是我正在使用的确切布局jsfiddle.net/exspwgab【参考方案5】:

我最终使用了此处找到的解决方案: http://davidecalignano.it/lazy-loading-with-responsive-images-and-unknown-height/#:~:text=And%20here%20is%20the%20formula,flashes%20on%20lazy%20loaded%20images.

HTML

<a class="thumb lazy-container" href="#">
 <img class="lazy" data-original="image.jpg" >
</a>

CSS

.lazy-container 
 display: block;
 position: relative;
 height: 0;


.post .lazy-container 
 padding-bottom: 55.3%;


.lazy-container img 
 position: absolute;
 top: 0;
 left: 0;
 width: 100%;
 height: 100%;

由于我所有的图像都有不同的高度,我将填充底部百分比作为每个图像的内联样式。

【讨论】:

链接无效。

以上是关于如何使用响应大小的图像防止卡顿并减少布局偏移?的主要内容,如果未能解决你的问题,请参考以下文章

如何防止 iOS 上的浏览​​器调整图像大小?

增加内容大小时如何防止内容偏移

如何防止 UIImageView 使用 Autolayout 调整大小

如何使用自动布局调整情节提要的图像大小?

响应式设计:如何调整图像/背景图像的大小并垂直对齐 div?

使用 flexbox 如何防止特定元素继承 flex 布局?