Skip to content

Custom RLE

David Karnok edited this page Jan 29, 2022 · 2 revisions

The original game uses two run-length encoding schemes to compress the image data further. The two schemes mainly differ in how the numerous literal, uncompressed bytes need to be painted onto the output. Most likely the encoder side tries both methods and picks the one that produced smaller output. The uncompressed bytes are indexes into a palette table (stored in the ANI file, may change over time). The coding has instructions for skipping pixels which means that newer frames have to be drawn onto the previous frames.

The decompression algorithms are implemented in RLE.java.

RLE method 1

The datastream has a control byte that tells what to do with the subsequent bytes:

Byte Description
0..127 Uncompressed data to be copied as literal into the output buffer (indexes the current palette).
128 The following two bytes in the stream combined into an int16 (little endian) indicate how many bytes/pixels to skip in the output.
129..191 The lower 6 bytes (byte & 0x3F) indicate how many bytes/pixels to skip in the output.
192 The following two bytes in the stream combined into an int16 (little endian) indicates how many bytes/pixels to fill in, and the 3rd byte tells what value to use for filling.
193..255 The lower 6 bytes (byte & 0x3F) indicate how many bytes/pixels to fill in and the subsequent byte tells what value to use for filling in.

RLE method 2

The datastream has a control byte that tells what to do with the subsequent bytes:

Byte Description
0 The following two bytes combined into an int16 (little endian) indicate how many subsequent values to copy to the output.
1..127 The byte tells how many subsequent values to copy to the output.
128 The following two bytes in the stream combined into an int16 (little endian) indicate how many bytes/pixels to skip in the output.
129..191 The lower 6 bytes (byte & 0x3F) indicate how many bytes/pixels to skip in the output.
192 The following two bytes in the stream combined into an int16 (little endian) indicates how many bytes/pixels to fill in, and the 3rd byte tells what value to use for filling.
193..255 The lower 6 bytes (byte & 0x3F) indicate how many bytes/pixels to fill in and the subsequent byte tells what value to use for filling in.
Clone this wiki locally