31 lines
1.2 KiB
Python
31 lines
1.2 KiB
Python
"""Apple IIGS Super Hi-Res colour helpers.
|
|
|
|
SHR colours are 12-bit ``$0RGB`` -- 4 bits per channel, each level scaled x17
|
|
(0->0, 15->255), exactly as MAME's apple2gs palette. There is no fixed master
|
|
palette: each of the 16 line-palettes holds 16 freely chosen 12-bit colours, so
|
|
the encoder works in the continuous 4096-colour space and quantises to 12-bit.
|
|
"""
|
|
from __future__ import annotations
|
|
|
|
import numpy as np
|
|
|
|
|
|
def quantize12(rgb):
|
|
"""Snap an RGB array (..,3) float 0-255 to the nearest 12-bit SHR colour."""
|
|
q4 = np.clip(np.rint(np.asarray(rgb) / 17.0), 0, 15).astype(np.int64)
|
|
return q4 * 17, q4 # (rgb 0..255 in x17 steps, 4-bit)
|
|
|
|
|
|
def color_word(r4: int, g4: int, b4: int) -> bytes:
|
|
"""16-bit little-endian SHR palette entry: low = (G<<4)|B, high = $0R."""
|
|
lo = ((g4 & 0x0F) << 4) | (b4 & 0x0F)
|
|
hi = r4 & 0x0F
|
|
return bytes([lo, hi])
|
|
|
|
|
|
def greys12(n: int = 16):
|
|
"""``n`` evenly spaced 12-bit greys, black..white (RGB array, 4-bit array)."""
|
|
lv4 = np.clip(np.rint(np.linspace(0, 15, n)), 0, 15).astype(np.int64)
|
|
rgb = np.stack([lv4 * 17] * 3, axis=1).astype(np.float64)
|
|
q4 = np.stack([lv4] * 3, axis=1)
|
|
return rgb, q4
|