数据URI编码的空白图像

88
我已经建立了一个图片滑块(基于优秀的bxSlider),它会在图片滑入视野前及时预加载图片。目前它已经基本可用,但我认为我的解决方案不符合有效的HTML规范。
我的技术方法如下:我生成滑块标记,第一张幻灯片图片像往常一样插入(使用<img src="foo.jpg">),随后的图片则在数据属性中引用,例如<img data-orig="bar.jpg">。然后JavaScript会在必要时操纵data-orig -> src的更改,从而触发预加载。
换句话说,我有:
<div class="slider">
    <div><img src="time.jpg" /></div> 
    <div><img src="data:" data-orig="fastelavn.jpg" /></div> 
    <div><img src="data:" data-orig="pels_strik.jpg" /></div> 
    <div><img src="data:" data-orig="fashion.jpg" /></div> 
</div>

为了避免空的 src="" 属性(在 一些浏览器 中会 影响性能),我插入了 src="data:" 以有效地插入一个空白图像作为占位符。
问题是,我似乎在 data-URI 的文档 中找不到任何关于这是否为有效 data-URI 的说明。我基本上想要最小的 data-URI,以解析为空/透明图像,这样浏览器就可以立即解析 src 并继续执行(没有错误或网络请求)。也许 src="data:image/gif;base64," 更好?

只需使用空哈希表。https://dev59.com/s2025IYBdhLWcg3w1JeG#28077004 - iGidas
@iGidas:这是个不好的想法,因为许多浏览器实际上会向主页面发出第二个请求(比原始图像造成更严重的性能损失,并在服务器日志中创建混乱的条目),尝试将HTML解释为图像,抛出错误,并可能导致真正的应用程序错误(例如,在购物车/结账页面中,“页面刷新”会导致添加更多商品到篮子中或触发安全措施)。 - Jens Roland
实际上,data:image/gif;base64, 作为 src 使用怎么样?甚至更短的 data:, 以逗号结尾。它似乎是有效的 HTML,并且在每个现代浏览器中都可以正常工作,没有任何错误。有什么反对使用它的论据吗? - bobo
7个回答

181
我研究了一下,最小可能的透明GIF图像,编码为data-uri,是这样的: data:image/gif;base64,R0lGODlhAQABAAAAACH5BAEKAAEALAAAAAABAAEAAAICTAEAOw== 现在我正在使用它。

2
如果您的img元素已经隐藏,并且您只是想避免HTTP 404错误,请参考https://dev59.com/s2025IYBdhLWcg3w1JeG#14115340,了解一个非透明图像的更短数据。 - Gili

46

如果您需要一个透明的1x1像素的图像,只需将此数据URI设置为src默认属性(保留///部分,它编码字节255,而不是注释)。

data:image/gif;base64,R0lGODlhAQABAIAAAP///wAAACH5BAEAAAAALAAAAAABAAEAAAICRAEAOw==

这实际上是一个 1x1 白色图像的 base64 编码。

data:image/gif;base64,R0lGODlhAQABAIAAAP7//wAAACH5BAAAAAAALAAAAAABAAEAAAICRAEAOw==

否则,您可以设置data:null并为每个图像节省约60个额外的字节。


4
您能提供一个链接来验证数据:null作为图像源是有效的吗? - Jens Roland
1
@JensRoland,根据Mozilla KB的说法,空数据是有效的:http://www-archive.mozilla.org/quality/networking/testing/datatests.html。但是非图像不会被渲染,因此任何alt属性都会被忽略。 - K3---rnc
1
@K3---rnc:我看到了Mozilla的那个列表;不幸的是,那不是规范,仅仅是Mozilla测试人员期望的行为;换句话说,它反映了Mozilla对规范的解释。这是一个好迹象,但并不能保证任何版本的IE或Webkit会表现相同。 - Jens Roland
@fcalderan 我很好奇,既然两者大小相同,为什么你提供了白色版本?白色相对于透明有什么优势吗? - Luke Gedeon

27
data:image/svg+xml,<svg xmlns="http://www.w3.org/2000/svg"/>

有效且高度可压缩。如果页面中还有另一个内联SVG,则基本上是免费的。


5
我喜欢这个。我只看到两个缺点:首先,在IE<9中不支持SVG(通常不是问题,但对于某些网站来说这是不可行的);其次,“SVG数据需要进行URI编码才能在IE和Firefox中使用”(请参见http://caniuse.com/#search=datauri),因此你实际上必须使用:`data:image/svg+xml,%3Csvg%20xmlns=%22http://www.w3.org/2000/svg%22/%3E`,它仍然比我的短4个字节,但看起来有点凌乱。 - Jens Roland

26

我见过的最小的

data:image/gif;base64,R0lGODlhAQABAAD/ACwAAAAAAQABAAACADs=

更新:据@bryc报告,此方法已失效,不再可用,请使用其他答案。


7
当然,除了那个只能在Chrome中使用。如果在Firefox中打开,将会收到“图像无法显示,因为它包含错误”的提示。请参见http://proger.i-forge.net/%D0%9A%D0%BE%D0%BC%D0%BF%D1%8C%D1%8E%D1%82%D0%B5%D1%80/[20121112]%20The%20smallest%20transparent%20pixel.html。 - Jens Roland
1
@JensRoland,没错,我确认在Firefox上它不起作用!虽然一年前使用时我不记得有任何问题与FF的兼容性!很奇怪。 - azerafati
@JensRoland 那个链接对我很有帮助。我需要一个透明的PNG图片:如果你改变一个src为透明gif的img元素的不透明度,当你重置不透明度时,透明效果会出现问题。 - Tom
1
这在Chrome中也不能起作用。如果您直接在Chrome中打开data:image/gif;base64,R0并将其与此答案进行比较,则会显示相同的“损坏”的16x16图像。因此,您会自欺欺人地认为Chrome正在将其正确呈现为1x1透明GIF。 - bryc
@bryc,看起来完全正确,尽管我5年前使用过它,那时它是有效的,或者我错误地认为它是有效的。因此,现在每个人都应该使用https://dev59.com/GGox5IYBdhLWcg3wklCE#19891866,我想。 - azerafati
@azerafati那个更好,但在FF中是白色的,在Chrome中是空白的,如果在非白色背景上使用可能会有问题。它也不是未来的解决方案,因为它剥夺了大多数图像软件所需的一个字节。就像你说的,过去有效的方法现在已经不再有效了...我曾经有一个更短的14B版本,当时只在Chrome中有效,但现在已经失效了。看看这里的答案,它揭示了所有的秘密:https://dev59.com/pXE85IYBdhLWcg3w3Xn6#15960901。我使用的是一个32B版本,在任何地方都是透明的。 :D干杯 - bryc

16
data:image/gif;base64,R0lGODlhAQABAAAAACwAAAAAAQABAAA=

更小了 :D


1
真的 - 那个很可爱!但它是否符合标准的gif格式?你能详细说明一下你是如何得到它的吗? - Jens Roland
2
http://proger.i-forge.net/The_smallest_transparent_pixel/eBQ - Alex
2
该链接指出,这个和14字节的仅适用于Chrome浏览器,并且不能保证在所有浏览器上都能正常工作。此外,生成的gif似乎无法在任何图像编辑器中打开。因此,我会犹豫使用它。 - Jens Roland
@JensRoland 添加一个缺失的字节(LZW头字节)将使其在大多数图像编辑器中打开(将“=”更改为“C”)。 在PS / Paint / Gimp中为黑色,在Firefox中为白色,在Chrome中为透明,因为没有颜色信息存在,软件决定默认值。 - bryc

9

一个1像素乘1像素的JPEG图片

data:image/jpeg;base64,/9j/4AAQSkZJRgABAQEAYABgAAD/2wBDAAIBAQIBAQICAgICAgICAwUDAwMDAwYEBAMFBwYHBwcGBwcICQsJCAgKCAcHCg0KCgsMDAwMBwkODw0MDgsMDAz/2wBDAQICAgMDAwYDAwYMCAcIDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAwMDAz/wAARCAABAAEDASIAAhEBAxEB/8QAHwAAAQUBAQEBAQEAAAAAAAAAAAECAwQFBgcICQoL/8QAtRAAAgEDAwIEAwUFBAQAAAF9AQIDAAQRBRIhMUEGE1FhByJxFDKBkaEII0KxwRVS0fAkM2JyggkKFhcYGRolJicoKSo0NTY3ODk6Q0RFRkdISUpTVFVWV1hZWmNkZWZnaGlqc3R1dnd4eXqDhIWGh4iJipKTlJWWl5iZmqKjpKWmp6ipqrKztLW2t7i5usLDxMXGx8jJytLT1NXW19jZ2uHi4+Tl5ufo6erx8vP09fb3+Pn6/8QAHwEAAwEBAQEBAQEBAQAAAAAAAAECAwQFBgcICQoL/8QAtREAAgECBAQDBAcFBAQAAQJ3AAECAxEEBSExBhJBUQdhcRMiMoEIFEKRobHBCSMzUvAVYnLRChYkNOEl8RcYGRomJygpKjU2Nzg5OkNERUZHSElKU1RVVldYWVpjZGVmZ2hpanN0dXZ3eHl6goOEhYaHiImKkpOUlZaXmJmaoqOkpaanqKmqsrO0tba3uLm6wsPExcbHyMnK0tPU1dbX2Nna4uPk5ebn6Onq8vP09fb3+Pn6/9oADAMBAAIRAxEAPwD9/KKKKAP/2Q==

1
可以显著缩小:/9j/4AAQSkZJRgABAQEAYABgAAD/2wBDAP//////////////////////////////////////////////////////////////////////////////////////wAALCAABAAEBAREA/8QAJgABAAAAAAAAAAAAAAAAAAAAAxABAAAAAAAAAAAAAAAAAAAAAP/aAAgBAQAAPwBH/9k。但如果你想要一个白色的1x1正方形,最好使用GIF:data:image/gif;base64,R0lGODlhAQABAAAAACwAAAAAAQABAAAC - bryc

5

Fabrizio的“白色gif”实际上并不是完全的白色:它是rgb(254, 255, 255)

我使用以下这个(恰好更小),可以在这个页面找到。

data:image/gif;base64,R0lGODlhAQABAIAAAP///wAAACwAAAAAAQABAAACAkQBADs=

那个可以生成白色像素,但我需要一个更通用的透明像素。 - Jens Roland

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接