#include "utils/logger.h" #include "filesystem/filemanager.h" #include "render/texture2d.h" #include "render/texturesmanager.h" #include "render/gl_shared.h" // STB Image loading code void Texture2D::CreateFromFile(const char* filename) { /* int width, height, channels; m_textureFileName = filename; File* file = g_fileManager->OpenFile(filename, FileAccess::Read); file->seek(SeekDir::End, 0); size_t imageSize = file->tell(); file->seek(SeekDir::Begin, 0); uint8_t* fileData = (uint8_t*)malloc(imageSize); file->read(fileData, imageSize); g_fileManager->CloseFile(file); uint8_t* imageData = stbi_load_from_memory(fileData, int(imageSize), &width, &height, &channels, 0); if (imageData == NULL) { free(fileData); Msg("Texture loading error: %s (%s)", filename, stbi_failure_reason()); assert(imageData); } CreateFromExistedData(imageData, width, height, channels); m_textureFileName = filename; free(fileData); stbi_image_free(imageData); */ } static const char* g_texFileExtensions[] = { ".png", ".jpeg", ".jpg", ".tga", ".bmp" }; const int kTexFileExtensionsSize = sizeof(g_texFileExtensions) / sizeof(g_texFileExtensions[0]); TexturesManager* g_texturesManager = NULL; TexturesManager::TexturesManager() { m_notex = NULL; } TexturesManager::~TexturesManager() { } void TexturesManager::Init() { //stbi_set_flip_vertically_on_load(true); m_notex = LoadTexture2D("content/textures/system/notex.png", true); if (!m_notex) { Logger::Error("TexturesManager::Init: Failed to initialize system texture! 'system/notex.png' is not exist."); } } void TexturesManager::Shutdown() { if (!m_textures.empty()) { LogMsg("--- unfreed textures ---"); for (std::vector::iterator it = m_textures.begin(); it != m_textures.end(); ++it) { LogMsg("%s", (*it)->m_textureFileName.c_str()); delete* it; *it = NULL; } m_textures.clear(); } } void TexturesManager::SetTexture(int slot, Texture2D* texture) { glActiveTexture(GL_TEXTURE0 + slot); glBindTexture(GL_TEXTURE_2D, texture ? texture->GetHandle() : 0); } Texture2D* TexturesManager::CreateManual2D(const char* name, int width, int height, PixelFormat format, bool useAsRenderTarget) { for (std::vector::iterator it = m_textures.begin(); it != m_textures.end(); ++it) { if ((*it)->m_textureFileName == name) { Logger::Error("TexturesManager::CreateManual2D: texture %s is already created!", name); } } // allocate Texture2D* texture = Texture2D::Create(); texture->CreateRaw(nullptr, width, height, format); texture->m_textureFileName = name; if (useAsRenderTarget) LogMsg("Created rt texture [%s]", name); return texture; } bool IsSupportedExtension(const char* filename) { std::string ext = fs::getFileExtension(filename); for (int i = 0; i < kTexFileExtensionsSize; i++) { if (ext == g_texFileExtensions[i]) { return true; } } return false; } Texture2D* TexturesManager::LoadTexture2D(const char* texturename, bool useMipmaps /*= false*/) { int texturesNbr = m_textures.size(); for (int i = 0; i < texturesNbr; i++) { if (m_textures[i]->m_textureFileName == texturename) return m_textures[i]; } if (strcmp(texturename, "$white$") == 0) { Texture2D* tex = Texture2D::Create(); tex->m_textureFileName = "$white$"; tex->CreateWhiteTexture(16, 16, 3); m_textures.push_back(tex); return tex; } if (strcmp(texturename, "$black$") == 0) { Texture2D* tex = Texture2D::Create(); tex->m_textureFileName = "$black$"; tex->CreateBlackTexture(16, 16, 3); m_textures.push_back(tex); return tex; } if (strcmp(texturename, "$gray$") == 0) { Texture2D* tex = Texture2D::Create(); tex->m_textureFileName = "$gray$"; tex->CreateGrayTexture(16, 16, 3); m_textures.push_back(tex); return tex; } if (strcmp(texturename, "$gray_console$") == 0) { Texture2D* tex = Texture2D::Create(); tex->CreateTexture_Generator(16, 16, 3, 32); m_textures.push_back(tex); return tex; } if (strlen(texturename) <= 0) { return m_notex; } std::string texnamebuf; // find texture from disk for (int i = 0; i < kTexFileExtensionsSize; i++) { std::string textureFilename = fs::getFileNameWithoutExtension(texturename); textureFilename += g_texFileExtensions[i]; if (g_fileManager->FileExist(textureFilename.c_str())) { texnamebuf = textureFilename; break; } } if (!texnamebuf.empty()) { Texture2D* texture = Texture2D::Create(); texture->CreateFromFile(texnamebuf.c_str()); if (useMipmaps) texture->GenerateMipmaps(); LogMsg("loaded %s", fs::getFilenameWithoutPathAndExtension(texturename).c_str()); m_textures.push_back(texture); return texture; } else if (texnamebuf.empty() && m_notex) { LogMsg("not found %s", fs::getFilenameWithoutPathAndExtension(texturename).c_str()); return m_notex; } return NULL; }