Xtool -mpng+reflate !free! Official
def extract_mpng_streams(png_path): """Extract all zlib-compressed streams from MPNG chunks""" streams = [] with open(png_path, 'rb') as f: # Verify PNG signature if f.read(8) != PNG_SIGNATURE: raise ValueError("Not a valid PNG file")
while True: chunk_type, data, _ = read_chunk(f) if chunk_type == CHUNK_TYPE_MPNG: # MPNG chunk structure: [index:4][compressed_data...] idx = struct.unpack('>I', data[:4])[0] compressed = data[4:] streams.append((idx, compressed)) elif chunk_type == CHUNK_TYPE_IEND: break return streams def reflate_stream(compressed_data, level=6, extract_only=False): """Reflate: decompress then recompress zlib stream""" decompressed = zlib.decompress(compressed_data) if extract_only: return decompressed # raw decompressed data recompressed = zlib.compress(decompressed, level) return recompressed xtool -mpng+reflate
def rebuild_png_with_mpng(input_path, output_path, streams, recompress_level=6, replace_map=None): """Rebuild PNG with modified MPNG streams""" with open(input_path, 'rb') as fin, open(output_path, 'wb') as fout: fout.write(fin.read(8)) # PNG signature data[:4])[0] compressed = data[4:] streams.append((idx