开发一款图片压缩工具(二):使用 pngquant 实现图片压缩
在网上有很多使用 python 的 pillow 库进行图片压缩的教程,使用简单,但是压缩效果存在明显的色彩不自然,这是因为 pillow 库采取的压缩算法没有优化的问题。
这个系列实现一款简单的压缩工具,使用 pngquant 有损压缩,压缩率高达 80%, 而且压缩后的图片没有明显差异。
系列文章:
1,使用 python 压缩 png 图片,高达 80% 压缩率,肉眼无差异(一):为什么不用 pillow库.md
2,使用 python 压缩 png 图片,高达 80% 压缩率,肉眼无差异(二):使用 pngquant 实现图片压缩
3,使用 python 压缩 png 图片,高达 80% 压缩率,肉眼无差异(三):使用 click 库实现命令行
4,使用 python 压缩 png 图片,高达 80% 压缩率,肉眼无差异(四):使用 requests 库上传
上一篇我尝试使用了 pillow 库对 png 图片进行了压缩,效果不好。这次我换用 pngquant 来压缩。
pngquant 是用于 PNG 图像有损压缩的命令行实用程序和库。压缩程序会显著减小文件大小(通常高达70%),并保持完全的alpha透明度。通过使用alpha通道将图像转换为更高效的8位PNG格式(通常比24/32位PNG文件小60-80%)。
pngquant 使用的算法主要是中值切割量化算法的改进版和 K-means 颜色校正。得到的图片颜色差异肉眼几乎无法察觉。
这是 pngquant 优化后的图片,几乎看不出区别:

这是 pillow 同样采用中值切割和 k-means 得到的优化效果, 云彩有明显颜色过渡不自然问题:

pngquant 压缩库安装
pngquant 提供了源码、命令行和 GUI 等多种形式。它不是 python 写的,所以只能用 python 调用命令行或者源码函数。 GUI 的工具目前来说还比较难用,并没有命令行方便,而源码形式可以通过 ctype 使用 python语言去调用 c 源码。但是目前对这方面还不怎么了解,可以后面再去使用 so 动态库等方式。
先用命令行形式进行 PNG 压缩。
1,下载 windows安装包 或者 mac 和 linux 版本的安装包。
2,命令行输入 pngquant 就可以使用了;
3,为了使用方便,可以配置环境变量(后面如果和 picom 集成在了一起再去掉 )。
pngquant-fs8.png
快速使用 pngquant
pngquant 图片名称.png
对于一些可选参数的说明:
1,--skip-if-larger pngquant 有时候压缩的文件会比源文件大。这个选项会判断,如果大就取消执行。强烈建议加上
2,--quality 0-100 图片质量。对于颜色没有特别要求的可以缩减到 10, 但是越小压缩率越低,通常不需要设置。
3,--force 强制执行,pngquant 会判断,如果有一个已经压缩的同名文件在当前文件夹,就不会执行。这个选项会覆盖原来的文件。
4,--output file 指定输入文件的名称。 可以指定为 jpg 格式,但是图片不会变得更小。
5,--speed 执行速度
使用 subprocess 调用 pngquant 命令行
对应的程序:
import subprocess
subprocess.run('pngquant elephant.png')
如果想获取程序运行时屏幕上显示的内容,可以使用 check_output 方法,在这里不需要。
接下来使用 subprocess 封装对应的压缩函数:
def pngquant_compress(fp, force=False, quality=None):
"""压缩函数.
参数:
fp: 文件名称
force: 如果存在同名文件,是否覆盖
quality: 压缩质量。 10-40, or 10
"""
force_command = '-f' if force else ''
quality_command = ''
if quality and isinstance(quality, int):
quality_command = f'--quality {quality}'
if quality and isinstance(quality, str):
quality_command = f'--quality {quality}'
command = f'pngquant {fp} --skip-if-larger {force_command} {quality_command}'
subprocess.run(command)
if __name__ == "__main__":
pngquant_compress('elephant.png', force=True, quality=20)
总结
之前使用大多数教程推荐的 pillow 库,效果并不好。这次换用知名的 pngquant 以后,色彩已经用肉眼很难感知。 要实现对 png 图片的压缩率和图片效果的平衡,pngquant 真是个不错的工具。
开发一款图片压缩工具(二):使用 pngquant 实现图片压缩的更多相关文章
- 尝试用python开发一款图片压缩工具1:尝试 pillow库
开发目的 我经常使用图片.公众号文章发文也好,还是生活中要使用素材.图片是一种比文字更加直观的载体.但是图片更加占用带宽,很多软件都对图片有大小限制.图片太大也会影响加载速度.我试过几款图片压缩工具, ...
- 开发一款图片压缩工具(三):使用 click 实现命令行
上一篇实现了图片的压缩函数.现在如果需要对图片进行压缩,可以调用实现的函数进行压缩: pngquant_compress('elephant.png', force=True, quality=20) ...
- python 开发一款图片压缩工具(四):上传图床
上一篇使用了 pngquant 图片压缩工具进行压缩,并通过 click 命令行工具构建了 picom 包.这篇的主要功能是实现图片上传. 图片上传功能的实现 通过 pngquant 压缩图片后,得到 ...
- 用C#开发一个WinForm版的批量图片压缩工具
我们在实际项目开发过程中,曾经遇到过一个需求,就是要开发一个对大量图片进行整理(删除掉一些不符合要求的图片).归类(根据格式进行分类,比如jpg格式.bmp格式等).压缩(因为有的图片很大很占空间,看 ...
- 从零开发一款自己的小程序UI组件库(二)
写在前面:从零开发一款自己的小程序UI组件库(一) 上节我们讲到初始化组件库模板.模板文件概述.模板上传npm以及npm包文件下载至本地并运用到项目.这节我们继续,内容主要有基础UI组件库的搭建(bu ...
- 从零开始开发一款H5小游戏(二) 创造游戏世界,启动发条
本系列文章对应游戏代码已开源 Sinuous game 上一节介绍了canvas的基础用法,了解了游戏开发所要用到的API.这篇文章开始,我将介绍怎么运用这些API来完成各种各样的游戏效果.这个过程更 ...
- 开发一款高端大气上档次的android应用需要必备的知识——记于2013年末
Android入门还是很简单的,看两本书,翻阅几篇文章,搭建了开发环境就算入门了.可是怎样开发一款完备的android应用呢,开发一款高端的android应用又需要那些知识呢,作者根据几年的开发经验做 ...
- Android--从零开始开发一款文章阅读APP
代码地址如下:http://www.demodashi.com/demo/11212.html 前言 本案例已经开源!如果你想免费下载,可以访问我的Github,所有案例均在上面,只求给个star.当 ...
- 手牵手,使用uni-app从零开发一款视频小程序 (系列上 准备工作篇)
系列文章 手牵手,使用uni-app从零开发一款视频小程序 (系列上 准备工作篇) 手牵手,使用uni-app从零开发一款视频小程序 (系列下 开发实战篇) 前言 好久不见,很久没更新博客了,前段时间 ...
随机推荐
- webpack配置打包vue文件
1.首先全局安装node,和npm.检查是否安装成功 2.新建一个文件下,进入该文件夹. 前先执行 npm init -y 然后就会在文件夹下出现一个package.json文件 然后执行 npm i ...
- 服务器上安装.NET Framework 3.5 sp1
操作系统是Windows Server 2008 R2 或 Windows Server 2012 或 Windows Server 2012 R2,可以直接进入“服务器管理器”添加“功能”.
- js事件的获取
获取元素样式属性 Method DES clientWidth 获取元素宽度 clientHeight 获取元素高度(内容+内边距) document.body.clientWidth 获取body宽 ...
- coding++:JS数组去重的几种常见方法
一.简单的去重方法 // 最简单数组去重法 /* * 新建一新数组,遍历传入数组,值不在新数组就push进该新数组中 * IE8以下不支持数组的indexOf方法 * */ function uniq ...
- Feign客户端实现RPC 调用
1,springcloud 中支持http调用的两种方式,RestTemplate,Feign客户端 2,Feign 客户端是一个声明式(注解方式)http 远程调用工具 3,实现方式如下: 第一步: ...
- NSObject常用方法
类 @interface NSObject <NSObject> { Class isa OBJC_ISA_AVAILABILITY; } // 初始化加载 + (void)load; / ...
- 有效括号算法题(Golang实现)
有效括号算法题 给定一个只包括 '(',')','{','}','[',']' 的字符串,判断字符串是否有效. 有效字符串需满足: 左括号必须用相同类型的右括号闭合.左括号必须以正确的顺序闭合.注意空 ...
- NodeMCU入坑指南-低成本打造零舍友闻风丧胆WiFi断网神器
前言 最近对IoT方面比较感兴趣,所以在某宝上入手了一块NodeMCU的开发板,至于为什么我选择这块开发板呢?嘿嘿,当然是因为便宜啊
- P3381 【模板】最小费用最大流(MCMF)
P3381 [模板]最小费用最大流 题目描述 如题,给出一个网络图,以及其源点和汇点,每条边已知其最大流量和单位流量费用,求出其网络最大流和在最大流情况下的最小费用. 输入格式 第一行包含四个正整数N ...
- 1037 Magic Coupon (25分)
The magic shop in Mars is offering some magic coupons. Each coupon has an integer N printed on it, m ...