98 lines
3.4 KiB
Python
98 lines
3.4 KiB
Python
#!/usr/bin/env python3
|
|
|
|
import argparse, itertools, os, struct, sys
|
|
from os import path
|
|
from sys import argv
|
|
|
|
parser = argparse.ArgumentParser(description=
|
|
'Convert a raw 24-bit RGB image into a packed 6-bit RGB image.',
|
|
epilog=
|
|
'Example usage: %(prog)s image.raw -n MyImage -a 0x0300 -l 0x00ff')
|
|
|
|
parser.add_argument('raw_file', nargs="+", help='A raw 24-bit RGB image')
|
|
parser.add_argument('-n', '--name',
|
|
help='Image name for variable definition/comments')
|
|
parser.add_argument('-a', '--start_address', type=lambda x:int(x, 0),
|
|
help='Start address for data')
|
|
parser.add_argument('-l', '--size_limit', type=lambda x:int(x, 0),
|
|
help='Size limit before splitting data segment')
|
|
parser.add_argument('-w', '--output_width', type=int, default=14,
|
|
help='Number of values to output before a line-break')
|
|
parser.add_argument('-d', '--add_defs', action='store_true',
|
|
help='Add variable definitions')
|
|
args = parser.parse_args()
|
|
|
|
stem = args.name
|
|
if stem is None:
|
|
stem = path.splitext(path.basename(args.raw_file))[0]
|
|
|
|
rawfile = stem + '.raw'
|
|
gclfile = stem + '.gcl'
|
|
|
|
raw = []
|
|
with open(rawfile, 'wb') as output:
|
|
for input_file in args.raw_file:
|
|
with open(input_file, 'rb') as input:
|
|
input.seek(0, os.SEEK_END)
|
|
size = input.tell()
|
|
input.seek(0, os.SEEK_SET)
|
|
|
|
while input.tell() < size:
|
|
# Read in 4 24-bit pixels and convert them to 6-bit pixels
|
|
pixels6 = []
|
|
for i in range(0, 4):
|
|
pixel24 = struct.unpack('<3B', input.read(3))
|
|
r = int(round((pixel24[0] / 255.0) * 3))
|
|
g = int(round((pixel24[1] / 255.0) * 3))
|
|
b = int(round((pixel24[2] / 255.0) * 3))
|
|
pixels6.append((b << 4) | (g << 2) | (r))
|
|
byte3 = ((pixels6[3] << 2) & 0xff) | ((pixels6[2] >> 4) & 0xff)
|
|
byte2 = ((pixels6[2] << 4) & 0xff) | ((pixels6[1] >> 2) & 0xff)
|
|
byte1 = ((pixels6[1] << 6) & 0xff) | ((pixels6[0]) & 0xff)
|
|
|
|
bytes = [byte1, byte2, byte3]
|
|
raw = itertools.chain(raw, bytes)
|
|
output.write(bytearray([byte1, byte2, byte3]))
|
|
|
|
# Write a GCL file
|
|
raw = list(raw)
|
|
with open(gclfile, 'w') as output:
|
|
defs_prefix = ''
|
|
if args.add_defs:
|
|
defs_prefix = '[def '
|
|
|
|
seg_start = args.start_address
|
|
|
|
split = len(raw)
|
|
if args.size_limit is not None:
|
|
split = args.size_limit
|
|
|
|
output.write('gcl0x\n\n')
|
|
n_seg = 0
|
|
for segment in [raw[i:i + split] for i in range(0, len(raw), split)]:
|
|
n_seg += 1
|
|
|
|
if args.start_address is not None:
|
|
output.write('$%04x:' % (seg_start))
|
|
seg_start += 0x100
|
|
|
|
if args.size_limit and len(raw) > args.size_limit:
|
|
output.write('\n%s{packed%s%02d}\n' % (defs_prefix, stem, n_seg))
|
|
else:
|
|
output.write('\n%s{packed%s}\n' % (defs_prefix, stem))
|
|
|
|
n_bytes = 0;
|
|
for val in segment:
|
|
if n_bytes == args.output_width:
|
|
output.write('\n')
|
|
n_bytes = 0
|
|
output.write(' $%02x#' % (val))
|
|
n_bytes += 1
|
|
|
|
if args.add_defs:
|
|
output.write('] packed%s%02d=\n' % (stem, n_seg))
|
|
if split < len(raw):
|
|
output.write('\n\\vLR>++ ret\n')
|
|
else:
|
|
output.write('\n\n')
|