#!/usr/bin/env python3 """ Decode the PREV (preview thumbnail) section from a pm4n file and save as PNG. Run: python3 decode_prev.py """ import struct, sys from pathlib import Path path = sys.argv[1] data = open(path, 'rb').read() prev_off = data.find(b'PREV') print(f"PREV at 0x{prev_off:06X}") # PREV section layout (from ANYCUBIC format docs and common reverse-engineering): # +0x00 "PREV" # +0x04 u32 section_length # +0x08 u32 image_width # +0x0C u32 image_height # +0x10 u32 image_data_length # +0x14 image data (RGB565 or RLE) for hdr_size in [0x14, 0x18, 0x10, 0x0C]: w = struct.unpack_from(' plausible dimensions {w}x{h}, data at +0x14, {dlen} bytes") break # Show first 64 bytes of PREV section print(f"\nPREV raw (first 64 bytes):") chunk = data[prev_off:prev_off+64] for i in range(0, 64, 16): row = chunk[i:i+16] hex_p = ' '.join(f'{b:02X}' for b in row) u_vals = [struct.unpack_from('> 11) & 0x1F) << 3 g = ((px >> 5) & 0x3F) << 2 b = (px & 0x1F) << 3 pixels.append((r, g, b)) img = Image.new('RGB', (w, h)) img.putdata(pixels) out = Path(path).with_suffix('.prev_thumb.png') img.save(out) print(f" Saved thumbnail to {out}") except Exception as e: print(f" Error: {e}") else: print(f" Size mismatch or bad dims, skipping decode") print(f" Expected {w*h*2} bytes for RGB565, got {img_data_len}")