donmccurdy / KTX-Parse

KTX 2.0 (.ktx2) parser and serializer.
MIT License
48 stars 7 forks source link

Exported files with multiple mip levels are invalid #117

Closed brianchirls closed 7 months ago

brianchirls commented 7 months ago

I'm seeing a couple of issues here:

First, the mip levels are stored in the wrong order. Per Section 3.13 of the spec:

Mip levels in the array are ordered from the level with the smallest size images, 𝑙𝑒𝑣𝑒𝑙𝑝 to that with the largest size images, 𝑙𝑒𝑣𝑒𝑙𝑏𝑎𝑠𝑒.

Note that the level index is still stored largest to smallest.

Second, mip level data is required to be aligned to the texel block size. See Section 3.13.2 and Section 3.9.7 on byteLength. This only applies when the supercompressionScheme is zero, since for super-compressed data, the block alignment is 1. It's not entirely clear from the spec, but I believe the mip padding comes before the level data, which would make sense to achieve the desired block alignment.

Note that the texel block size for each format is given in a giant table, but I think you can derive it by dividing the largest mip level byte length by the total number of pixels.

Thanks for reading and for this useful code!

brianchirls commented 7 months ago

There's a little more information in the levelImages description. It looks like you only need mip padding once before all the level data (makes sense), and there's some math on how to compute the total number of blocks, which would seem to enable derivation of the block size, as mentioned above.

donmccurdy commented 7 months ago

Thank you @brianchirls! Work in progress at https://github.com/donmccurdy/KTX-Parse/pull/120.

donmccurdy commented 7 months ago

Fixed and published to v0.7.0, thank you! This was a good nudge to go ahead and get ktx validate *.ktx2 wired up as part of the test suite.

brianchirls commented 7 months ago

Thanks @donmccurdy!!