zoukankan      html  css  js  c++  java
  • 使用 python 压缩 png 图片,高达 80% 压缩率,肉眼无差异(三):使用 click 库实现命令行

    在网上有很多使用 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 库上传

    上一篇实现了图片的压缩函数。现在如果需要对图片进行压缩,可以调用实现的函数进行压缩:

    pngquant_compress('elephant.png', force=True, quality=20)

    但是每次输入 python run_script.py 没有对应的参数传入, 还要去改脚本参数挺麻烦的。为了使用起来更方便,可以添加命令行的方式进行调用:

    python run_script.py elephant.png --force --quality 30
    

    python 的 click 库可以非常方便的实现命令行调用。 click 是 flask 作者开发的。用法很简单,只需要添加装饰器在需要运行的程序上就可以了:

    image.pngimage.png

    当我输入 python demo.py --help 的时候, 会显示命令行帮助信息:

    image.pngimage.png

    click 必填参数 argument

    可以在函数上添加 @click.argument('arg_name')

    import click
    @click.argument("arg_name")
    def pngquant_compress():

    当程序没有填入必填参数时,将会提示:

    image.pngimage.png

    click 可选参数 option

    option 是 click 的重点,比 argument 要灵活很多。他的表示方法和 argument 差不多:

    import click
    @click.option("--force")
    def pngquant_compress():
        pass

    如果想用多个名称同时表示一个参数,只需要继续在 option 方法中添加位置参数, 就可以通过 -f, --violent 的形式 传入可选参数:

    import click
    @click.option("--force", "-f", "--violent")
    def pngquant_compress():
        pass

    如果不想以 --force value 的形式传入值,也可以直接通过 flag 形式,不传入任何值:

    import click
    @click.option("--force", "-f", "--violent", is_flag=True)
    def pngquant_compress():
        pass

    显示提示信息:

    import click
    @click.option(
        "--force""-f""--violent"
        is_flag=True,
        help="强制执行"
        )
    def pngquant_compress():
        pass

    参数类型限制

    比如 quality 参数传入的可以是数字 20, 也可以是 20-30 这种形式。这时候需要自定义一种数据类型进行校验。

    class QualityInteger(click.ParamType):
        name = "QualityInteger"

        def convert(self, value, param, ctx):
            if value.isdigit():
                return int(value)
            try:
                min_v, max_v = value.split('-')
                int(min_v), int(max_v)
                return value
            except ValueError:
                self.fail('参数不符合类似 20-30 或者 30 的规范')

    此时如果输入的参数没有通过检验,命令行会提示错误:

    picom>python demo_06_封装成命令行.py elephant.png -q 20-4a
    Usage: demo_06_封装成命令行.py [OPTIONS] FP
    
    Error: Invalid value for "--quality" / "-q": 参数不符合类似 20-30 或者 30 的规范
    

    setuptools 打包

    from setuptools import setup, find_packages

    setup(
        name='picom',
        version='0.1',
        install_requires=[
            'Click',
            'requests'
        ],
    )

    setup.cfg 配置文件:

    [metadata]
    name = picom
    description = A app to compress images.
    
    [options]
    packages = find:
    package_dir = = src
    include_package_data = true
    python_requires = >= 3.6
    
    [options.packages.find]
    where = src
    
    [options.entry_points]
    console_scripts =
        picom = picom.cli:cli
    

    把 picom 模块放入依赖包路径,执行 pip install --editable . 可以安装这个模块。 安装完成以后,可以在 python 解释器路径看到 picom.exe 命令行文件。建议创建虚拟环境安装,以免对系统环境造成污染。

    image.pngimage.png

    撤销 pngquant 全局变量,改由 picom 包内调用

    之前在 pngquant_compress 函数中使用 pngquant 命令行是采用环境变量,现在既然是通过 picom 命令去执行,就可以把 pngquant 的环境变量去掉。

    首先需要在 picom 包中添加一个 ext 的包存放 pngquant 的执行文件。 image.png

    修改原来的调用函数:

    # pngquant.py

    # 原来的写法
    command = f'pngquant {fp} --skip-if-larger {force_command} {quality_command}'

    # 新写法,直接调用 ext/ 下的可执行文件,而不是环境变量中的 pngquant
    pngquant_cmd = Path(__file__).resolve().parent / 'ext' / 'pngquant'
    command = f'{pngquant_cmd} {fp} --skip-if-larger {force_command} {quality_command}'

    总结

    通过 click 库和 setuptool 打包,picom 压缩工具使用变得比较简单:

    picom elephant.png
    
  • 相关阅读:
    Windows Phone 7(WP7)开发 自订磁贴(深度链接)
    Windows Phone 7(WP7)开发 在ViewModel中使用NavigationService
    Windows Phone 7(WP7)开发 显示长文本(高度大于2000px)
    类属性生成器(小程序)
    Windows Phone 7(WP7)开发 ListBox的分页加载
    Windows Phone 7(WP7)开发工具 查看独立存储空间中数据库内容
    Windows Phone 7(WP7)开发 获取网络状态
    发布一个XNA写的小雷电源码
    用python来个百度关键词刷排名脚本
    win7下 VirtualBox虚拟机开机后台自启动
  • 原文地址:https://www.cnblogs.com/heniu/p/12790476.html
Copyright © 2011-2022 走看看