def create_collage(image_filename): from multiprocessing import Pool, cpu_count from PIL import ImageDraw image = utils.open_image(image_filename) width, height = image.size n_palettes = len(palette.available_palettes) n_methods = len(available_methods) canvas_size = (width * (n_palettes + 1), height * (n_methods + 1)) canvas = Image.new('RGB', canvas_size) canvas.paste(image, (0, 0)) drawer = ImageDraw.Draw(canvas) font = _get_font(image.size) font_color = (255, 255, 255, 255) image_matrix = utils.pil2numpy(image) work_objects = [] for p_i, p in enumerate(palette.available_palettes): text_width, text_height = font.getsize(p) text_pos = ((p_i + 1) * width + (width - text_width) / 2, (height - text_height) / 2) drawer.text(text_pos, p, font=font, fill=font_color) for m_i, m in enumerate(available_methods): if p_i == 0: text_width, text_height = font.getsize(m) text_pos = ((width - text_width) / 2, (m_i + 1) * height + (height - text_height) / 2) drawer.text(text_pos, m, font=font, fill=font_color) image_offset = ((p_i + 1) * width, (m_i + 1) * height) work_objects.append((image_offset, image_matrix, m, p)) del drawer pool = Pool(cpu_count()) results = pool.map(_do_work, work_objects) for r in results: image_offset, dither_image = r canvas.paste(dither_image, image_offset) canvas.save('collage.png') canvas.show()
opr = utils.clamp(opr + random.gauss(0.0, 1./6.)) opg = utils.clamp(opg + random.gauss(0.0, 1./6.)) opb = utils.clamp(opb + random.gauss(0.0, 1./6.)) new_pixel = numpy.array(utils.closest_palette_color([opr, opg, opb], palette_name), dtype=numpy.float) new_matrix[x][y] = new_pixel return new_matrix _available_methods = OrderedDict([ ('random' , randomized), ('block_random' , block_randomized), ]) if __name__ == '__main__': import argparse parser = argparse.ArgumentParser() parser.add_argument('image_filename', help='Path to an image file to dither') parser.add_argument('-b', '--bit-depth', type=int, default=1, help='Number of bits in dithered image') palette_help_str = 'Name of palette to use. Can be one of: ' + ', '.join(palette.available_palettes) parser.add_argument('-p', '--palette', type=str, default=default_palette, help=palette_help_str) args = parser.parse_args() image = utils.open_image(args.image_filename) image_matrix = utils.pil2numpy(image) dither_matrix = randomized(image_matrix, args.palette) dither_image = utils.numpy2pil(dither_matrix) dither_image.show()
import error_diffusion import palette import utils DEBUGMODE = False default_palette = 'cga_mode4_2_high' if __name__ == '__main__': import argparse palette_help_str = 'Name of palette to use. Can be one of: ' + ', '.join(palette.available_palettes) parser = argparse.ArgumentParser() parser.add_argument('image_filename', help='Path to an image file to dither') parser.add_argument('-p', '--palette', type=str, default=default_palette, help=palette_help_str) args = parser.parse_args() image = utils.open_image(args.image_filename) image_bands = list(image.split()) for b in range(3): image_bands[b] = image_bands[b].convert('RGB') image_matrix = utils.pil2numpy(image_bands[b]) dither_matrix = error_diffusion._available_methods['floyd_steinberg'](image_matrix, args.palette) image_bands[b] = utils.numpy2pil(dither_matrix) image_bands[b] = image_bands[b].convert('L') dither_image = Image.merge('RGB', image_bands) dither_image.show()