#include "pch.h" #include "log.h" #include "asset.h" #ifdef __APPLE__ #include #endif #ifdef __ANDROID__ AAssetManager* Asset::m_am; #endif std::vector Asset::list_files(std::string folder, bool is_asset, const std::string& filter_regex) { std::vector names; #ifdef _WIN32 WIN32_FIND_DATAA fd; HANDLE hFind = ::FindFirstFileA((folder + "*").c_str(), &fd); if (hFind != INVALID_HANDLE_VALUE) { do { // read all (real) files in current folder // , delete '!' read other 2 default folder . and .. if (!(fd.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY)) { names.push_back(fd.cFileName); } } while (::FindNextFileA(hFind, &fd)); ::FindClose(hFind); } #elif __ANDROID__ if (is_asset) { AAssetDir* dir = AAssetManager_openDir(Asset::m_am, folder.c_str()); while (const char* name = AAssetDir_getNextFileName(dir)) { //LOG("asset: %s", name); names.push_back(name); } AAssetDir_close(dir); } else { } #else if (is_asset) { NSString* bundle_path = [[NSBundle mainBundle] resourcePath]; std::string base = [bundle_path cStringUsingEncoding : 1]; std::string abs_path = base + "/" + folder; } DIR *dp; struct dirent *ep; dp = opendir(abs_path.c_str()); if (dp != NULL) { while ((ep = readdir(dp))) if (ep->d_type != DT_DIR) names.push_back(ep->d_name); closedir(dp); } else LOG("Couldn't open the directory: %s", folder.c_str()); #endif if (!filter_regex.empty()) { std::regex r(filter_regex); names.erase(std::remove_if(names.begin(), names.end(), [&r](const std::string& s) { return !std::regex_match(s, r); }), names.end()); } return names; } bool Asset::open(const char* path) { LOG("Asset::open %s", path); m_current_path = path; std::string file_path = path; #ifdef __ANDROID__ if (!(m_asset = AAssetManager_open(m_am, path, AASSET_MODE_RANDOM))) { LOG("AAssetManager_open failed"); return false; } m_len = (int)AAsset_getLength(m_asset); m_data = (uint8_t*)AAsset_getBuffer(m_asset); #else #ifdef __APPLE__ NSString* bundle_path = [[NSBundle mainBundle] resourcePath]; std::string base = [bundle_path cStringUsingEncoding:1]; file_path = base + "/" + path; #endif LOG("asset file: %s", file_path.c_str()); if (!(m_fp = fopen(file_path.c_str(), "rb"))) { LOG("errno = %d", errno); return false; } fseek(m_fp, 0, SEEK_END); m_len = (int)ftell(m_fp); fseek(m_fp, 0, SEEK_SET); #endif return true; } glm::uint8_t* Asset::read_all() { #ifdef __ANDROID__ return m_data; #else if (!m_data) { m_data = new uint8_t[m_len]; if (m_len != fread(m_data, 1, m_len, m_fp)) { LOG("ASSET READ FAILED for %s", m_current_path.c_str()); delete m_data; m_data = nullptr; } } return m_data; #endif } void Asset::close() { #ifdef __ANDROID__ AAsset_close(m_asset); #else if (m_fp) fclose(m_fp); if (m_data) delete m_data; m_data = nullptr; #endif }