aboutsummaryrefslogtreecommitdiffstats
path: root/tools/unique.py
diff options
context:
space:
mode:
Diffstat (limited to 'tools/unique.py')
-rwxr-xr-xtools/unique.py106
1 files changed, 0 insertions, 106 deletions
diff --git a/tools/unique.py b/tools/unique.py
deleted file mode 100755
index 34530a3e..00000000
--- a/tools/unique.py
+++ /dev/null
@@ -1,106 +0,0 @@
-#!/usr/bin/env python3
-# -*- coding: utf-8 -*-
-
-"""
-Usage: python unique.py [-f|--flip] [-x|--cross] image.png
-
-Erase duplicate tiles from an input image.
--f or --flip counts X/Y mirrored tiles as duplicates.
--x or --cross erases with a cross instead of a blank tile.
-"""
-
-import sys
-
-import png
-
-def rgb5_pixels(row):
- yield from (tuple(c // 8 for c in row[x:x+3]) for x in range(0, len(row), 4))
-
-def rgb8_pixels(row):
- yield from (c * 8 + c // 4 for pixel in row for c in pixel)
-
-def gray_pixels(row):
- yield from (pixel[0] // 10 for pixel in row)
-
-def rows_to_tiles(rows, width, height):
- assert len(rows) == height and len(rows[0]) == width
- yield from (tuple(tuple(row[x:x+8]) for row in rows[y:y+8])
- for y in range(0, height, 8) for x in range(0, width, 8))
-
-def tiles_to_rows(tiles, width, height):
- assert width % 8 == 0 and height % 8 == 0
- width, height = width // 8, height // 8
- tiles = list(tiles)
- assert len(tiles) == width * height
- tile_rows = (tiles[y:y+width] for y in range(0, width * height, width))
- yield from ([tile[y][x] for tile in tile_row for x in range(8)]
- for tile_row in tile_rows for y in range(8))
-
-def tile_variants(tile, flip):
- yield tile
- if flip:
- yield tile[::-1]
- yield tuple(row[::-1] for row in tile)
- yield tuple(row[::-1] for row in tile[::-1])
-
-def unique_tiles(tiles, flip, cross):
- if cross:
- blank = [[(0, 0, 0)] * 8 for _ in range(8)]
- for y in range(8):
- blank[y][y] = blank[y][7 - y] = (31, 31, 31)
- blank = tuple(tuple(row) for row in blank)
- else:
- blank = tuple(tuple([(31, 31, 31)] * 8) for _ in range(8))
- seen = set()
- for tile in tiles:
- if any(variant in seen for variant in tile_variants(tile, flip)):
- yield blank
- else:
- yield tile
- seen.add(tile)
-
-def is_grayscale(colors):
- return (colors.issubset({(31, 31, 31), (21, 21, 21), (10, 10, 10), (0, 0, 0)}) or
- colors.issubset({(31, 31, 31), (20, 20, 20), (10, 10, 10), (0, 0, 0)}))
-
-def erase_duplicates(filename, flip, cross):
- with open(filename, 'rb') as file:
- width, height, rows = png.Reader(file).asRGBA8()[:3]
- rows = [list(rgb5_pixels(row)) for row in rows]
- if width % 8 or height % 8:
- return False
- tiles = unique_tiles(rows_to_tiles(rows, width, height), flip, cross)
- rows = list(tiles_to_rows(tiles, width, height))
- if is_grayscale({c for row in rows for c in row}):
- rows = [list(gray_pixels(row)) for row in rows]
- writer = png.Writer(width, height, greyscale=True, bitdepth=2, compression=9)
- else:
- rows = [list(rgb8_pixels(row)) for row in rows]
- writer = png.Writer(width, height, greyscale=False, bitdepth=8, compression=9)
- with open(filename, 'wb') as file:
- writer.write(file, rows)
- return True
-
-def main():
- flip = cross = False
- while True:
- if len(sys.argv) < 2:
- print(f'Usage: {sys.argv[0]} [-f|--flip] [-x|--cross] tileset.png', file=sys.stderr)
- sys.exit(1)
- elif sys.argv[1] in {'-f', '--flip'}:
- flip = True
- elif sys.argv[1] in {'-x', '--cross'}:
- cross = True
- elif sys.argv[1] in {'-fx', '-xf'}:
- flip = cross = True
- else:
- break
- sys.argv.pop(1)
- for filename in sys.argv[1:]:
- if not filename.lower().endswith('.png'):
- print(f'{filename} is not a .png file!', file=sys.stderr)
- elif not erase_duplicates(filename, flip, cross):
- print(f'{filename} is not divisible into 8x8 tiles!', file=sys.stderr)
-
-if __name__ == '__main__':
- main()