使用 CSS 媒体查询作为移动解决方案的唯一组成部分的缺点之一是,相同的内容会提供给台式机浏览器和移动设备(理论上移动设备速度较慢,网络速度也较慢)。
为两者提供相同的 HTML… 这不是什么大问题。 提供比移动设备上需要的尺寸大好几倍的图片,这才是问题所在。 许多聪明的人试图解决这个问题,因此我只想在这里重点介绍一下他们的工作:
CSS3 方法
虽然这个 由 Nicolas Gallagher 编写的方法 **目前在任何浏览器中都不起作用**,但我认为它是我最喜欢的。 您将最小的图片作为默认源,然后将指向较大版本图片的 URL 路径列出为 HTML5 数据属性。
<img src="image-mobile.jpg"
data-src-desktop="image-desktop.jpg"
alt="">
然后使用 CSS 生成的内容通过媒体查询,如果屏幕宽度表明是台式机,则使用较大版本图片替换图形。
@media (min-width: 1024px) {
img[data-src-desktop] {
content: attr(data-src-desktop, url);
}
}
即使是 当前 CSS 规范的开发版本,它已从 原始版本 中大大精简,也保留了这种功能。
Nicolas 在 他的文章 中清楚地概述了这种方法的潜在缺点,我认为每一个缺点都可以在未来的技术中得到解决。
JavaScript 方法
虽然上面提到的 CSS3 方法目前只是理论上的,但 这种 JavaScript 技术 由 Scott Jehl (来自 Filament Group ) 开发,已经可以投入使用(即使仍然处于实验阶段)。
这项技术实际上是 JavaScript、HTML 和 .htaccess(仅适用于 Apache 服务器)的结合。 Readme 文件中对它的解释最清楚。
一旦 rwd-images.js 加载,它就会测试屏幕宽度,如果宽度很大,它就会在您页面的头部插入一个 BASE 元素,将所有后续图片、脚本和样式表请求定向到一个名为“/rwd-router/” 的虚构目录。 当这些请求到达服务器时,.htaccess 文件会确定请求是否为响应式图片(它是否带有 ?full 查询参数?)。 它会立即将响应式图片请求重定向到其完整尺寸,而所有非响应式图片请求都会通过忽略“/rwd-router/” 部分的 URL 重写,定向到其适当的目标。
Cookie 方法
Keith Clark 有一种方法 可以存储一个包含当前设备屏幕尺寸的 cookie。 在提供图片之前,可以测试该 cookie,并用它来决定提供哪个尺寸的图片。
它通过设置一个包含屏幕尺寸的 cookie 来实现。
document.cookie = "device_dimensions=" + screen.width + "x" + screen.height;
然后图片实际上是通过一个简单的脚本进行路由的。 文件名是一个参数。
<img src="images/?test.png">
脚本会读取 cookie 并提供合适的图片。 查看 完整文章 以了解所有代码。
还有其他方法吗?
您是否见过其他试图解决这个问题的项目? 我希望能够将这篇文章更新为最新的最佳方法。
我一直都在使用这个移动样板,它会先加载较小的内容,然后随着屏幕尺寸变大再添加较大的版本。 我想这与您讨论的有点不同,但还是想提一下。
http://stuffandnonsense.co.uk/projects/320andup/
顺便说一句,很喜欢您的网站。 它帮了我无数次!
假设所有图片资源都是通过 CSS 使用 background-image 加载的(我知道这不太现实,只是在这里想一想),那么您是否可以只是将媒体查询添加到包含图片的所有内容中? 也就是说,如果是在台式机上,先测试分辨率是否足够大,然后再提供较大版本的图片? 我想,如果您这样做的话,移动版本就不会尝试加载较大版本的台式机图片,对吧?
关于元素,如果您默认有一个规则,它表示
img { display none; }
… 然后使用媒体查询,如果您满足某个分辨率要求,就选择性地将其设置为显示为 inline/block/任何其他值,那么较小的屏幕设备是否仍然会加载图片资源,即使 display 设置为 none?
有一些媒体查询可以用来检查屏幕宽度等等。 在 CSS-Tricks 这个无穷无尽的资源库中,Chris 实际上已经介绍过这个内容。
不幸的是,您的假设是错误的,许多(大多数?)移动浏览器会下载他们在样式表中找到的所有图片,无论如何,即使媒体查询意味着它们永远不会被使用。
@Martin Ansty: 如果图片位于从未使用过的类上,移动浏览器是否会下载它? 我想,如果您检测到浏览器,然后在 body 元素中添加一个类,那么就可以为特定浏览器指定特定图片… 这样,未使用过的类就不会加载。
只需在 Firefox 中使用 FireBug 扩展进行一些测试。 我发现,未使用过的类上的图片没有被加载。 如果您想自己检查,可以在 Net > Images 部分查看… 它会显示所有加载的图片。
我使用的方法完全与您建议的一样,所有图片都是背景,并且使用媒体查询来更改图片。 我使用相同的方法,使用 background-size 在 iPhone4 上显示 @2x 图片。 我的服务器日志没有反映出大多数移动浏览器会下载所有图片,看起来效果很好。
喜欢 PHP 的方法 :-D
告诉我更多?
我也想知道更多。
考虑到我总是使用 WordPress 环境,PHP 可能是一个不错的选择。
http://www.dannyherran.com/2011/02/detect-mobile-browseruser-agent-with-php-ipad-iphone-blackberry-and-others/
这个脚本运行得很好,可以用来选择不同的 php 文件。
Sencha.io Src(以前称为 Tinysrc)怎么样?
http://www.sencha.com/products/io/
我在几个网站上使用过它,效果很好。
即使使用媒体查询,您 CSS 中指定的所有资源都会被加载。 我今天写了一篇关于它的文章 http://wolfslittlestore.be/2011/06/28/load-times-responsive-images/
在客户通过 FCK 或 TinyMCE 等所见即所得编辑器输入内容的场景中,将每个图片设置为背景图片是不现实的。
即使是可能,也是一个非常糟糕的主意,因为它破坏了网络的语义。谷歌图片不会索引你的背景图片。
我相信你也可以将所有背景图片声明放在两个独立的样式表中,并使用媒体查询来确定最初加载哪个图片。
或者我在这条路上遗漏了什么(除了如果你调整浏览器大小会加载两组图片)?
啊!我真的希望你能编辑评论。
<link rel=”stylesheet” media=”screen and (max-width: 800px)” href=”small_graphics.css”>
<link rel=”stylesheet” media=”screen and (min-width: 801px)” href=”normal_graphics.css”>
当然,这只会对背景图片有效,而不会对实际的 img 标签有效!
这是一个关键问题。这不仅影响移动设备图形,还影响使用大型详细图形的网站。我更倾向于先加载低质量图片,这样网站可以更快地加载其全部内容,然后在页面加载完成后应用高质量图片。我们过去可以使用 lowsrc 来实现这一点,但使用一种不仅能检测屏幕尺寸还能检测网络速度的新技术将非常有用。
你使用什么方法从低分辨率转换为高分辨率?
这些示例在页面加载后更改了 html 背景,但可以将其改编为内联图片,并且不使用背景,例如使用替代 img 属性。
$(window).load(function(){
$(“html”).addClass(“bgHighRes”)
})
我需要一些使用 PS CS5 的帮助。
我认为你走错地方了。谷歌搜索一下,你会得到更好的结果。
或者试试 Envato 的网站:http://psd.tutsplus.com/
我使用了一些 jQuery 和 timthumb.php 来完成朋友的首页。脚本如下所示
这样他就可以通过设置页面的 WordPress 特色图片来更改首页图片。
忘记提了,它最初应该是一个幻灯片(因此是 ‘#homepage-slideshow’ 选择器),但他更喜欢使用单张图片。它在:http://www.charlesmellersh.com/
我刚开始接触 CSS 和这个网站,但在阅读了这些技术和评论后,我认为我已经想出了一个解决这个问题的算法…
设置移动 CSS
检查屏幕尺寸
如果(屏幕尺寸 == 桌面) 则将 CSS 更改为桌面 CSS
将它放到网站的那一部分
我认为这是一个简单的代码,它应该通过为移动/桌面设置正确的 CSS 来很好地工作……我还没有测试它,因为我在工作,我会在晚些时候回家后测试它,并查看结果。
这看起来很有趣。
有人对此有负面或正面反馈吗?
Kevin Sweeny 的代码似乎做了同样的事情,只是作为一个标准做法。
我糊涂了吗?
如果我没有糊涂,那么它仍然没有解决标记中图片标签的问题,而这就是这篇文章的主题。
我之前遇到了同样的问题,并想出了我认为是不错的解决方案。虽然我知道并喜欢 PHP,但它让我花费了更多费用来托管动态网站。因此,我需要使用纯 JavaScript 来加载较小的图片。当页面准备就绪(但图片尚未加载)时,我只是编辑页面上所有图片的 src。我把所有较小的图片放在一个文件夹 /m 中,并保持与 /media 相同的文件夹结构,所有桌面图片都驻留在那里。这样,我就可以在 src 中简单地将 ‘media/’ 替换为 ‘m/’。以下是我的代码
$(document).ready(function() {
// 在此处替换图片
if(480 >= window.innerWidth) {
$(“img”).attr(‘src’,function(i, val) {
return val.replace(‘media’,’m’);
});
}
});
我想指出 JavaScript 解决方案中一个常见的错误。我们感兴趣的不是屏幕尺寸(screen.width 和 screen.height),而是视窗尺寸(document.documentElement.clientHeight 和 document.documentElement.clientWidth)。虽然对于移动浏览器来说可能是一样的,但对于桌面浏览器来说肯定不是。为什么一个在 1920×1080 屏幕上以 600×400 像素运行的桌面浏览器应该获得与全屏以 1920×1080 像素运行的桌面浏览器相同的图片?
前几天不是有一篇文章谈到过这个吗?https://css-tricks.org.cn/9778-screen-resolution-notequalto-browser-window/
如何为所有元素提供一个 data-largeimage src,并使用 JavaScript 在视窗大于 1024px 时用它来替换 src=”” 属性?
img 标签上的原始 src=”” 是图片的移动版本,但在桌面版中,它会立即被 data-largeimage=”urltobiggerimage” 中提供的更大图片 src 替换,因为 JavaScript 检测到了桌面分辨率。
有什么想法吗?(稍后我会发布一个示例)
怎么样…
上下文特定图片
* { margin: 0; padding: 0; }
img{ width:100% }
body { background: #CCC; }
#page-wrap { width: 256px; margin: 0 auto; }
@media (max-width:769px) {
#page-wrap { width: 150px; margin: 0 auto; }
}
var winW;
var img;
var imgState;
function specificImage() {
img = document.getElementsByTagName(“img”);
winW = window.innerWidth;
if (winW >= 770 && imgState != “desktop”) {
imgState = “desktop”;
for ( var t = 0; t < img.length; ++t ) {
var imageChanger=img[t].src;
img[t].src = imageChanger.replace("mobile","desktop");
};
}
else if (winW <= 770 && imgState == "desktop") {
imgState = "mobile";
for ( var t = 0; t < img.length; ++t ) {
var imageChanger=img[t].src;
img[t].src = imageChanger.replace("desktop","mobile");
};
};
};
window.onresize = function () {
specificImage();
};
你只需要在图片文件夹中创建两个子文件夹,一个用于大型图片,另一个用于小型图片。页面将默认加载小型图片,然后检测窗口大小。如果窗口大于 769px(在本例中),它将加载更大的图片。它还会在调整大小后交换图片。
哎呀!忘记更改代码了…
你可能可以改编视网膜显示 jQuery 插件中使用的技术:http://troymcilvena.com/post/998277515/jquery-retina
它会在文件名中追加一个 -2x,以便在检测到高 DPI 显示时使用更高分辨率的版本。你必须设置高度和宽度以防止它变得是两倍大小,这很明显。
你也可以做同样的事情,只是检测屏幕/窗口宽度。当它检测到更大的宽度时,用更大的版本替换图片。如果没有设置 h & w,它将是你在其中设置的任何大小。在窗口大小改变时让它动态地做到这一点应该不需要花费太多功夫。
我认为,在可能的情况下,只将图片调整大小以适应较小的屏幕危害更小。图片下载会更大,但我们仍然有机会使用媒体查询来动态地更改网站布局(在调整浏览器窗口大小时),并且不依赖于移动用户代理检测。
在我看来,说起来容易做起来难。虽然现在很多移动用户都拥有 3G 或更快的网络,但我不知道它是否无处不在。无论如何,强制用户使用更大的图片似乎是错误的。你不仅忽略了他们固有的更慢的连接,而且你也不尊重很多用户没有无限数据流量计划,并且必须将他们的下载量控制在一定范围内以避免超出流量费用这一事实。
听起来很多人都把通过 CSS 加载的背景图片和 HTML 中的图片混淆了。
这篇文章是关于 HTML 中的图片。
Josh。我没有尝试你的代码,但它与我的想法差不多。将它与一个脚本结合起来,该脚本在通过 CMS 上传时自动创建两个版本的 IMG,这是一个大赢家。
您好,文章不错。Windows 也支持 URL 重写:IIS7 内置了它,IIS6 可以使用第三方插件,例如来自 HeliconTech 的插件。不太可能出现在基于 IIS6 的共享托管套餐中,但随着主机升级,我们中的更多人可以享受类似于 .htaccess 的优势!
如何在像我的网站这样的 CDN 环境中使用 CSS3 的方法?
http://www.benchee.com/
我可以选择每种可能的图像大小,并为每个图像设置多个不同的子域吗?