zoukankan      html  css  js  c++  java
  • img2html实现将图片转换成网页

      简单介绍img2html的用法,安装就不用说了pip。这个包现只支持python2,支持python的话需改下源码这几个部分:

      加注释的是修改的地方

    #!/usr/bin/env python
    # encoding=utf-8
    
    from __future__ import print_function, unicode_literals
    
    from collections import namedtuple
    from itertools import cycle
    
    import jinja2
    from PIL import Image
    
    Point = namedtuple('Point', ['x', 'y'])
    Pixel = namedtuple('Pixel', ['r', 'g', 'b'])
    RenderItem = namedtuple('RenderItem', ['color', 'char'])
    RenderGroup = list
    HTMLImage = list
    
    TEMPLATE = '''
    <html>
    <head>
        <meta charset="utf-8">
        <title>{{ title }}</title>
        <style type="text/css">
            body {
                margin: 0px; padding: 0px; line-height:100%; letter-spacing:0px; text-align: center;
                min- {{width}}px;
                 auto !important;
                font-size: {{size}}px;
                background-color: #{{background}};
                font-family: {{font_family}};
            }
        </style>
    </head>
    <body>
    <div>
    {% for group in html_image %}
        {% for item in group %}<font color="#{{ item.color }}">{{ item.char }}</font>{% endfor %}
        <br>
    {% endfor %}
    </div>
    </body>
    </html>'''
    
    
    _c = cycle(r'/-|')
    
    
    def _progress_callback(percent):
        if percent == 100:
            print('
    Done!               ')
        else:
            import sys, time
            lca = getattr(_progress_callback, '_last_call_at', 0)
            if time.time() - lca > 0.1:
                _progress_callback._last_call_at = time.time()
                # _c.next() => next(_c)
                sys.stdout.write('
    {} progress: {:.2f}%'.format(next(_c), percent))
                sys.stdout.flush()
    
    
    class Img2HTMLConverter(object):
        def __init__(self,
                     font_size=10,
                     char='',
                     background='#000000',
                     title='img2html by xlzd',
                     font_family='monospace',
                     progress_callback=None):
            self.font_size = font_size
            self.background = background
            self.title = title
            self.font_family = font_family
            # if isinstance(char, str):
            #     char = char.decode('utf-8')
            self.char = cycle(char)
            self._prg_cb = progress_callback or _progress_callback
    
        def convert(self, source):
            image = Image.open(source)
    
            width, height = image.size
            row_blocks = int(round(float(width) / self.font_size))
            col_blocks = int(round(float(height) / self.font_size))
    
            html_image = HTMLImage()
            progress = 0.0
            step = 1. / (col_blocks * row_blocks)
            # xrange => range
            for col in range(col_blocks):
                render_group = RenderGroup()
                for row in range(row_blocks):
                    pixels = []
                    for y in range(self.font_size):
                        for x in range(self.font_size):
                            point = Point(row * self.font_size + x, col * self.font_size + y)
                            if point.x >= width or point.y >= height:
                                continue
                            pixels.append(Pixel(*image.getpixel(point)[:3]))
                    average = self.get_average(pixels=pixels)
                    color = self.rgb2hex(average)
                    # render_item = RenderItem(color=color, char=self.char.next())
                    render_item = RenderItem(color=color, char=next(self.char))
                    render_group.append(render_item)
    
                    progress += step
                    self._prg_cb(progress * 100)
    
                html_image.append(render_group)
    
            self._prg_cb(100)
            return self.render(html_image)
    
        def render(self, html_image):
            template = jinja2.Template(TEMPLATE)
            return template.render(
                html_image=html_image,
                size=self.font_size,
                background=self.background,
                title=self.title,
                font_family=self.font_family,
                width=self.font_size * len(html_image[0]) * 2
            )
    
        @staticmethod
        def rgb2hex(pixel):
            return '{:02x}{:02x}{:02x}'.format(*pixel)
    
        @staticmethod
        def get_average(pixels):
            r, g, b = 0, 0, 0
            for pixel in pixels:
                r += pixel.r
                g += pixel.g
                b += pixel.b
            base = float(len(pixels))
            return Pixel(
                r=int(round(r / base)),
                g=int(round(g / base)),
                b=int(round(b / base)),
            )

      具体实现代码如下:

    # -*- coding: utf-8 -*-
    # Nola
    """
    img2html : Convert image to HTML
    
    optional arguments:
      -b #RRGGBB, --background #RRGGBB  background color (#RRGGBB format)
      -s (4~30), --size (4~30)          font size (int)
      -c CHAR, --char CHAR              characters
      -t TITLE, --title TITLE           html title
      -f FONT, --font FONT              html font
      -i IN, --in IN                    要转换的图片
      -o OUT, --out OUT                 输出文件名
    $ img2html -i timg.jpg -o timg_html.html
    """
    from img2html.converter import Img2HTMLConverter
    
    converter = Img2HTMLConverter(char='',title='金木研')
    html = converter.convert('timg.jpg')
    with open('timg_html.html',mode='w',encoding='utf-8') as f:
        f.write(html)

      准备一张图片,编写py文件,生成html文件,文件结构如图:

      前后对比效果如图:

       密密麻麻的爱字,看起来着实有点像十字绣,也许你会发现这个包更有趣的实用之处。

    实践出真知~
  • 相关阅读:
    第一章--购物车作业
    第一章--三级菜单作业
    第3章 文件操作-函数练习题
    面试题2.20
    Python 技巧(三)—— list 删除一个元素的三种做法
    Python 字符串操作方法大全
    员工信息增删改查程序
    Python之print函数详解
    判断登陆用户名和密码是否正确-记事本存用户名密码
    软件开发目录规范
  • 原文地址:https://www.cnblogs.com/NolaLi/p/10113782.html
Copyright © 2011-2022 走看看