diff --git a/JGE/src/JFileSystem.cpp b/JGE/src/JFileSystem.cpp index 2b9b2cb07..43477fe10 100644 --- a/JGE/src/JFileSystem.cpp +++ b/JGE/src/JFileSystem.cpp @@ -1,277 +1,287 @@ -//------------------------------------------------------------------------------------- -// -// JGE++ is a hardware accelerated 2D game SDK for PSP/Windows. -// -// Licensed under the BSD license, see LICENSE in JGE root for details. -// -// Copyright (c) 2007 James Hui (a.k.a. Dr.Watson) -// -//------------------------------------------------------------------------------------- - -#ifdef WIN32 - #pragma warning(disable : 4786) -#endif - -#include "../include/JGE.h" -#include "../include/JFileSystem.h" -#include "../include/JLogger.h" -#include "tinyxml/tinyxml.h" -#include "unzip/unzip.h" - - -#include -#include -#include -#include - - -JZipCache::JZipCache(){} - -JZipCache::~JZipCache(){ - map::iterator it; - for (it = dir.begin(); it != dir.end(); it++){ - delete(it->second); - } - dir.clear(); -} - -void JFileSystem::preloadZip(string filename){ - map::iterator it = mZipCache.find(filename); - if (it != mZipCache.end()) return; - - JZipCache * cache = new JZipCache(); - mZipCache[filename] = cache; - - if (!mZipAvailable || !mZipFile) { - AttachZipFile(filename); - if (!mZipAvailable || !mZipFile) return; - } - int err = unzGoToFirstFile (mZipFile); - while (err == UNZ_OK){ - unz_file_pos* filePos = new unz_file_pos(); - char filenameInzip[4096]; - if (unzGetCurrentFileInfo(mZipFile, NULL, filenameInzip, sizeof(filenameInzip), NULL, 0, NULL, 0) == UNZ_OK){ - unzGetFilePos(mZipFile, filePos); - string name = filenameInzip; - cache->dir[name] = filePos; - } - err = unzGoToNextFile(mZipFile); - } -} - -JFileSystem* JFileSystem::mInstance = NULL; - -JFileSystem* JFileSystem::GetInstance() -{ - if (mInstance == NULL) - { - mInstance = new JFileSystem(); - } - - return mInstance; -} - - -void JFileSystem::Destroy() -{ - if (mInstance) - { - delete mInstance; - mInstance = NULL; - } -} - - -JFileSystem::JFileSystem() -{ - mZipAvailable = false; -#if defined (WIN32) || defined (LINUX) || defined (IOS) - mFile = NULL; -#else - mFile = -1; -#endif - mPassword = NULL; - mZipFile = NULL; - mFileSize = 0; - -#ifdef RESPATH - SetResourceRoot(RESPATH"/"); -#else - SetResourceRoot("Res/"); // default root folder -#endif -} - - -JFileSystem::~JFileSystem() -{ - DetachZipFile(); - - map::iterator it; - for (it = mZipCache.begin(); it != mZipCache.end(); it++){ - delete(it->second); - } - mZipCache.clear(); -} - - -bool JFileSystem::AttachZipFile(const string &zipfile, char *password /* = NULL */) -{ - if (mZipAvailable && mZipFile != NULL) - { - if (mZipFileName != zipfile) - DetachZipFile(); // close the previous zip file - else - return true; - } - - mZipFileName = zipfile; - mPassword = password; - - mZipFile = unzOpen(mZipFileName.c_str()); - - if (mZipFile != NULL) - { - mZipAvailable = true; - return true; - } - - return false; -} - - -void JFileSystem::DetachZipFile() -{ - if (mZipAvailable && mZipFile != NULL) - { - unzCloseCurrentFile(mZipFile); - unzClose(mZipFile); - } - - mZipFile = NULL; - mZipAvailable = false; -} - - -bool JFileSystem::OpenFile(const string &filename) -{ - - string path = mResourceRoot + filename; - JLOG("JFileSystem::OpenFile"); - JLOG(path.c_str()); - - if (mZipAvailable && mZipFile != NULL) - { - preloadZip(mZipFileName); - map::iterator it = mZipCache.find(mZipFileName); - if (it == mZipCache.end()){ - DetachZipFile(); - return OpenFile(filename); - } - JZipCache * zc = it->second; - map::iterator it2 = zc->dir.find(filename); - if (it2 == zc->dir.end()){ - DetachZipFile(); - return OpenFile(filename); - } - unzGoToFilePos(mZipFile,it2->second); - char filenameInzip[256]; - unz_file_info fileInfo; - - if (unzGetCurrentFileInfo(mZipFile, &fileInfo, filenameInzip, sizeof(filenameInzip), NULL, 0, NULL, 0) == UNZ_OK) - mFileSize = fileInfo.uncompressed_size; - else - mFileSize = 0; - - return (unzOpenCurrentFilePassword(mZipFile, mPassword) == UNZ_OK); - } - else - { - #if defined (WIN32) || defined (LINUX)|| defined (IOS) - mFile = fopen(path.c_str(), "rb"); - if (mFile != NULL) - { - fseek(mFile, 0, SEEK_END); - mFileSize = ftell(mFile); - fseek(mFile, 0, SEEK_SET); - return true; - } - #else - mFile = sceIoOpen(path.c_str(), PSP_O_RDONLY, 0777); - if (mFile > 0) - { - mFileSize = sceIoLseek(mFile, 0, PSP_SEEK_END); - sceIoLseek(mFile, 0, PSP_SEEK_SET); - return true; - } - #endif - - - } - - return false; - -} - - -void JFileSystem::CloseFile() -{ - if (mZipAvailable && mZipFile != NULL){ - unzCloseCurrentFile(mZipFile); - return; - } - - #if defined (WIN32) || defined (LINUX) || defined (IOS) - if (mFile != NULL) - fclose(mFile); - #else - if (mFile > 0) - sceIoClose(mFile); - #endif -} - - -int JFileSystem::ReadFile(void *buffer, int size) -{ - if (mZipAvailable && mZipFile != NULL) - { - return unzReadCurrentFile(mZipFile, buffer, size); - } - else - { - #if defined (WIN32) || defined (LINUX) || defined (IOS) - return fread(buffer, 1, size, mFile); - #else - return sceIoRead(mFile, buffer, size); - #endif - } -} - - -int JFileSystem::GetFileSize() -{ - return mFileSize; -} - - -void JFileSystem::SetResourceRoot(const string& resourceRoot) -{ -#ifdef IOS - NSString *pathUTF8 = [NSString stringWithUTF8String: resourceRoot.c_str()]; - NSString *fullpath = [[[NSBundle mainBundle] resourcePath] stringByAppendingPathComponent:pathUTF8]; - mResourceRoot = [fullpath cStringUsingEncoding:1]; - mResourceRoot += "/"; -#else - mResourceRoot = resourceRoot; -#endif -} - -string JFileSystem::GetResourceRoot() -{ - return mResourceRoot; -} - -string JFileSystem::GetResourceFile(string filename) -{ - string result = mResourceRoot; - return result.append(filename); +//------------------------------------------------------------------------------------- +// +// JGE++ is a hardware accelerated 2D game SDK for PSP/Windows. +// +// Licensed under the BSD license, see LICENSE in JGE root for details. +// +// Copyright (c) 2007 James Hui (a.k.a. Dr.Watson) +// +//------------------------------------------------------------------------------------- + +#ifdef WIN32 + #pragma warning(disable : 4786) +#endif + +#include "../include/JGE.h" +#include "../include/JFileSystem.h" +#include "../include/JLogger.h" +#include "tinyxml/tinyxml.h" +#include "unzip/unzip.h" + + +#include +#include +#include +#include + + +JZipCache::JZipCache(){} + +JZipCache::~JZipCache(){ + map::iterator it; + for (it = dir.begin(); it != dir.end(); it++){ + delete(it->second); + } + dir.clear(); +} + +void JFileSystem::preloadZip(string filename){ + map::iterator it = mZipCache.find(filename); + if (it != mZipCache.end()) return; + + JZipCache * cache = new JZipCache(); + mZipCache[filename] = cache; + + if (!mZipAvailable || !mZipFile) + { + AttachZipFile(filename); + if (!mZipAvailable || !mZipFile) return; + } + int err = unzGoToFirstFile (mZipFile); + while (err == UNZ_OK){ + unz_file_pos* filePos = new unz_file_pos(); + char filenameInzip[4096]; + if (unzGetCurrentFileInfo(mZipFile, NULL, filenameInzip, sizeof(filenameInzip), NULL, 0, NULL, 0) == UNZ_OK){ + unzGetFilePos(mZipFile, filePos); + string name = filenameInzip; + cache->dir[name] = filePos; + } + err = unzGoToNextFile(mZipFile); + } +} + +JFileSystem* JFileSystem::mInstance = NULL; + +JFileSystem* JFileSystem::GetInstance() +{ + if (mInstance == NULL) + { + mInstance = new JFileSystem(); + } + + return mInstance; +} + + +void JFileSystem::Destroy() +{ + if (mInstance) + { + delete mInstance; + mInstance = NULL; + } +} + + +JFileSystem::JFileSystem() +{ + mZipAvailable = false; +#if defined (WIN32) || defined (LINUX) || defined (IOS) + mFile = NULL; +#else + mFile = -1; +#endif + mPassword = NULL; + mZipFile = NULL; + mFileSize = 0; + +#ifdef RESPATH + SetResourceRoot(RESPATH"/"); +#else + SetResourceRoot("Res/"); // default root folder +#endif +} + + +JFileSystem::~JFileSystem() +{ + DetachZipFile(); + + map::iterator it; + for (it = mZipCache.begin(); it != mZipCache.end(); it++){ + delete(it->second); + } + mZipCache.clear(); +} + + +bool JFileSystem::AttachZipFile(const string &zipfile, char *password /* = NULL */) +{ + if (mZipAvailable && mZipFile != NULL) + { + if (mZipFileName != zipfile) + DetachZipFile(); // close the previous zip file + else + return true; + } + + mZipFileName = zipfile; + mPassword = password; + + mZipFile = unzOpen(mZipFileName.c_str()); + + if (mZipFile != NULL) + { + mZipAvailable = true; + return true; + } + + return false; +} + + +void JFileSystem::DetachZipFile() +{ + if (mZipAvailable && mZipFile != NULL) + { + JLOG("DetachZipFile"); + int error = unzCloseCurrentFile(mZipFile); + if (error < 0 ) + JLOG("error calling unzCloseCurrentFile"); + + error = unzClose(mZipFile); + if (error < 0) + JLOG("Error calling unzClose"); + } + + mZipFile = NULL; + mZipAvailable = false; +} + + +bool JFileSystem::OpenFile(const string &filename) +{ + string path = mResourceRoot + filename; + JLOG(path.c_str()); + + if (mZipAvailable && mZipFile != NULL) + { + JLOG("zip available, calling preload") + preloadZip(mZipFileName); + map::iterator it = mZipCache.find(mZipFileName); + if (it == mZipCache.end()) + { + JLOG("zip cache miss, detaching & calling open again"); + DetachZipFile(); + return OpenFile(filename); + } + JZipCache * zc = it->second; + map::iterator it2 = zc->dir.find(filename); + if (it2 == zc->dir.end()) + { + JLOG("directory miss, detaching & calling open again"); + DetachZipFile(); + return OpenFile(filename); + } + unzGoToFilePos(mZipFile,it2->second); + char filenameInzip[256]; + unz_file_info fileInfo; + + JLOG("calling unzGetCurrentFileInfo"); + if (unzGetCurrentFileInfo(mZipFile, &fileInfo, filenameInzip, sizeof(filenameInzip), NULL, 0, NULL, 0) == UNZ_OK) + mFileSize = fileInfo.uncompressed_size; + else + mFileSize = 0; + + return (unzOpenCurrentFilePassword(mZipFile, mPassword) == UNZ_OK); + } + else + { +#if defined (WIN32) || defined (LINUX)|| defined (IOS) + mFile = fopen(path.c_str(), "rb"); + if (mFile != NULL) + { + fseek(mFile, 0, SEEK_END); + mFileSize = ftell(mFile); + fseek(mFile, 0, SEEK_SET); + return true; + } +#else + JLOG("calling sceIOpen"); + mFile = sceIoOpen(path.c_str(), PSP_O_RDONLY, 0777); + if (mFile > 0) + { + JLOG("calling sceIoSeek"); + mFileSize = sceIoLseek(mFile, 0, PSP_SEEK_END); + sceIoLseek(mFile, 0, PSP_SEEK_SET); + return true; + } +#endif + } + + return false; +} + + +void JFileSystem::CloseFile() +{ + if (mZipAvailable && mZipFile != NULL){ + unzCloseCurrentFile(mZipFile); + return; + } + + #if defined (WIN32) || defined (LINUX) || defined (IOS) + if (mFile != NULL) + fclose(mFile); + #else + if (mFile > 0) + sceIoClose(mFile); + #endif +} + + +int JFileSystem::ReadFile(void *buffer, int size) +{ + if (mZipAvailable && mZipFile != NULL) + { + return unzReadCurrentFile(mZipFile, buffer, size); + } + else + { + #if defined (WIN32) || defined (LINUX) || defined (IOS) + return fread(buffer, 1, size, mFile); + #else + return sceIoRead(mFile, buffer, size); + #endif + } +} + + +int JFileSystem::GetFileSize() +{ + return mFileSize; +} + + +void JFileSystem::SetResourceRoot(const string& resourceRoot) +{ +#ifdef IOS + NSString *pathUTF8 = [NSString stringWithUTF8String: resourceRoot.c_str()]; + NSString *fullpath = [[[NSBundle mainBundle] resourcePath] stringByAppendingPathComponent:pathUTF8]; + mResourceRoot = [fullpath cStringUsingEncoding:1]; + mResourceRoot += "/"; +#else + mResourceRoot = resourceRoot; +#endif +} + +string JFileSystem::GetResourceRoot() +{ + return mResourceRoot; +} + +string JFileSystem::GetResourceFile(string filename) +{ + string result = mResourceRoot; + return result.append(filename); }