From 64d9d7b3eb7cece81da8b2cb56eb0f50d87a5964 Mon Sep 17 00:00:00 2001 From: chai Date: Fri, 1 Mar 2019 08:50:34 +0800 Subject: *misc --- Source/Asura.Engine/Graphics/STBDecoder.cpp | 69 +++++++++++++++++++++++++++++ 1 file changed, 69 insertions(+) create mode 100644 Source/Asura.Engine/Graphics/STBDecoder.cpp (limited to 'Source/Asura.Engine/Graphics/STBDecoder.cpp') diff --git a/Source/Asura.Engine/Graphics/STBDecoder.cpp b/Source/Asura.Engine/Graphics/STBDecoder.cpp new file mode 100644 index 0000000..d4d578f --- /dev/null +++ b/Source/Asura.Engine/Graphics/STBDecoder.cpp @@ -0,0 +1,69 @@ +#include "STBDecoder.h" + +#include "Exceptions/Exception.h" +#include "stb/stb_image.h" + +namespace AsuraEngine +{ + namespace Graphics + { + + bool STBDecoder::CanDecode(const Filesystem::DataBuffer* buffer) + { + int w = 0; + int h = 0; + int comp = 0; + + int status = stbi_info_from_memory((const stbi_uc *)buffer->data, buffer->size, &w, &h, &comp); + + return status == 1 && w > 0 && h > 0; + } + + void STBDecoder::Decode(const Filesystem::DataBuffer* db, ImageData* imageData) + { + if (!db) + throw Exception("Could not decode image with stb decoder because of null databuffer."); + if (!imageData) + throw Exception("Could not decode image with stb decoder because of null output image data."); + const stbi_uc *buffer = (const stbi_uc *)db->data; + int bufferlen = db->size; + int width, height; + int comp = 0; + byte* data = nullptr; + PixelFormat format = PIXELFORMAT_UNKNOWN; + std::size_t size = 0; + + if (stbi_is_hdr_from_memory(buffer, bufferlen)) + { + // 4个channel都是float + data = (byte*)stbi_loadf_from_memory(buffer, bufferlen, &width, &height, &comp, STBI_rgb_alpha); + format = PIXELFORMAT_RGBA32F; + size = width * height * 4 * sizeof(float); + } + else + { + data = (byte*)stbi_load_from_memory(buffer, bufferlen, &width, &height, &comp, STBI_rgb_alpha); + format = PIXELFORMAT_ASTC_8x5; + size = width * height * 4; + } + if (data) + { + // 保证内存被释放,做一个防护,理论上不会出现没有释放的情况,因为image data是一次性的,image才是多次的。 + if (imageData->pixels) + delete[] imageData->pixels; + imageData->pixels = (byte*)data; + imageData->format = format; + imageData->width = width; + imageData->height = height; + } + else + { + const char *err = stbi_failure_reason(); + if (err == nullptr) + err = "unknown error"; + throw Exception("Could not decode image with stb_image (%s).", err); + } + } + + } +} \ No newline at end of file -- cgit v1.1-26-g67d0