Okay, I looked into G2M4 closer, here’s the output:
As with the previous beast, there are two types of images combined in single tile โ so-called synthetic layer and natural layer. What you see if the first layer decoded.
Here’s the general tile structure:
- Compression subtype (top bits from the first byte).
- Transparency colour (three bytes)
- Number of palette entries minus one (one byte)
- Palette entries (byte triplets)
- Synthetic layer (16-bit BE chunk size plus deflated data, may be not present)
- Natural layer (probably headerless JPEG data, too lazy to verify)
Synthetic layer image is (after decompression) contains packed bitmap that uses palette from above, each row is coded as 8-bit flag [packed row data]
. If the flag is zero then row data is present (that’s my guess, it always seems to be zero). Row data is just palette indices stored as 1/2/4 or 8 bits per index depending on palette size. Sample output you can see above.
Feel free to complete RE.
to complete it? is there some codebase / patches somewhere?
your decoded image looks good! ๐
what does g2m do? try to optimize a screen so that plain one-color backgrounds and text get simple processing and images get jpg processing? does all of that REALLY help the compression ratio in the long run vs just using mjpeg ?
i guess mjpeg isnt great at text.
@compn
To complete? Yes รขโฌโ the format is almost known already, just write a proper decoder. I have a hack for decoder but I won’t release it (now at least) because it’s not functioning properly and ugly.
As for G2M base principle, it seems to code sharp details separately so they stay sharp and there are definitely less bits are wasted on compressing smoother JPEG background. Feel free to paint some smooth background, save its copy as JPEG at fixed quality, paint something with sharp edges over it, save that as JPEG at the same quality and compare the output file sizes.
Also MSS3/4 have blocks coded as in JPEG and some special coding mixed exactly for this reason.