Added support for ETC2/EAC compressed textures. Changed the CompressedFormat enum names to capitalize the format names (e.g. "PVR1rgba4" instead of "pvr1rgba4".) Improved sRGB support for compressed textures.

--HG--
branch : minor
This commit is contained in:
Alex Szpakowski
2015-01-20 07:53:44 -04:00
parent c1d4613ff7
commit 18ab3973e8
15 changed files with 170 additions and 52 deletions
+1 -2
View File
@@ -43,8 +43,7 @@ CompressedData::CompressedData(std::list<CompressedFormatHandler *> formats, lov
if (parser == nullptr)
throw love::Exception("Could not parse compressed data: Unknown format.");
// DataImages SubImage vector will be populated by a parser.
data = parser->parse(filedata, dataImages, dataSize, format);
data = parser->parse(filedata, dataImages, dataSize, format, sRGB);
if (data == nullptr)
throw love::Exception("Could not parse compressed data.");
@@ -60,10 +60,12 @@ public:
* to the returned data.
* @param[out] dataSize The total size in bytes of the returned data.
* @param[out] format The format of the Compressed Data.
* @param[out] sRGB Whether the texture is sRGB-encoded.
*
* @return The single block of memory containing the parsed images.
**/
virtual uint8 *parse(filesystem::FileData *filedata, std::vector<CompressedData::SubImage> &images, size_t &dataSize, CompressedData::Format &format) = 0;
virtual uint8 *parse(filesystem::FileData *filedata, std::vector<CompressedData::SubImage> &images,
size_t &dataSize, CompressedData::Format &format, bool &sRGB) = 0;
}; // CompressedFormatHandler
+30 -4
View File
@@ -67,7 +67,6 @@ enum KTXGLInternalFormat
{
KTX_GL_ETC1_RGB8_OES = 0x8D64,
// LOVE doesn't support EAC or ETC2 yet, but it won't be hard to add.
KTX_GL_COMPRESSED_R11_EAC = 0x9270,
KTX_GL_COMPRESSED_SIGNED_R11_EAC = 0x9271,
KTX_GL_COMPRESSED_RG11_EAC = 0x9272,
@@ -91,12 +90,37 @@ enum KTXGLInternalFormat
KTX_GL_COMPRESSED_RGBA_S3TC_DXT5_EXT = 0x83F3
};
CompressedData::Format convertFormat(uint32 glformat)
CompressedData::Format convertFormat(uint32 glformat, bool &sRGB)
{
sRGB = false;
switch (glformat)
{
case KTX_GL_ETC1_RGB8_OES:
return CompressedData::FORMAT_ETC1;
case KTX_GL_COMPRESSED_R11_EAC:
return CompressedData::FORMAT_EAC_R;
case KTX_GL_COMPRESSED_SIGNED_R11_EAC:
return CompressedData::FORMAT_EAC_Rs;
case KTX_GL_COMPRESSED_RG11_EAC:
return CompressedData::FORMAT_EAC_RG;
case KTX_GL_COMPRESSED_SIGNED_RG11_EAC:
return CompressedData::FORMAT_EAC_RGs;
case KTX_GL_COMPRESSED_RGB8_ETC2:
return CompressedData::FORMAT_ETC2_RGB;
case KTX_GL_COMPRESSED_SRGB8_ETC2:
sRGB = true;
return CompressedData::FORMAT_ETC2_RGB;
case KTX_GL_COMPRESSED_RGB8_PUNCHTHROUGH_ALPHA1_ETC2:
return CompressedData::FORMAT_ETC2_RGBA1;
case KTX_GL_COMPRESSED_SRGB8_PUNCHTHROUGH_ALPHA1_ETC2:
sRGB = true;
return CompressedData::FORMAT_ETC2_RGBA1;
case KTX_GL_COMPRESSED_RGBA8_ETC2_EAC:
return CompressedData::FORMAT_ETC2_RGBA;
case KTX_GL_COMPRESSED_SRGB8_ALPHA8_ETC2_EAC:
sRGB = true;
return CompressedData::FORMAT_ETC2_RGBA;
case KTX_GL_COMPRESSED_RGB_PVRTC_4BPPV1_IMG:
return CompressedData::FORMAT_PVR1_RGB4;
case KTX_GL_COMPRESSED_RGB_PVRTC_2BPPV1_IMG:
@@ -135,7 +159,7 @@ bool KTXHandler::canParse(const filesystem::FileData *data)
return true;
}
uint8 *KTXHandler::parse(filesystem::FileData *filedata, std::vector<CompressedData::SubImage> &images, size_t &dataSize, CompressedData::Format &format)
uint8 *KTXHandler::parse(filesystem::FileData *filedata, std::vector<CompressedData::SubImage> &images, size_t &dataSize, CompressedData::Format &format, bool &sRGB)
{
if (!canParse(filedata))
throw love::Exception("Could not decode compressed data (not a KTX file?)");
@@ -151,7 +175,8 @@ uint8 *KTXHandler::parse(filesystem::FileData *filedata, std::vector<CompressedD
header.numberOfMipmapLevels = std::max(header.numberOfMipmapLevels, 1u);
CompressedData::Format cformat = convertFormat(header.glInternalFormat);
bool isSRGB = false;
CompressedData::Format cformat = convertFormat(header.glInternalFormat, isSRGB);
if (cformat == CompressedData::FORMAT_UNKNOWN)
throw love::Exception("Unsupported image format in KTX file.");
@@ -232,6 +257,7 @@ uint8 *KTXHandler::parse(filesystem::FileData *filedata, std::vector<CompressedD
dataSize = totalsize;
format = cformat;
sRGB = isSRGB;
return data;
}
+1 -1
View File
@@ -42,7 +42,7 @@ public:
// Implements CompressedFormatHandler.
virtual bool canParse(const filesystem::FileData *data);
virtual uint8 *parse(filesystem::FileData *filedata, std::vector<CompressedData::SubImage> &images, size_t &dataSize, CompressedData::Format &format);
virtual uint8 *parse(filesystem::FileData *filedata, std::vector<CompressedData::SubImage> &images, size_t &dataSize, CompressedData::Format &format, bool &sRGB);
}; // KTXHandler
+17 -1
View File
@@ -74,6 +74,21 @@ CompressedData::Format convertFormat(uint16 texformat)
{
case ETC1_RGB_NO_MIPMAPS:
return CompressedData::FORMAT_ETC1;
case ETC2PACKAGE_RGB_NO_MIPMAPS:
return CompressedData::FORMAT_ETC2_RGB;
case ETC2PACKAGE_RGBA_NO_MIPMAPS_OLD:
case ETC2PACKAGE_RGBA_NO_MIPMAPS:
return CompressedData::FORMAT_ETC2_RGBA;
case ETC2PACKAGE_RGBA1_NO_MIPMAPS:
return CompressedData::FORMAT_ETC2_RGBA1;
case ETC2PACKAGE_R_NO_MIPMAPS:
return CompressedData::FORMAT_EAC_R;
case ETC2PACKAGE_RG_NO_MIPMAPS:
return CompressedData::FORMAT_EAC_RG;
case ETC2PACKAGE_R_SIGNED_NO_MIPMAPS:
return CompressedData::FORMAT_EAC_Rs;
case ETC2PACKAGE_RG_SIGNED_NO_MIPMAPS:
return CompressedData::FORMAT_EAC_RGs;
default:
return CompressedData::FORMAT_UNKNOWN;
}
@@ -98,7 +113,7 @@ bool PKMHandler::canParse(const filesystem::FileData *data)
return true;
}
uint8 *PKMHandler::parse(filesystem::FileData *filedata, std::vector<CompressedData::SubImage> &images, size_t &dataSize, CompressedData::Format &format)
uint8 *PKMHandler::parse(filesystem::FileData *filedata, std::vector<CompressedData::SubImage> &images, size_t &dataSize, CompressedData::Format &format, bool &sRGB)
{
if (!canParse(filedata))
throw love::Exception("Could not decode compressed data (not a PKM file?)");
@@ -146,6 +161,7 @@ uint8 *PKMHandler::parse(filesystem::FileData *filedata, std::vector<CompressedD
dataSize = totalsize;
format = cformat;
sRGB = false;
return data;
}
+1 -1
View File
@@ -42,7 +42,7 @@ public:
// Implements CompressedFormatHandler.
virtual bool canParse(const filesystem::FileData *data);
virtual uint8 *parse(filesystem::FileData *filedata, std::vector<CompressedData::SubImage> &images, size_t &dataSize, CompressedData::Format &format);
virtual uint8 *parse(filesystem::FileData *filedata, std::vector<CompressedData::SubImage> &images, size_t &dataSize, CompressedData::Format &format, bool &sRGB);
}; // PKMHandler
+2 -1
View File
@@ -294,7 +294,7 @@ bool PVRHandler::canParse(const filesystem::FileData *data)
return false;
}
uint8 *PVRHandler::parse(filesystem::FileData *filedata, std::vector<CompressedData::SubImage> &images, size_t &dataSize, CompressedData::Format &format)
uint8 *PVRHandler::parse(filesystem::FileData *filedata, std::vector<CompressedData::SubImage> &images, size_t &dataSize, CompressedData::Format &format, bool &sRGB)
{
if (!canParse(filedata))
throw love::Exception("Could not decode compressed data (not a PVR file?)");
@@ -376,6 +376,7 @@ uint8 *PVRHandler::parse(filesystem::FileData *filedata, std::vector<CompressedD
dataSize = totalsize;
format = cformat;
sRGB = (header3.colorSpace == 1);
return data;
}
+1 -1
View File
@@ -40,7 +40,7 @@ public:
// Implements CompressedFormatHandler.
virtual bool canParse(const filesystem::FileData *data);
virtual uint8 *parse(filesystem::FileData *filedata, std::vector<CompressedData::SubImage> &images, size_t &dataSize, CompressedData::Format &format);
virtual uint8 *parse(filesystem::FileData *filedata, std::vector<CompressedData::SubImage> &images, size_t &dataSize, CompressedData::Format &format, bool &sRGB);
}; // PVRHandler
+9 -4
View File
@@ -32,12 +32,13 @@ bool DDSHandler::canParse(const filesystem::FileData *data)
return dds::isCompressedDDS(data->getData(), data->getSize());
}
uint8 *DDSHandler::parse(filesystem::FileData *filedata, std::vector<CompressedData::SubImage> &images, size_t &dataSize, CompressedData::Format &format)
uint8 *DDSHandler::parse(filesystem::FileData *filedata, std::vector<CompressedData::SubImage> &images, size_t &dataSize, CompressedData::Format &format, bool &sRGB)
{
if (!dds::isDDS(filedata->getData(), filedata->getSize()))
throw love::Exception("Could not decode compressed data (not a DDS file?)");
CompressedData::Format texformat = CompressedData::FORMAT_UNKNOWN;
bool isSRGB = false;
uint8 *data = nullptr;
dataSize = 0;
@@ -48,7 +49,7 @@ uint8 *DDSHandler::parse(filesystem::FileData *filedata, std::vector<CompressedD
// Attempt to parse the dds file.
dds::Parser parser(filedata->getData(), filedata->getSize());
texformat = convertFormat(parser.getFormat());
texformat = convertFormat(parser.getFormat(), isSRGB);
if (texformat == CompressedData::FORMAT_UNKNOWN)
throw love::Exception("Could not parse compressed data: Unsupported format.");
@@ -96,11 +97,14 @@ uint8 *DDSHandler::parse(filesystem::FileData *filedata, std::vector<CompressedD
}
format = texformat;
sRGB = isSRGB;
return data;
}
CompressedData::Format DDSHandler::convertFormat(dds::Format ddsformat)
CompressedData::Format DDSHandler::convertFormat(dds::Format ddsformat, bool &sRGB)
{
sRGB = false;
switch (ddsformat)
{
case dds::FORMAT_DXT1:
@@ -124,7 +128,8 @@ CompressedData::Format DDSHandler::convertFormat(dds::Format ddsformat)
case dds::FORMAT_BC7:
return CompressedData::FORMAT_BC7;
case dds::FORMAT_BC7srgb:
return CompressedData::FORMAT_BC7SRGB;
sRGB = true;
return CompressedData::FORMAT_BC7;
default:
return CompressedData::FORMAT_UNKNOWN;
}
+2 -2
View File
@@ -48,11 +48,11 @@ public:
// Implements CompressedFormatHandler.
virtual bool canParse(const filesystem::FileData *data);
virtual uint8 *parse(filesystem::FileData *filedata, std::vector<CompressedData::SubImage> &images, size_t &dataSize, CompressedData::Format &format);
virtual uint8 *parse(filesystem::FileData *filedata, std::vector<CompressedData::SubImage> &images, size_t &dataSize, CompressedData::Format &format, bool &sRGB);
private:
static CompressedData::Format convertFormat(dds::Format ddsformat);
static CompressedData::Format convertFormat(dds::Format ddsformat, bool &sRGB);
}; // DDSHandler