SixLabors / ImageSharp.Textures

Texture loading and manipulation library
Apache License 2.0
61 stars 13 forks source link

KTX2 support #3

Open vpenades opened 3 years ago

vpenades commented 3 years ago

It looks like the final draft of the Universal Basis KTX2 format has been published.

I would suggest to begin doing some prospective work on this format, since it's been designed to become "the mother of all texture formats"

It is worth to note that KTX2 includes support for some of the compression formats already covered by DDS.

JimBobSquarePants commented 3 years ago

Feel free to have a go. Would be cool to have support.

brianpopow commented 3 years ago

I have started working on support for decoding ktx2 texture. We already support a large variety of pixel formats and some compressions which are common to other formats like dds (e.g. DXT1, DXT3, DXT5 and BC4-BC7). Whats missing is support for compression like ETC and ASTC.

vpenades commented 3 years ago

Question: I did not have time to check the library, but I would like to use it in one of my projects...

One of the advantages of KTX2 is that the underlaying data can be "decoded" to DDS or ETC on demand, instead of the classic RGB decoding, so the textures can be uploaded to the host GPU in a format that's able to decode to RGB on execution.

I understand this library is able to do that? I mean: decoding ktx2 to DDS or ETC ?

I also understand that for now, encoding is out of scope, right?

brianpopow commented 3 years ago

One of the advantages of KTX2 is that the underlaying data can be "decoded" to DDS or ETC on demand, instead of the classic RGB decoding, so the textures can be uploaded to the host GPU in a format that's able to decode to RGB on execution.

I understand this library is able to do that? I mean: decoding ktx2 to DDS or ETC ?

I think I am not sure that i understand what you mean by that. Usually the compressions are tied to a specific pixel format. For example ETC1 decodes a block into 4x4 pixels of RGB data. Similar DXT1 decodes a block to pixels with RGB565. While DXT3 decodes to RGB with alpha. So the texture will always be decompressed to a specific pixel format.

Maybe you could point me to the section of the KTX 2 Specification you are talking about, so i get a better understanding of the usecase (I have no experience with game development)

I also understand that for now, encoding is out of scope, right?

At the moment i do focus on covering the decoding of all the different compressions. I would not say encoding is completely out of scope, but i would say decoding is more common usecase for most users. I do think it should be fairly simple to add encoding for uncompressed textures, though. For encoding with compression, i would need help to do so. That would be to much just for me to do alone.

vpenades commented 3 years ago

@brianpopow DDS and other block compression based images are decoded to RGB when you want to process them as normal images, like in a content processing pipeline, or generating a thumbnail, etc.

But, whe you load them to the GPU as textures you don't decompress the textures to RGB, you upload the block bytes as is to the GPU, because modern GPUs can decode the blocks at render time.

The problem with block compressed textures is that they're chipset specific, so Dtx encodings are usually found in desktop graphics cards, and ETC encoding is found in smartphone graphics chipsets.

This presents a problem, because a developer needs to provide different texture encodings, depending on the target platform.

At this point, KTX2 is introduced: the idea of KTX2 is not (only) decompress KTX2 blocks to RGB, but to decompress KTX2 blocks to Dtx and Etc blocks at load time.

So, the actual use of KTX2 for realtime rendering is, on load, transcode the blocks to Dtx or Etc, based on the host support, and then upload the transcoded blocks to the gpu as Dtx or Etc.

You can read the theory behind the format here: https://github.com/BinomialLLC/basis_universal

Basis Universal is a "supercompressed" GPU texture compression system that outputs a highly compressed intermediate file format (.basis) that can be quickly transcoded to a very wide variety of GPU compressed and uncompressed pixel formats: ASTC 4x4 L/LA/RGB/RGBA, PVRTC1 4bpp RGB/RGBA, PVRTC2 RGB/RGBA, BC7 mode 6 RGB, BC7 mode 5 RGB/RGBA, BC1-5 RGB/RGBA/X/XY, ETC1 RGB, ETC2 RGBA, ATC RGB/RGBA, ETC2 EAC R11 and RG11, FXT1 RGB, and uncompressed raster image formats 8888/565/4444.

This information is probably outdated, but Ktx2 is built upon the same theory: decoding is not done against RGB, it is done against known GPU block encodings (and from there, to RGB if you wish)