每个响应式网站开发教程都建议使用display:none
CSS 属性来隐藏移动浏览器加载的内容,以便网站加载更快。这是真的吗?不display:none
加载图像还是仍然在移动浏览器上加载内容?有什么方法可以防止在移动浏览器上加载不必要的内容?
18 回答
浏览器变得越来越智能。今天,如果您的浏览器(取决于版本)可以确定它没有用,它可能会跳过图像加载。
图像具有display:none
样式,但脚本可以读取其大小。如果父级隐藏,Chrome v68.0 不会加载图像。
你可以在那里查看:http: //jsfiddle.net/tnk3j08s/
您也可以通过查看浏览器开发人员工具的“网络”选项卡来检查它。
请注意,如果浏览器位于小型 CPU 计算机上,则不必渲染图像(和布局页面)将使整个渲染操作更快,但我怀疑这在今天是否真正有意义。
如果您想阻止加载图像,您可能根本不将 IMG 元素添加到文档中(或将 IMGsrc
属性设置为"data:"
或"about:blank"
)。
如果您在 CSS 中将图像设置为 div 的背景图像,则当该 div 设置为“display: none”时,图像将不会加载。当 CSS 被禁用时,它仍然不会加载,因为 CSS 被禁用了。
答案并不像简单的是或否那么简单。看看我最近做的一个测试的结果:
- 在 Chrome 中:加载所有 8 个屏幕截图-* 图像 (img 1)
- 在 Firefox 中:仅加载了当前显示的 1 个屏幕截图-* 图像 (img 2)
所以在进一步挖掘之后我发现了这个,它解释了每个浏览器如何处理加载基于 css display: none; 的 img 资产。
摘自博客文章:
- Chrome 和 Safari (WebKit):
WebKit 每次都会下载文件,除非通过不匹配的媒体查询应用背景。- Firefox:
如果样式被隐藏,Firefox 将不会下载带有背景图像的图像,但它们仍会从 img 标签下载资源。- Opera:
与 Firefox 一样,Opera 不会加载无用的背景图像。- Internet Explorer:
IE,像 WebKit 一样会下载背景图像,即使它们有 display: none; IE6 出现了一些奇怪的东西:带有背景图像和显示的元素:将不会下载内联设置...但如果这些样式未内联应用,它们将会是。
HTML5<picture>
标签将帮助您根据屏幕宽度解析正确的图像源
显然浏览器的行为在过去 5 年中没有太大变化,许多人仍然会下载隐藏的图像,即使display: none
它们上设置了属性。
即使有媒体查询解决方法,它也只有在图像被设置为 CSS 中的背景时才有用。
虽然我认为这个问题只有一个 JS 解决方案(延迟加载、图片填充等),但似乎有一个很好的纯 HTML 解决方案,它是开箱即用的 HTML5。
那就是<picture>
标签。
MDN是这样描述它的:
HTML
<picture>
元素是一个容器,用于为其中包含<source>
的特定元素指定多个元素<img>
。浏览器将根据页面的当前布局(图像将出现的框的约束)和将在其上显示的设备(例如普通或 hiDPI 设备)选择最合适的来源。
以下是如何使用它:
<picture>
<source srcset="mdn-logo-wide.png" media="(min-width: 600px)">
<img src="mdn-logo-narrow.png" alt="MDN">
</picture>
背后的逻辑
img
仅当没有任何媒体规则适用时,浏览器才会加载标签的来源。当<picture>
浏览器不支持该元素时,它将再次回退到显示img
标签。
通常,您会将最小的图像作为来源,<img>
因此不会为较大的屏幕加载重图像。反之亦然,如果媒体规则适用,<img>
则不会下载源代码,而是下载相应<source>
标签的 url 内容。
这里唯一的陷阱是,如果浏览器不支持该元素,它只会加载小图像。另一方面,在 2017 年,我们应该以移动优先的方式思考和编码。
在有人过于退出之前,这是当前浏览器支持的<picture>
:
桌面浏览器
移动浏览器
有关浏览器支持的更多信息,您可以在Can I use上找到。
好消息是html5please的语句是将它与后备一起使用。我个人打算听取他们的建议。
有关标签的更多信息,您可以在W3C 的规范中找到。那里有一个免责声明,我觉得很重要:
该元素与外观相似的
picture
元素有些不同。虽然它们都包含元素,但当元素嵌套在元素中时,源元素的属性没有意义,并且资源选择算法不同。同样,元素本身不显示任何内容。它只是为其包含的元素提供一个上下文,使其能够从多个 URL 中进行选择。video
audio
source
src
picture
picture
img
所以它说的是,它只通过为图像提供一些上下文来帮助您提高加载图像时的性能。
你仍然可以使用一些 CSS 魔法来隐藏小型设备上的图像:
<style>
picture { display: none; }
@media (min-width: 600px) {
picture {
display: block;
}
}
</style>
<picture>
<source srcset="the-real-image-source" media="(min-width: 600px)">
<img src="a-1x1-pixel-image-that-will-be-hidden-in-the-css" alt="MDN">
</picture>
因此浏览器不会显示实际图像,只会下载1x1
像素图像(如果您多次使用它可以缓存)。但是请注意,如果<picture>
浏览器不支持该标签,即使在桌面屏幕上,也不会显示实际图像(因此您肯定需要一个 polyfill 备份)。
** 2019 年答案**
在正常情况下display:none
不会阻止图像被下载
/*will be downloaded*/
#element1 {
display: none;
background-image: url('https://picsum.photos/id/237/100');
}
但是如果祖先元素有,display:none
那么后代的图像将不会被下载
/* Markup */
<div id="father">
<div id="son"></div>
</div>
/* Styles */
#father {
display: none;
}
/* #son will not be downloaded because the #father div has display:none; */
#son {
background-image: url('https://picsum.photos/id/234/500');
}
其他阻止图片下载的情况:
1-目标元素不存在
/* never will be downloaded because the target element doesn't exist */
#element-dont-exist {
background-image: url('https://picsum.photos/id/240/400');
}
2- 两个相等的类加载不同的图像
/* The first image of #element2 will never be downloaded because the other #element2 class */
#element2 {
background-image: url('https://picsum.photos/id/238/200');
}
/* The second image of #element2 will be downloaded */
#element2 {
background-image: url('https://picsum.photos/id/239/300');
}
是的,它会渲染得更快一点,只是因为它不需要渲染图像,而且在屏幕上排序的元素少了一个。
如果您不想加载它,请将 DIV 留空,以便稍后将包含<img>
标签的 html 加载到其中。
尝试使用我之前提到的 firebug 或 wireshark,你会看到即使display:none
存在文件也会被传输。
如果显示设置为无,Opera 是唯一不会加载图像的浏览器。Opera 现在已经转移到 webkit 并且将渲染所有图像,即使它们的显示设置为无。
这是一个可以证明这一点的测试页面:
当图像具有
display: none
或位于带有 的元素中时display:none
,浏览器可能会选择不下载图像,直到将display
设置为另一个值。
display
当您切换到时,只有 Opera 会下载图像block
。所有其他浏览器都会立即下载它。
如果 div 设置为“display:none”,则会加载div 元素的背景图像。
无论如何,如果同一个 div 有一个父级并且该父级设置为 'display:none',则子元素的背景图像将不会加载。:)
使用引导程序的示例:
<link href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap.min.css" rel="stylesheet" integrity="sha384-BVYiiSIFeK1dGmJRAkycuHAHRg32OmUcww7on3RYdg4Va+PmSTsz/K68vbdEjh4u" crossorigin="anonymous">
<div class="col-xs-12 visible-lg">
<div style="background-image: url('http://via.placeholder.com/300x300'); background-repeat:no-repeat; height: 300px;">lg</div>
</div>
<div class="col-xs-12 visible-md">
<div style="background-image: url('http://via.placeholder.com/200x200'); background-repeat:no-repeat; height: 200px;">md</div>
</div>
<div class="col-xs-12 visible-sm">
<div style="background-image: url('http://via.placeholder.com/100x100'); background-repeat:no-repeat; height: 100px">sm</div>
</div>
<div class="col-xs-12 visible-xs">
<div style="background-image: url('http://via.placeholder.com/50x50'); background-repeat:no-repeat; height: 50px">xs</div>
</div>
即使后者直接或间接隐藏在display: none
属性中,浏览器似乎仍然会下载图像。
我发现防止这种情况发生的唯一标准方法是使用标签loading
的属性:img
<img src="https://cdn.test/img.jpg" loading="lazy">
所有最新的浏览器都支持它,除了 Safari 和 Firefox Android。
如果您在 CSS 中将图像设置为 div 的背景图像,则当该 div 设置为“显示:无”时,图像将不会加载。
只是扩展布伦特的解决方案。
您可以为纯 CSS 解决方案执行以下操作,它还使 img 框实际上在响应式设计设置中表现得像一个 img 框(这就是透明 png 的用途),如果您的设计使用响应式动态 - 这尤其有用 -调整图像大小。
<img style="display: none; height: auto; width:100%; background-image:
url('img/1078x501_1.jpg'); background-size: cover;" class="center-block
visible-lg-block" src="img/400x186_trans.png" alt="pic 1 mofo">
仅当触发与 visible-lg-block 相关的媒体查询并将 display:none 更改为 display:block 时,才会加载图像。透明 png 用于允许浏览器在流畅的设计(高度:自动;宽度:100%)中为您的 <img> 块(以及背景图像)设置适当的高度:宽度比率。
1078/501 = ~2.15 (large screen)
400/186 = ~2.15 (small screen)
因此,对于 3 个不同的视口,您最终会得到如下所示的内容:
<img style="display: none; height: auto; width:100%; background-image: url('img/1078x501_1.jpg'); background-size: cover;" class="center-block visible-lg-block" src="img/400x186_trans.png" alt="pic 1">
<img style="display: none; height: auto; width:100%; background-image: url('img/517x240_1.jpg'); background-size: cover;" class="center-block visible-md-block" src="img/400x186_trans.png" alt="pic 1">
<img style="display: none; height: auto; width:100%; background-image: url('img/400x186_1.jpg'); background-size: cover;" class="center-block visible-sm-block" src="img/400x186_trans.png" alt="pic 1">
并且仅在初始加载期间加载您的默认媒体视口大小图像,然后根据您的视口,图像将动态加载。
而且没有javascript!
如果是这样,有没有办法不在移动浏览器上加载不必要的内容?
利用<img src="" srcset="">
http://www.webdesignerdepot.com/2015/08/the-state-of-responsive-images/
为了防止获取资源,请使用<template>
Web Components 的元素。
不会。如果您考虑节省手机用户带宽,图像将照常加载并且仍将使用用户的带宽。您可以做的是使用媒体查询并过滤您希望加载图像的设备。您的图像必须设置为 div 等的背景图像,而不是标签,因为无论屏幕大小和媒体查询设置如何,图像标签都会加载图像。
大家好,我在同样的问题上苦苦挣扎,如何不在移动设备上加载图像。
但我想出了一个很好的解决方案。首先制作一个img标签,然后在src属性中加载一个空白svg。现在您可以将图像的 URL 设置为带有内容的内联样式:url('link to your image');。现在将您的 img 标签包装在您选择的包装器中。
<div class="test">
<img src="data:image/svg+xml,%3Csvg%20xmlns=%22http://www.w3.org/2000/svg%22/%3E" style="content:url('https://blog.prepscholar.com/hubfs/body_testinprogress.gif?t=1495225010554')">
</div>
@media only screen and (max-width: 800px) {
.test{
display: none;
}
}
将包装器设置为在您不想加载图像的断点上不显示。img 标签的内联 css 现在被忽略,因为包装在带有 display none 的包装器中的元素的样式将被忽略,因此不会加载图像,直到到达包装器具有显示块的断点。
好了,不用在移动断点上加载 img 的非常简单的方法 :)
查看此代码笔,以获取工作示例:http ://codepen.io/fennefoss/pen/jmXjvo
使用@media query CSS,基本上我们只是发布了一个项目,其中我们在桌面上有一个巨大的树图像,但没有显示在桌面/移动屏幕上。所以防止图像加载它很容易
这是一个小片段:
.tree {
background: none top left no-repeat;
}
@media only screen and (min-width: 1200px) {
.tree {
background: url(enormous-tree.png) top left no-repeat;
}
}
您可以使用相同的 CSS 来显示和隐藏显示/可见性/不透明度,但图像仍在加载,这是我们想出的最安全的代码。
我们正在谈论无法在移动设备上加载的图像,对吗?那么如果你只是做了一个@media (min-width: 400px){background-image:thing.jpg}
那么它不会只在某个屏幕宽度以上寻找图像吗?
另一种可能性是使用<noscript>
标签并将图像放置在<noscript>
标签内。然后根据需要使用 javascript 删除noscript
标签。通过这种方式,您可以使用渐进增强按需加载图像。
使用我写的这个 polyfill 来读取<noscript>
IE8 中标签的内容
将 display:none 与图像一起使用的技巧是为它们分配一个 id。这是因为不需要很多代码就可以让它工作。这是一个使用媒体查询和 3 个样式表的示例。一种用于手机,一种用于平板电脑,一种用于台式机。我有 3 张图片,手机、平板电脑和台式机的图片。手机屏幕上只会显示手机的图像,平板电脑只会显示平板电脑的图像,桌面会显示桌面计算机的图像。这是一个使其工作的代码示例:
源代码:
<div id="content">
<img id="phone" src="images/phone.png" />
<img id="tablet" src="images/tablet.png" />
<img id="desktop" src="images/desktop.png" />
</div>
不需要媒体查询的电话 CSS。它的 img#phone 使它工作:
img#phone {
display: block;
margin: 6em auto 0 auto;
width: 70%;
}
img#tablet {display: none;}
img#desktop {display: none;}
平板电脑CSS:
@media only screen and (min-width: 641px) {
img#phone {display: none;}
img#tablet {
display: block;
margin: 6em auto 0 auto;
width: 70%;
}
}
和桌面css:
@media only screen and (min-width: 1141px) {
img#tablet {display: none;}
img#desktop {
display: block;
margin: 6em auto 0 auto;
width: 80%;
}
}
祝你好运,让我知道它是如何为你工作的。