图片压缩之 PNG
链接:https://zhuanlan.zhihu.com/p/19570424
来源:知乎
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。
PNG(Portable Network Graphics) 是一种大家经常使用的位图格式。
PNG 的特点
- 位图
- 支持半透明 (BMP不支持,JPEG不支持,GIF不支持,TIFF支持)
- 支持无损压缩 (BMP不支持,JPEG支持,GIF不支持,TIFF支持)
- 不支持动画 (A-PNG没有得到广泛应用,GIF是事实标准)
- 不支持有损压缩, 确切地说,是没有可调整的质量设置。(JPEG支持,WebP支持)
PNG 的用途
- 有透明度的图标
- 有透明度的界面元素,如按钮,背景
- 对图片尺寸不敏感的一般用途
PNG 的压缩
PNG-8 压缩
虽然 PNG 的自带无损压缩使它比 BMP 和 TIFF 已经「聪明」了很多,但对于网络传播仍然嫌大。PNG-8 是唯一可行的压缩方法。
大家可能立即想到的就是 Photoshop 自带的 PNG-8 压缩。
它的原理是缩减图片的色彩空间,8位就是2的8次方种颜色,也就是256色(或更少)。对于一般的按钮和界面图标,可能只有几种颜色;但对于照片来说,256色肯定完全不够用。为了能显示过渡色,有两种办法来欺骗眼睛。一种是 Diffusion, 有一点像点彩画的做法,用两种相近颜色的来拼凑。它的参数是 Dither,Dither参数越大,混合得越均匀,但文件也会变大。
![](https://pic3.zhimg.com/09cc448f7b5f7a41a2ecc61b7a4c63b2_b.jpg)
另外一种就是用图案,看上去不太自然,现在很少用。
Photoshop 自带的 PNG-8 压缩有严重的缺点,就是它的透明只能全透明,不能半透明。虽然这样的格式支持广泛,包括 IE 6 都支持。但也大大限制了 PNG 的使用范围。
透明PNG的压缩
如果不考虑 IE6 的话,又希望在保留透明度同时压缩大小,那么好消息是还可以用第三方工具,在 Mac 上有 ImageAlpha ,网页上有 TinyPNG 。它的原理是让 PNG-8 的 256 色中包含透明色。可以用的压缩工具:
- http://www.libpng.org/pub/png/apps/pngquant.html 原始的 pngquant
- http://pngnq.sourceforge.net
- pngquant — lossy PNG compressor 升级版的 pngquant
- PNGOUT
- http://optipng.sourceforge.net
- http://pmt.sourceforge.net/pngcrush/
压缩参数
这些库都有很多参数可以调节。有兴趣的同学可以去亲自尝试一下。我知道你们还是想看现成的结果。
原大 94KB, 无压缩 12KB, pngQuant 压缩后 5KB 几乎无变化, WebP压缩后 3KB 有明显瑕疵。
首先,用 ImageMagick 把图标改小:这里附加了一点锐化和高级的重采样算法,可以保证图片压小了之后清晰。用默认的算法有时图片会糊,但这样会稍微增加计算量。
convert ${input} -resize 68x -unsharp 0x1+0.3 -filter Lanczos ${out}
然后,用 pngquant 把PNG压缩:
pngquant -f --speed 1 --ext opt.png ${input}
如果嫌压缩的机器太闲,最后还可以用PNGOut压缩掉10%左右:
pngout -ks -f6 ${input}
要用 WebP 吗?
WebP 是谷人希 (谷歌!人类的希望!) 推行的自造轮子,它的特点是,支持半透明的有损压缩,像是 PNG 和 JPEG 的杂交品种。技术小白鼠看到 Spec 容易流口水,也容易尝试使用,因为它号称可以比 png 小 45%,比 JPEG 小 30% 什么的。
WebP lossless images are 26% smaller in size compared to PNGs. WebP lossy images are 25-34% smaller in size compared to JPEG images at equivalent SSIM index.
但我不建议大规模使用,原因无非:
- 支持差。Chrome 当然能用,但包括 Photoshop 在内的大多数程序打不开。
- 压得慢。亲测。人家可能用了高级算法,但对于服务器来说,这点很蛋疼。
- 逻辑复杂。和理想不同,为了万无一失,你需要两套图片。一套 WebP,一套普通的 PNG 或者 JPEG。这就要压两次,还要存两次,还要加判断的逻辑。
- 先把手头的 PNG 和 JPEG 压好再说吧!
不就是为了让图小一点吗,你已经试了所有的办法了吗?压缩参数都优化过了吗?你用 WebP 默认的参数去压,也不会比别人优化过的 PNG 和 JPEG 参数效果好、文件小的。把参数吃透,压到极限,你还觉得文件太大?
其实除了 WebP,还有类似 JPEG 2000 之类的轮子从来就没有推开,我悲观的认为,现有的格式已经足够好,新格式都没有极其显著的优越性,而大家的网速还在提升,带宽成本在下降。于是它们只能算生不逢时吧。