//------------------------------------------------------------------- // WavePool members. //------------------------------------------------------------------- void WavePool::load(char *f) { myFile myfile; int i; SDL_RWops *memSample = NULL; // read in header if (!myfile.open(f)) error("WavPool not found: ", f); myfile.read(&nsamples, sizeof(long)); // Just quit if empty library. if (nsamples == 0) { myfile.close(); return; } sample = new Sample[nsamples]; myfile.read(sample, nsamples * sizeof(Sample)); fseek(myfile.getFILE(), myfile.getbase(), SEEK_SET); memSample = SDL_RWFromMem(myfile.getMemory(), myfile.getsize()); // Load WAVES. for (i = 0; i < nsamples; i++) { #ifndef NO_SOUND memSample->seek(memSample, (long)sample[i].sample, RW_SEEK_SET); if((sample[i].sample = Mix_LoadWAV_RW(memSample, SDL_FALSE)) == NULL) error("Error loading sample. ", (char *)Mix_GetError()); #endif } SDL_RWclose(memSample); myfile.close(); }
int64_t Dx_FileRead_size(const char *filename) { SDL_RWops *rwops = Dx_File_OpenStream(filename); if (rwops != NULL) { int64_t size = rwops->size(rwops); rwops->close(rwops); return size; } return 0; }
static int graphics_AndroidTextureReader(void* buffer, size_t bytes, void* userdata) { SDL_RWops* ops = (SDL_RWops*)userdata; #ifndef NOTHREADEDSDLRW int i = ops->read(ops, buffer, 1, bytes); #else // workaround for http:// bugzilla.libsdl.org/show_bug.cgi?id=1422 int i = main_NoThreadedRWopsRead(ops, buffer, 1, bytes); #endif return i; }
void initLoad(){ /*ファイルオープン*/ ARCHIVE archive; openArchive(&archive,LOAD_ARCHIVE); /*背景取得*/ SDL_RWops* bgData = getGraphixFile(&archive,LOAD_BG); getSpriteFromOPS(&LoadBGSprite,bgData); bgData->close(bgData); //メモリ開放は忘れずに closeArchive(&archive); }
static void LoadArchivePics( PicManager *pm, const char *archive, const char *dirname) { char *buf = NULL; char path[CDOGS_PATH_MAX]; sprintf(path, "%s/%s", archive, dirname); tinydir_dir dir; if (tinydir_open(&dir, path) != 0) { LOG(LM_MAP, LL_DEBUG, "no pic dir(%s): %s", path, strerror(errno)); goto bail; } while (dir.has_next) { tinydir_file file; if (tinydir_readfile(&dir, &file) != 0) { LOG(LM_MAP, LL_WARN, "cannot read file: %s", strerror(errno)); break; } if (!file.is_reg) goto nextFile; long len; buf = ReadFileIntoBuf(file.path, "rb", &len); if (buf == NULL) goto nextFile; SDL_RWops *rwops = SDL_RWFromMem(buf, len); bool isPng = IMG_isPNG(rwops); if (isPng) { SDL_Surface *data = IMG_Load_RW(rwops, 0); if (data != NULL) { char nameBuf[CDOGS_FILENAME_MAX]; PathGetBasenameWithoutExtension(nameBuf, file.path); PicManagerAdd(&pm->customPics, &pm->customSprites, nameBuf, data); } } rwops->close(rwops); nextFile: CFREE(buf); buf = NULL; if (tinydir_next(&dir) != 0) { printf( "Could not go to next file in dir %s: %s\n", path, strerror(errno)); goto bail; } } bail: CFREE(buf); tinydir_close(&dir); }
static void LoadArchiveSounds( SoundDevice *device, const char *archive, const char *dirname) { char *buf = NULL; char path[CDOGS_PATH_MAX]; sprintf(path, "%s/%s", archive, dirname); tinydir_dir dir; if (tinydir_open(&dir, path) != 0) { LOG(LM_MAP, LL_DEBUG, "no sound dir(%s): %s", path, strerror(errno)); goto bail; } while (dir.has_next) { tinydir_file file; tinydir_readfile(&dir, &file); if (!file.is_reg) goto nextFile; long len; buf = ReadFileIntoBuf(file.path, "rb", &len); if (buf == NULL) goto nextFile; SDL_RWops *rwops = SDL_RWFromMem(buf, len); Mix_Chunk *data = Mix_LoadWAV_RW(rwops, 0); if (data != NULL) { char nameBuf[CDOGS_FILENAME_MAX]; strcpy(nameBuf, file.name); // Remove extension char *dot = strrchr(nameBuf, '.'); if (dot != NULL) { *dot = '\0'; } SoundAdd(&device->customSounds, nameBuf, data); } rwops->close(rwops); nextFile: CFREE(buf); buf = NULL; if (tinydir_next(&dir) != 0) { printf( "Could not go to next file in dir %s: %s\n", path, strerror(errno)); goto bail; } } bail: CFREE(buf); tinydir_close(&dir); }
void AddResource(ResourceManager resourceManager, std::string identifier, ResourceType resourceType) { ResourceHandle resourceHandle = CreateResourceHandle(resourceType); switch (resourceType) { case TEXTURE: { std::string strId = resourceManager->assetBaseDir + identifier; resourceHandle->textureRes->texture = IMG_LoadTexture(resourceManager->renderer, strId.c_str()); if(!resourceHandle->textureRes->texture) { LOGE("Unable to load resource: %s\n", strId.c_str()); FreeResourceHandle(resourceManager, resourceHandle); assert(0); } resourceHandle->textureRes->name = identifier; } break; case TMX_MAP: { std::string strId = resourceManager->assetBaseDir + identifier; resourceHandle->tmxMapResource->map.ParseFile(strId); break; } case ENTITY: { std::string strId = resourceManager->assetBaseDir + identifier; SDL_RWops * file = SDL_RWFromFile (strId.c_str(), "rb"); if (!file) { assert(0); } int fileSize = file->size(file); if (fileSize <= 0) { assert(0); } char* fileText = new char[fileSize + 1]; fileText[fileSize] = 0; file->read(file, fileText, 1, fileSize); file->close(file); std::string text(fileText, fileText+fileSize); delete [] fileText; resourceHandle->entityTemplateResource->xml.Parse(text.c_str()); break; } default: assert(0); } resourceManager->resources[identifier] = resourceHandle; }
extern warp_result_t save_file (const char *path, const char *data, size_t size) { SDL_RWops *io = SDL_RWFromFile(path, "w"); if (io == NULL) { return warp_failure("Cannot open the file: %s.", path); } const size_t saved_count = io->write(io, data, size, 1); io->close(io); if (saved_count != 1) { warp_log_e("Expected to save single object," " number of saved objects: %zu", saved_count); } return warp_success(); }
/* See documentation in header file. */ int ini_parse(const char* filename, int (*handler)(void*, const char*, const char*, const char*), void* user) { SDL_RWops* file = SDL_RWFromFile(filename, "r"); int error; if (!file) return -1; error = ini_parse_file(file, handler, user); file->close(file); return error; }
std::string LoadAllText(std::string file) { SDL_RWops *rw = SDL_RWFromFile(file.c_str(), "r"); auto size = rw->size(rw); char* script = new char[size + 1]; memset(script, 0, size + 1); rw->read(rw, script, sizeof(char), size); rw->close(rw); std::string result = script; delete[] script; return result; }
void Purity::LuaManager::doFile(const std::string& luaFileName) { SDL_RWops* file = SDL_RWFromFile(luaFileName.c_str(), "rb"); int fileSize = file->size(file); char* fileContents = new char[fileSize + 1]; file->read(file, fileContents, 1, fileSize); fileContents[fileSize] = '\0'; file->close(file); luaL_dostring(mLuaState, fileContents); delete [] fileContents; }
void Purity::Font::loadFont() { SDL_RWops* fontFile = SDL_RWFromFile(mFontFileName.c_str(), "rb"); if (fontFile == nullptr) { std::cerr << "Error loading font file" << ": " << SDL_GetError() << std::endl; } const auto fontFileSize = fontFile->size(fontFile); mFontData.reserve(fontFileSize); fontFile->read(fontFile, &mFontData[0], 1, fontFileSize); fontFile->close(fontFile); }
int SDLJBN_AddMappingsFromFile(const char *file) { int ret = 0; char *s = NULL; SDLJBN_Init(); SDL_RWops *rwops = SDL_RWFromFile(file, "r"); if (rwops == NULL) { err = "Cannot open file"; ret = -1; goto bail; } // Read file into memory const Sint64 fsize = rwops->size(rwops); if (fsize == -1) { err = "Cannot find file size"; ret = -1; goto bail; } s = SDL_malloc((size_t)fsize + 1); if (s == NULL) { err = "Out of memory"; ret = -1; goto bail; } if (SDL_RWread(rwops, s, (size_t)fsize, 1) == 0) { err = "Cannot read file"; ret = -1; goto bail; } s[fsize] = '\0'; ret = ReadMappingsString(s); bail: SDL_RWclose(rwops); SDL_free(s); return ret; }
SDL_RWops *SDL_RWFromBundle(Bundle *bundle, const char *filename) { SDL_RWops *rwops; RWOpsBundle * b = calloc(1, sizeof(RWOpsBundle)); b->handle = bundle->handle; for (int i = 0 ; i < bundle->n_files ; ++i) { if (strcmp(bundle->file[i].name, filename) == 0) { b->file = &bundle->file[i]; break; } } if (!b->file) { free(b); return NULL; } rwops = SDL_AllocRW(); if (rwops != NULL) { rwops->seek = bnd_seek; rwops->read = bnd_read; rwops->write = NULL; rwops->close = bnd_close; rwops->hidden.unknown.data1 = b; rwops->seek(rwops, 0, SEEK_SET); } else { free(b); } return rwops; }
extern warp_result_t read_file(const char *path, warp_array_t *out_buffer) { SDL_RWops *io = SDL_RWFromFile(path, "r"); if (io == NULL) { return warp_failure("Cannot open the file: %s.", path); } Sint64 size = io->size(io); char *content = malloc(sizeof (char) * (size + 1)); if (content == NULL) { io->close(io); return warp_failure("Cannot allocate file buffer for file: %s", path); } if (io->read(io, content, size, 1) == 0) { free(content); io->close(io); return warp_failure("Error while reading file: %s.", path); } io->close(io); content[size] = '\0'; *out_buffer = warp_array_create_from_buffer(content, sizeof (char), size + 1, NULL); free(content); return warp_success(); }
void Map::ParseFile(const string &fileName) { file_name = fileName; int lastSlash = fileName.find_last_of("/"); // Get the directory of the file using substring. if (lastSlash > 0) { file_path = fileName.substr(0, lastSlash + 1); } else { file_path = ""; } char* fileText; int fileSize; // Open the file for reading. #ifdef USE_SDL2_LOAD SDL_RWops * file = SDL_RWFromFile (fileName.c_str(), "rb"); #else FILE *file = fopen(fileName.c_str(), "rb"); #endif // Check if the file could not be opened. if (!file) { has_error = true; error_code = TMX_COULDNT_OPEN; error_text = "Could not open the file."; return; } // Find out the file size. #ifdef USE_SDL2_LOAD fileSize = file->size(file); #else fseek(file, 0, SEEK_END); fileSize = ftell(file); fseek(file, 0, SEEK_SET); #endif // Check if the file size is valid. if (fileSize <= 0) { has_error = true; error_code = TMX_INVALID_FILE_SIZE; error_text = "The size of the file is invalid."; return; } // Allocate memory for the file and read it into the memory. fileText = new char[fileSize + 1]; fileText[fileSize] = 0; #ifdef USE_SDL2_LOAD file->read(file, fileText, 1, fileSize); #else fread(fileText, 1, fileSize, file); #endif #ifdef USE_SDL2_LOAD file->close(file); #else fclose(file); #endif // Copy the contents into a C++ string and delete it from memory. std::string text(fileText, fileText+fileSize); delete [] fileText; ParseText(text); }
static void PicManagerLoadDirImpl( PicManager *pm, const char *path, const char *prefix) { tinydir_dir dir; if (tinydir_open(&dir, path) == -1) { perror("Cannot open image dir"); goto bail; } for (; dir.has_next; tinydir_next(&dir)) { tinydir_file file; if (tinydir_readfile(&dir, &file) == -1) { perror("Cannot read image file"); goto bail; } if (file.is_reg) { SDL_RWops *rwops = SDL_RWFromFile(file.path, "rb"); const bool isPng = IMG_isPNG(rwops); if (isPng) { SDL_Surface *data = IMG_Load_RW(rwops, 0); if (!data) { perror("Cannot load image"); fprintf(stderr, "IMG_Load: %s\n", IMG_GetError()); } else { char buf[CDOGS_PATH_MAX]; if (prefix) { char buf1[CDOGS_PATH_MAX]; sprintf(buf1, "%s/%s", prefix, file.name); PathGetWithoutExtension(buf, buf1); } else { PathGetBasenameWithoutExtension(buf, file.name); } PicManagerAdd(&pm->pics, &pm->sprites, buf, data); } } rwops->close(rwops); } else if (file.is_dir && file.name[0] != '.') { if (prefix) { char buf[CDOGS_PATH_MAX]; sprintf(buf, "%s/%s", prefix, file.name); PicManagerLoadDirImpl(pm, file.path, buf); } else { PicManagerLoadDirImpl(pm, file.path, file.name); } } } bail: tinydir_close(&dir); }
int main(int argc, char *argv[]) { SDL_RWops *rwops = NULL; char test_buf[30]; /* Enable standard application logging */ SDL_LogSetPriority(SDL_LOG_CATEGORY_APPLICATION, SDL_LOG_PRIORITY_INFO); cleanup(); /* test 1 : basic argument test: all those calls to SDL_RWFromFile should fail */ rwops = SDL_RWFromFile(NULL, NULL); if (rwops) RWOP_ERR_QUIT(rwops); rwops = SDL_RWFromFile(NULL, "ab+"); if (rwops) RWOP_ERR_QUIT(rwops); rwops = SDL_RWFromFile(NULL, "sldfkjsldkfj"); if (rwops) RWOP_ERR_QUIT(rwops); rwops = SDL_RWFromFile("something", ""); if (rwops) RWOP_ERR_QUIT(rwops); rwops = SDL_RWFromFile("something", NULL); if (rwops) RWOP_ERR_QUIT(rwops); SDL_Log("test1 OK\n"); /* test 2 : check that inexistent file is not successfully opened/created when required */ /* modes : r, r+ imply that file MUST exist modes : a, a+, w, w+ checks that it succeeds (file may not exists) */ rwops = SDL_RWFromFile(FBASENAME2, "rb"); /* this file doesn't exist that call must fail */ if (rwops) RWOP_ERR_QUIT(rwops); rwops = SDL_RWFromFile(FBASENAME2, "rb+"); /* this file doesn't exist that call must fail */ if (rwops) RWOP_ERR_QUIT(rwops); rwops = SDL_RWFromFile(FBASENAME2, "wb"); if (!rwops) RWOP_ERR_QUIT(rwops); rwops->close(rwops); unlink(FBASENAME2); rwops = SDL_RWFromFile(FBASENAME2, "wb+"); if (!rwops) RWOP_ERR_QUIT(rwops); rwops->close(rwops); unlink(FBASENAME2); rwops = SDL_RWFromFile(FBASENAME2, "ab"); if (!rwops) RWOP_ERR_QUIT(rwops); rwops->close(rwops); unlink(FBASENAME2); rwops = SDL_RWFromFile(FBASENAME2, "ab+"); if (!rwops) RWOP_ERR_QUIT(rwops); rwops->close(rwops); unlink(FBASENAME2); SDL_Log("test2 OK\n"); /* test 3 : creation, writing , reading, seeking, test : w mode, r mode, w+ mode */ rwops = SDL_RWFromFile(FBASENAME1, "wb"); /* write only */ if (!rwops) RWOP_ERR_QUIT(rwops); if (1 != rwops->write(rwops, "1234567890", 10, 1)) RWOP_ERR_QUIT(rwops); if (10 != rwops->write(rwops, "1234567890", 1, 10)) RWOP_ERR_QUIT(rwops); if (7 != rwops->write(rwops, "1234567", 1, 7)) RWOP_ERR_QUIT(rwops); if (0 != rwops->seek(rwops, 0L, RW_SEEK_SET)) RWOP_ERR_QUIT(rwops); if (0 != rwops->read(rwops, test_buf, 1, 1)) RWOP_ERR_QUIT(rwops); /* we are in write only mode */ rwops->close(rwops); rwops = SDL_RWFromFile(FBASENAME1, "rb"); /* read mode, file must exists */ if (!rwops) RWOP_ERR_QUIT(rwops); if (0 != rwops->seek(rwops, 0L, RW_SEEK_SET)) RWOP_ERR_QUIT(rwops); if (20 != rwops->seek(rwops, -7, RW_SEEK_END)) RWOP_ERR_QUIT(rwops); if (7 != rwops->read(rwops, test_buf, 1, 7)) RWOP_ERR_QUIT(rwops); if (SDL_memcmp(test_buf, "1234567", 7)) RWOP_ERR_QUIT(rwops); if (0 != rwops->read(rwops, test_buf, 1, 1)) RWOP_ERR_QUIT(rwops); if (0 != rwops->read(rwops, test_buf, 10, 100)) RWOP_ERR_QUIT(rwops); if (0 != rwops->seek(rwops, -27, RW_SEEK_CUR)) RWOP_ERR_QUIT(rwops); if (2 != rwops->read(rwops, test_buf, 10, 3)) RWOP_ERR_QUIT(rwops); if (SDL_memcmp(test_buf, "12345678901234567890", 20)) RWOP_ERR_QUIT(rwops); if (0 != rwops->write(rwops, test_buf, 1, 1)) RWOP_ERR_QUIT(rwops); /* readonly mode */ rwops->close(rwops); /* test 3: same with w+ mode */ rwops = SDL_RWFromFile(FBASENAME1, "wb+"); /* write + read + truncation */ if (!rwops) RWOP_ERR_QUIT(rwops); if (1 != rwops->write(rwops, "1234567890", 10, 1)) RWOP_ERR_QUIT(rwops); if (10 != rwops->write(rwops, "1234567890", 1, 10)) RWOP_ERR_QUIT(rwops); if (7 != rwops->write(rwops, "1234567", 1, 7)) RWOP_ERR_QUIT(rwops); if (0 != rwops->seek(rwops, 0L, RW_SEEK_SET)) RWOP_ERR_QUIT(rwops); if (1 != rwops->read(rwops, test_buf, 1, 1)) RWOP_ERR_QUIT(rwops); /* we are in read/write mode */ if (0 != rwops->seek(rwops, 0L, RW_SEEK_SET)) RWOP_ERR_QUIT(rwops); if (20 != rwops->seek(rwops, -7, RW_SEEK_END)) RWOP_ERR_QUIT(rwops); if (7 != rwops->read(rwops, test_buf, 1, 7)) RWOP_ERR_QUIT(rwops); if (SDL_memcmp(test_buf, "1234567", 7)) RWOP_ERR_QUIT(rwops); if (0 != rwops->read(rwops, test_buf, 1, 1)) RWOP_ERR_QUIT(rwops); if (0 != rwops->read(rwops, test_buf, 10, 100)) RWOP_ERR_QUIT(rwops); if (0 != rwops->seek(rwops, -27, RW_SEEK_CUR)) RWOP_ERR_QUIT(rwops); if (2 != rwops->read(rwops, test_buf, 10, 3)) RWOP_ERR_QUIT(rwops); if (SDL_memcmp(test_buf, "12345678901234567890", 20)) RWOP_ERR_QUIT(rwops); rwops->close(rwops); SDL_Log("test3 OK\n"); /* test 4: same in r+ mode */ rwops = SDL_RWFromFile(FBASENAME1, "rb+"); /* write + read + file must exists, no truncation */ if (!rwops) RWOP_ERR_QUIT(rwops); if (1 != rwops->write(rwops, "1234567890", 10, 1)) RWOP_ERR_QUIT(rwops); if (10 != rwops->write(rwops, "1234567890", 1, 10)) RWOP_ERR_QUIT(rwops); if (7 != rwops->write(rwops, "1234567", 1, 7)) RWOP_ERR_QUIT(rwops); if (0 != rwops->seek(rwops, 0L, RW_SEEK_SET)) RWOP_ERR_QUIT(rwops); if (1 != rwops->read(rwops, test_buf, 1, 1)) RWOP_ERR_QUIT(rwops); /* we are in read/write mode */ if (0 != rwops->seek(rwops, 0L, RW_SEEK_SET)) RWOP_ERR_QUIT(rwops); if (20 != rwops->seek(rwops, -7, RW_SEEK_END)) RWOP_ERR_QUIT(rwops); if (7 != rwops->read(rwops, test_buf, 1, 7)) RWOP_ERR_QUIT(rwops); if (SDL_memcmp(test_buf, "1234567", 7)) RWOP_ERR_QUIT(rwops); if (0 != rwops->read(rwops, test_buf, 1, 1)) RWOP_ERR_QUIT(rwops); if (0 != rwops->read(rwops, test_buf, 10, 100)) RWOP_ERR_QUIT(rwops); if (0 != rwops->seek(rwops, -27, RW_SEEK_CUR)) RWOP_ERR_QUIT(rwops); if (2 != rwops->read(rwops, test_buf, 10, 3)) RWOP_ERR_QUIT(rwops); if (SDL_memcmp(test_buf, "12345678901234567890", 20)) RWOP_ERR_QUIT(rwops); rwops->close(rwops); SDL_Log("test4 OK\n"); /* test5 : append mode */ rwops = SDL_RWFromFile(FBASENAME1, "ab+"); /* write + read + append */ if (!rwops) RWOP_ERR_QUIT(rwops); if (1 != rwops->write(rwops, "1234567890", 10, 1)) RWOP_ERR_QUIT(rwops); if (10 != rwops->write(rwops, "1234567890", 1, 10)) RWOP_ERR_QUIT(rwops); if (7 != rwops->write(rwops, "1234567", 1, 7)) RWOP_ERR_QUIT(rwops); if (0 != rwops->seek(rwops, 0L, RW_SEEK_SET)) RWOP_ERR_QUIT(rwops); if (1 != rwops->read(rwops, test_buf, 1, 1)) RWOP_ERR_QUIT(rwops); if (0 != rwops->seek(rwops, 0L, RW_SEEK_SET)) RWOP_ERR_QUIT(rwops); if (20 + 27 != rwops->seek(rwops, -7, RW_SEEK_END)) RWOP_ERR_QUIT(rwops); if (7 != rwops->read(rwops, test_buf, 1, 7)) RWOP_ERR_QUIT(rwops); if (SDL_memcmp(test_buf, "1234567", 7)) RWOP_ERR_QUIT(rwops); if (0 != rwops->read(rwops, test_buf, 1, 1)) RWOP_ERR_QUIT(rwops); if (0 != rwops->read(rwops, test_buf, 10, 100)) RWOP_ERR_QUIT(rwops); if (27 != rwops->seek(rwops, -27, RW_SEEK_CUR)) RWOP_ERR_QUIT(rwops); if (0 != rwops->seek(rwops, 0L, RW_SEEK_SET)) RWOP_ERR_QUIT(rwops); if (3 != rwops->read(rwops, test_buf, 10, 3)) RWOP_ERR_QUIT(rwops); if (SDL_memcmp(test_buf, "123456789012345678901234567123", 30)) RWOP_ERR_QUIT(rwops); rwops->close(rwops); SDL_Log("test5 OK\n"); cleanup(); return 0; /* all ok */ }
int main(int argc, char ** argv) { #ifdef WIN32 SetUnhandledExceptionFilter( UnhandledExceptionProc ); #endif for(int i = 1; i < argc;) { int ret = argsHandler(argc, argv, i); if(!ret) { // ignore unknown arg i++; } } if ( cg_printVersion ) { printf( "%s\n", PACKAGE_STRING ); return 0; } if ( cg_printHelp ) { printHelp( argv[0] ); return 0; } std::unique_ptr<SplashWindow> splashWindow; try{ // start recording backtrace spades::reflection::Backtrace::StartBacktrace(); SPADES_MARK_FUNCTION(); // show splash window // NOTE: splash window uses image loader, which assumes backtrace is already initialized. splashWindow.reset(new SplashWindow()); auto showSplashWindowTime = SDL_GetTicks(); auto pumpEvents = [&splashWindow] { splashWindow->PumpEvents(); }; // initialize threads spades::Thread::InitThreadSystem(); spades::DispatchQueue::GetThreadQueue()->MarkSDLVideoThread(); SPLog("Package: " PACKAGE_STRING); // setup user-specific default resource directories #ifdef WIN32 static wchar_t buf[4096]; GetModuleFileNameW(NULL, buf, 4096); std::wstring appdir = buf; appdir = appdir.substr(0, appdir.find_last_of(L'\\')+1); if(SUCCEEDED(SHGetFolderPathW(NULL, CSIDL_APPDATA, NULL, 0, buf))){ std::wstring datadir = buf; datadir += L"\\OpenSpades\\Resources"; spades::FileManager::AddFileSystem(new spades::DirectoryFileSystem(Utf8FromWString(datadir.c_str()), true)); } spades::FileManager::AddFileSystem(new spades::DirectoryFileSystem(Utf8FromWString((appdir + L"Resources").c_str()), false)); //fltk has a console window on windows (can disable while building, maybe use a builtin console for a later release?) HWND hCon = GetConsoleWindow(); if( NULL != hCon ) { setIcon( hCon ); } #elif defined(__APPLE__) std::string home = getenv("HOME"); spades::FileManager::AddFileSystem (new spades::DirectoryFileSystem("./Resources", false)); // OS X application is made of Bundle, which contains its own Resources directory. { char *baseDir = SDL_GetBasePath(); if(baseDir) { spades::FileManager::AddFileSystem (new spades::DirectoryFileSystem(baseDir, false)); SDL_free(baseDir); } } spades::FileManager::AddFileSystem (new spades::DirectoryFileSystem(home+"/Library/Application Support/OpenSpades/Resources", true)); #else std::string home = getenv("HOME"); spades::FileManager::AddFileSystem (new spades::DirectoryFileSystem("./Resources", false)); spades::FileManager::AddFileSystem(new spades::DirectoryFileSystem(CMAKE_INSTALL_PREFIX "/" OPENSPADES_INSTALL_RESOURCES, false)); std::string xdg_data_home = home+"/.local/share"; if (getenv("XDG_DATA_HOME") == NULL) { SPLog("XDG_DATA_HOME not defined. Assuming that XDG_DATA_HOME is ~/.local/share"); } else { std::string xdg_data_home = getenv("XDG_DATA_HOME"); SPLog("XDG_DATA_HOME is %s", xdg_data_home.c_str()); } struct stat info; if ( stat((xdg_data_home+"/openspades").c_str(), &info ) != 0 ) { if ( stat((home+"/.openspades").c_str(), &info ) != 0) { } else if( info.st_mode & S_IFDIR ) { SPLog("Openspades directory in XDG_DATA_HOME not found, though old directory exists. Trying to resolve compatibility problem."); if (rename( (home+"/.openspades").c_str() , (xdg_data_home+"/openspades").c_str() ) != 0) { SPLog("Failed to move old directory to new."); } else { SPLog("Successfully moved old directory."); if (mkdir((home+"/.openspades").c_str(), S_IRWXU | S_IRWXG | S_IROTH | S_IXOTH) == 0) { SDL_RWops *io = SDL_RWFromFile((home+"/.openspades/CONTENT_MOVED_TO_NEW_DIR").c_str(), "wb"); if (io != NULL) { const char* text = ("Content of this directory moved to "+xdg_data_home+"/openspades").c_str(); io->write(io, text, strlen(text), 1); io->close(io); } } } } } spades::FileManager::AddFileSystem (new spades::DirectoryFileSystem(xdg_data_home+"/openspades/Resources", true)); #endif // start log output to SystemMessages.log try{ spades::StartLog(); }catch(const std::exception& ex){ SDL_InitSubSystem(SDL_INIT_VIDEO); auto msg = spades::Format("Failed to start recording log because of the following error:\n{0}\n\n" "OpenSpades will continue to run, but any critical events are not logged.", ex.what()); if(SDL_ShowSimpleMessageBox(SDL_MESSAGEBOX_WARNING, "OpenSpades Log System Failure", msg.c_str(), splashWindow->GetWindow())) { // showing dialog failed. } } SPLog("Log Started."); // load preferences. spades::Settings::GetInstance()->Load(); pumpEvents(); // dump CPU info (for debugging?) { spades::CpuID cpuid; SPLog("---- CPU Information ----"); SPLog("Vendor ID: %s", cpuid.GetVendorId().c_str()); SPLog("Brand ID: %s", cpuid.GetBrand().c_str()); SPLog("Supports MMX: %s", cpuid.Supports(spades::CpuFeature::MMX)?"YES":"NO"); SPLog("Supports SSE: %s", cpuid.Supports(spades::CpuFeature::SSE)?"YES":"NO"); SPLog("Supports SSE2: %s", cpuid.Supports(spades::CpuFeature::SSE2)?"YES":"NO"); SPLog("Supports SSE3: %s", cpuid.Supports(spades::CpuFeature::SSE3)?"YES":"NO"); SPLog("Supports SSSE3: %s", cpuid.Supports(spades::CpuFeature::SSSE3)?"YES":"NO"); SPLog("Supports FMA: %s", cpuid.Supports(spades::CpuFeature::FMA)?"YES":"NO"); SPLog("Supports AVX: %s", cpuid.Supports(spades::CpuFeature::AVX)?"YES":"NO"); SPLog("Supports AVX2: %s", cpuid.Supports(spades::CpuFeature::AVX2)?"YES":"NO"); SPLog("Supports AVX512F: %s", cpuid.Supports(spades::CpuFeature::AVX512F)?"YES":"NO"); SPLog("Supports AVX512CD: %s", cpuid.Supports(spades::CpuFeature::AVX512CD)?"YES":"NO"); SPLog("Supports AVX512ER: %s", cpuid.Supports(spades::CpuFeature::AVX512ER)?"YES":"NO"); SPLog("Supports AVX512PF: %s", cpuid.Supports(spades::CpuFeature::AVX512PF)?"YES":"NO"); SPLog("Simultaneous Multithreading: %s", cpuid.Supports(spades::CpuFeature::SimultaneousMT)?"YES":"NO"); SPLog("Misc:"); SPLog("%s", cpuid.GetMiscInfo().c_str()); SPLog("-------------------------"); } // register resource directory specified by Makefile (or something) #if defined(RESDIR_DEFINED) spades::FileManager::AddFileSystem(new spades::DirectoryFileSystem(RESDIR, false)); #endif // search current file system for .pak files { std::vector<spades::IFileSystem*> fss; std::vector<spades::IFileSystem*> fssImportant; std::vector<std::string> files = spades::FileManager::EnumFiles(""); struct Comparator { static int GetPakId(const std::string& str) { if(str.size() >= 4 && str[0] == 'p' && str[1] == 'a' && str[2] == 'k' && (str[3] >= '0' && str[3] <= '9')){ return atoi(str.c_str() + 3); }else{ return 32767; } } static bool Compare(const std::string& a, const std::string& b) { int pa = GetPakId(a); int pb = GetPakId(b); if(pa == pb){ return a < b; }else{ return pa < pb; } } }; std::sort(files.begin(), files.end(), Comparator::Compare); for(size_t i = 0; i < files.size(); i++){ std::string name = files[i]; // check extension if(name.size() < 4 || name.rfind(".pak") != name.size() - 4){ continue; } if(spades::FileManager::FileExists(name.c_str())) { spades::IStream *stream = spades::FileManager::OpenForReading(name.c_str()); spades::ZipFileSystem *fs = new spades::ZipFileSystem(stream); if(name[0] == '_' && false) { // last resort for #198 SPLog("Pak Registered: %s (marked as 'important')\n", name.c_str()); fssImportant.push_back(fs); }else{ SPLog("Pak Registered: %s\n", name.c_str()); fss.push_back(fs); } } } for(size_t i = fss.size(); i > 0; i--){ spades::FileManager::AppendFileSystem(fss[i - 1]); } for(size_t i = 0; i < fssImportant.size(); i++){ spades::FileManager::PrependFileSystem(fssImportant[i]); } } pumpEvents(); // initialize localization system SPLog("Initializing localization system"); spades::LoadCurrentLocale(); _Tr("Main", "Localization System Loaded"); pumpEvents(); // parse args // initialize AngelScript SPLog("Initializing script engine"); spades::ScriptManager::GetInstance(); pumpEvents(); ThreadQuantumSetter quantumSetter; (void)quantumSetter; // suppress "unused variable" warning SDL_InitSubSystem(SDL_INIT_VIDEO); // we want to show splash window at least for some time... pumpEvents(); auto ticks = SDL_GetTicks(); if(ticks < showSplashWindowTime + 1500) { SDL_Delay(showSplashWindowTime + 1500 - ticks); } pumpEvents(); // everything is now ready! if( !cg_autoConnect ) { if(!((int)cl_showStartupWindow != 0 || splashWindow->IsStartupScreenRequested())) { splashWindow.reset(); SPLog("Starting main screen"); spades::StartMainScreen(); }else{ splashWindow.reset(); SPLog("Starting startup window"); ::spades::gui::StartupScreen::Run(); } } else { splashWindow.reset(); spades::ServerAddress host(cg_lastQuickConnectHost.CString(), (int)cg_protocolVersion == 3 ? spades::ProtocolVersion::v075 : spades::ProtocolVersion::v076 ); spades::StartClient(host, cg_playerName); } spades::Settings::GetInstance()->Flush(); }catch(const ExitRequestException&){ // user changed his mind. }catch(const std::exception& ex) { try { splashWindow.reset(nullptr); }catch(...){ } std::string msg = ex.what(); msg = _Tr("Main", "A serious error caused OpenSpades to stop working:\n\n{0}\n\nSee SystemMessages.log for more details.", msg); SPLog("[!] Terminating due to the fatal error: %s", ex.what()); SDL_InitSubSystem(SDL_INIT_VIDEO); if(SDL_ShowSimpleMessageBox(SDL_MESSAGEBOX_ERROR, _Tr("Main", "OpenSpades Fatal Error").c_str(), msg.c_str(), nullptr)) { // showing dialog failed. // TODO: do appropriate action } } return 0; }
int SDL_main(int argc, char** argv) { #else #ifdef WINDOWS int CALLBACK WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow) { #else int main(int argc, char** argv) { #endif #endif thread_MarkAsMainThread(); #if defined(ANDROID) || defined(__ANDROID__) printinfo("Blitwizard %s starting", VERSION); #endif // set signal handlers: signalhandling_Init(); // set path to blitwizard binary: #ifdef UNIX if (argc > 0) { binpath = file_GetAbsolutePathFromRelativePath(argv[0]); } #endif // test crash handling: //*((int*)5) = 2; // evaluate command line arguments: const char* script = "game.lua"; int scriptargfound = 0; int option_changedir = 0; char* option_templatepath = NULL; int nextoptionistemplatepath = 0; int nextoptionisscriptarg = 0; int gcframecount = 0; #ifdef WINDOWS // obtain command line arguments a special way on windows: int argc = __argc; char** argv = __argv; #endif // we want to store the script arguments so we can pass them to lua: char** scriptargs = malloc(sizeof(char*) * MAXSCRIPTARGS); if (!scriptargs) { printerror("Error: failed to allocate script args space"); return 1; } int scriptargcount = 0; // parse command line arguments: int i = 1; while (i < argc) { if (!scriptargfound) { // pre-scriptname arguments // process template path option parameter: if (nextoptionistemplatepath) { nextoptionistemplatepath = 0; if (option_templatepath) { free(option_templatepath); } option_templatepath = strdup(argv[i]); if (!option_templatepath) { printerror("Error: failed to strdup() template " "path argument"); main_Quit(1); return 1; } file_MakeSlashesNative(option_templatepath); i++; continue; } // various options: if ((argv[i][0] == '-' || strcasecmp(argv[i],"/?") == 0) && !nextoptionisscriptarg) { if (strcasecmp(argv[i], "--") == 0) { // this enforces the next arg to be the script name: nextoptionisscriptarg = 1; i++; continue; } if (strcasecmp(argv[i],"--help") == 0 || strcasecmp(argv[i], "-help") == 0 || strcasecmp(argv[i], "-?") == 0 || strcasecmp(argv[i],"/?") == 0 || strcasecmp(argv[i],"-h") == 0) { printf("blitwizard %s (C) 2011-2013 Jonas Thiem et al\n", VERSION); printf("Usage:\n blitwizard [blitwizard options] " "[script name] [script options]\n\n"); printf("The script name should be a .lua file containing\n" "Lua source code for use with blitwizard.\n\n"); printf("The script options (optional) are passed through\n" "to the script.\n\n"); printf("Supported blitwizard options:\n"); printf(" -changedir Change working directory to " "the\n" " folder of the script\n"); printf(" -help Show this help text and quit\n"); printf(" -templatepath [path] Check another place for " "templates\n" " (not the default " "\"templates/\")\n"); printf(" -version Show extended version info and quit\n"); return 0; } if (strcasecmp(argv[i], "-changedir") == 0) { option_changedir = 1; i++; continue; } if (strcasecmp(argv[i], "-templatepath") == 0) { nextoptionistemplatepath = 1; i++; continue; } if (strcmp(argv[i], "-v") == 0 || strcasecmp(argv[i], "-version") == 0 || strcasecmp(argv[i], "--version") == 0) { printf("blitwizard %s (C) 2011-2013 Jonas Thiem et al\n",VERSION); printf("\nSupported features of this build:\n"); #ifdef USE_SDL_AUDIO printf(" Audio device: SDL 2\n"); #else #ifdef USE_AUDIO #ifdef WINDOWS printf(" Audio device: waveOut\n"); #else printf(" Audio device: only virtual (not audible)\n"); #endif #else printf(" Audio device: no\n"); printf(" Playback support: none, audio disabled\n"); printf(" Resampling support: none, audio disabled\n"); #endif #endif #if (defined(USE_SDL_AUDIO) || defined(USE_AUDIO)) printf(" Playback support: Ogg (libogg)%s%s\n", #if defined(USE_FLAC_AUDIO) ", FLAC (libFLAC)" #else "" #endif , #if defined(USE_FFMPEG_AUDIO) #ifndef USE_FLAC_AUDIO ", FLAC (FFmpeg),\n mp3 (FFmpeg), WAVE (FFmpeg), mp4 (FFmpeg),\n many more.. (FFmpeg)\n (Please note FFmpeg can fail to load at runtime,\n resulting in FFmpeg playback support not working)" #else ",\n mp3 (FFmpeg), WAVE (FFmpeg), mp4 (FFmpeg),\n many more.. (FFmpeg)\n (Please note FFmpeg can fail to load at runtime,\n resulting in FFmpeg playback support not working)" #endif #else "" #endif ); #if defined(USE_SPEEX_RESAMPLING) printf(" Resampling: libspeex\n"); #else printf(" Resampling: none (non-48kHz audio will sound wrong!)\n"); #endif #endif #ifdef USE_GRAPHICS #ifdef USE_SDL_GRAPHICS #ifdef USE_OGRE_GRAPHICS printf(" Graphics device: SDL 2, Ogre\n"); printf(" 2d graphics support: SDL 2, Ogre\n"); printf(" 3d graphics support: Ogre\n"); #else printf(" Graphics device: SDL 2\n"); printf(" 2d graphics support: SDL 2\n"); printf(" 3d graphics support: none\n"); #endif #else printf(" Graphics device: only virtual (not visible)\n"); printf(" 2d graphics support: virtual\n"); printf(" 3d graphics support: none\n"); #endif #else printf(" Graphics device: none\n"); printf(" 2d graphics support: none, graphics disabled\n"); printf(" 3d graphics support: none, graphics disabled\n"); #endif #if defined(USE_PHYSICS2D) || defined(USE_PHYSICS3D) printf(" Physics: yes\n"); #else printf(" Physics: no\n"); #endif #if defined(USE_PHYSICS2D) printf(" 2d physics: Box2D\n"); #else printf(" 2d physics: none\n"); #endif #if defined(USE_PHYSICS3D) printf(" 3d physics: bullet\n"); #else printf(" 3d physics: none\n"); #endif #if defined(USE_PHYSFS) printf(" .zip archive resource loading: yes\n"); #else printf(" .zip archive resource loading: no\n"); #endif printf("\nVarious build options:\n"); printf(" SYSTEM_TEMPLATE_PATH:\n %s\n", SYSTEM_TEMPLATE_PATH); #if defined(USE_LIB_FLAGS) printf(" FINAL_USE_LIB_FLAGS:\n %s\n", USE_LIB_FLAGS); #endif printf("\nCheck out http://www.blitwizard.de/" " for info about blitwizard.\n"); fflush(stdout); exit(0); } printwarning("Warning: Unknown Blitwizard option: %s", argv[i]); } else { scriptargfound = 1; script = argv[i]; } } else { // post-scriptname arguments -> store them for Lua if (scriptargcount < MAXSCRIPTARGS) { scriptargs[scriptargcount] = strdup(argv[i]); scriptargcount++; } } i++; } #ifdef USE_AUDIO // This needs to be done at some point before we actually // initialise audio so that the mixer is ready for use then audiomixer_Init(); #endif // check the provided path: char outofmem[] = "Out of memory"; char* error; char* filenamebuf = NULL; #if defined(ANDROID) || defined(__ANDROID__) printinfo("Blitwizard startup: locating lua start script..."); #endif // if no template path was provided, default to "templates/" if (!option_templatepath) { option_templatepath = strdup("templates/"); if (!option_templatepath) { printerror("Error: failed to allocate initial template path"); main_Quit(1); return 1; } file_MakeSlashesNative(option_templatepath); } // load internal resources appended to this binary, // so we can load the game.lua from it if there is any inside: #ifdef WINDOWS // windows // try encrypted first: if (!resources_LoadZipFromOwnExecutable(NULL, 1)) { // ... ok, then attempt unencrypted: resources_LoadZipFromOwnExecutable(NULL, 0); } #else #ifndef ANDROID // unix systems // encrypted first: if (!resources_LoadZipFromOwnExecutable(argv[0], 1)) { // ... ok, then attempt unencrypted: resources_LoadZipFromOwnExecutable(argv[0], 0); } #endif #endif // check if provided script path is a folder: if (file_IsDirectory(script)) { // make sure it isn't inside a resource file as a proper file: if (!resources_LocateResource(script, NULL)) { // it isn't, so we can safely assume it is a folder. // -> append "game.lua" to the path if (filenamebuf) { free(filenamebuf); } filenamebuf = file_AddComponentToPath(script, "game.lua"); if (!filenamebuf) { printerror("Error: failed to add component to script path"); main_Quit(1); return 1; } script = filenamebuf; } } // check if script file is internal resource or disk file int scriptdiskfile = 0; struct resourcelocation s; if (!resources_LocateResource(script, &s)) { printerror("Error: cannot locate script file \"%s\"", script); main_Quit(1); return 1; } else { if (s.type == LOCATION_TYPE_ZIP) { scriptdiskfile = 0; } else{ scriptdiskfile = 1; } } // compose game.lua path variable (for os.gameluapath()) if (scriptdiskfile) { gameluapath = file_GetAbsolutePathFromRelativePath(script); } else { gameluapath = strdup(script); } if (!gameluapath) { // string allocation failed printerror("Error: failed to allocate script path (gameluapath)"); main_Quit(1); return 1; } else { if (gameluapath) { file_MakeSlashesCrossplatform(gameluapath); } } // check if we want to change directory to the provided script path: if (option_changedir) { char* p = file_GetAbsoluteDirectoryPathFromFilePath(script); if (!p) { printerror("Error: NULL returned for absolute directory"); main_Quit(1); return 1; } char* newfilenamebuf = file_GetFileNameFromFilePath(script); if (!newfilenamebuf) { free(p); printerror("Error: NULL returned for file name"); main_Quit(1); return 1; } if (filenamebuf) { free(filenamebuf); } filenamebuf = newfilenamebuf; if (!file_Cwd(p)) { free(filenamebuf); printerror("Error: Cannot cd to \"%s\"", p); free(p); main_Quit(1); return 1; } free(p); script = filenamebuf; } /*#if defined(ANDROID) || defined(__ANDROID__) printinfo("Blitwizard startup: Preparing graphics framework..."); #endif // initialise graphics #ifdef USE_GRAPHICS if (!graphics_Init(&error)) { printerror("Error: Failed to initialise graphics: %s",error); free(error); fatalscripterror(); main_Quit(1); return 1; } sdlinitialised = 1; #endif*/ #if defined(ANDROID) || defined(__ANDROID__) printinfo("Blitwizard startup: Initialising physics..."); #endif #ifdef USE_PHYSICS2D // initialise physics physics2ddefaultworld = physics_createWorld(0); if (!physics2ddefaultworld) { printerror("Error: Failed to initialise Box2D physics"); fatalscripterror(); main_Quit(1); return 1; } luacfuncs_object_initialisePhysicsCallbacks(); #endif #if defined(ANDROID) || defined(__ANDROID__) printinfo("Blitwizard startup: Reading templates if present..."); #endif // Search & run templates. Separate code for desktop/android due to // android having the templates in embedded resources (where cwd'ing to // isn't supported), while for the desktop it is a regular folder. #if !defined(ANDROID) int checksystemwidetemplate = 1; // see if the template path points to a virtual zip folder: if (resource_IsFolderInZip(option_templatepath)) { // it does. run templates from here. checksystemwidetemplate = 0; if (!attemptTemplateLoad(option_templatepath)) { checksystemwidetemplate = 1; } } else { // see if there is a template directory & file: if (file_DoesFileExist(option_templatepath) && file_IsDirectory(option_templatepath)) { checksystemwidetemplate = 0; // now run template file: if (!attemptTemplateLoad(option_templatepath)) { checksystemwidetemplate = 1; } } } #if defined(SYSTEM_TEMPLATE_PATH) if (checksystemwidetemplate) { attemptTemplateLoad(SYSTEM_TEMPLATE_PATH); } #endif #else // if !defined(ANDROID) // on Android, we only allow templates/init.lua. // see if we can read the file: int exists = 0; SDL_RWops* rwops = SDL_RWFromFile("templates/init.lua", "rb"); if (rwops) { exists = 1; rwops->close(rwops); } if (exists) { // run the template file: attemptTemplateLoad("templates/"); } #endif // free template dir now that we've loaded things: free(option_templatepath); #if defined(ANDROID) || defined(__ANDROID__) printinfo("Blitwizard startup: Executing lua start script..."); #endif // push command line arguments into script state: i = 0; int pushfailure = 0; while (i < scriptargcount) { if (!luastate_PushFunctionArgumentToMainstate_String(scriptargs[i])) { pushfailure = 1; break; } i++; } if (pushfailure) { printerror("Error: Couldn't push all script arguments into script state"); main_Quit(1); return 1; } // free arguments: i = 0; while (i < scriptargcount) { free(scriptargs[i]); i++; } free(scriptargs); // open and run provided script file and pass the command line arguments: if (!luastate_DoInitialFile(script, scriptargcount, &error)) { if (error == NULL) { error = outofmem; } printerror("Error: an error occured when running \"%s\": %s", script, error); if (error != outofmem) { free(error); } fatalscripterror(); main_Quit(1); return 1; } // enable blitwizard.onLog doConsoleLog(); #if defined(ANDROID) || defined(__ANDROID__) printinfo("Blitwizard startup: Calling blitwiz.on_init..."); #endif doConsoleLog(); // call init if (!luastate_CallFunctionInMainstate("blitwizard.onInit", 0, 1, 1, &error, NULL, NULL)) { printerror("Error: An error occured when calling blitwizard.onInit: %s",error); if (error != outofmem) { free(error); } fatalscripterror(); main_Quit(1); return 1; } doConsoleLog(); // when graphics or audio is open, run the main loop #if defined(ANDROID) || defined(__ANDROID__) printinfo("Blitwizard startup: Entering main loop..."); #endif doConsoleLog(); // Initialise audio when it isn't main_InitAudio(); doConsoleLog(); // If we failed to initialise audio, we want to simulate it #ifdef USE_AUDIO uint64_t simulateaudiotime = 0; if (simulateaudio) { simulateaudiotime = time_GetMilliseconds(); } #endif uint64_t logictimestamp = time_GetMilliseconds(); uint64_t lastdrawingtime = 0; uint64_t physicstimestamp = time_GetMilliseconds(); while (!wantquit) { doConsoleLog(); uint64_t timeNow = time_GetMilliseconds(); // this is a hack for SDL bug http://bugzilla.libsdl.org/show_bug.cgi?id=1422 #ifdef USE_AUDIO // simulate audio if (simulateaudio) { while (simulateaudiotime < time_GetMilliseconds()) { char buf[48 * 4 * 2]; audiomixer_GetBuffer(buf, 48 * 4 * 2); simulateaudiotime += 1; // 48 * 1000 times * 4 bytes * 2 channels per second = simulated 48kHz 32bit stereo audio } } #endif // ifdef USE_AUDIO // check for unused, no longer playing media objects: checkAllMediaObjectsForCleanup(); // slow sleep: check if we can safe some cpu by waiting longer unsigned int deltaspan = TIMESTEP; #ifndef USE_GRAPHICS int nodraw = 1; #else int nodraw = 1; if (graphics_AreGraphicsRunning()) { nodraw = 0; } #endif // see how much time as already passed since the last frame: uint64_t delta = time_GetMilliseconds()-lastdrawingtime; // sleep/limit FPS as much as we can if (delta < (deltaspan-10)) { // the time passed is smaller than the optimal waiting time // -> sleep if (connections_NoConnectionsOpen() && !listeners_HaveActiveListeners()) { // no connections, use regular sleep time_Sleep((deltaspan-10)-delta); connections_SleepWait(0); } else { // use connection select wait to get connection events connections_SleepWait(deltaspan-delta); } } else { // the time passed exceeds the optimal waiting time already // -> don't slow down at all connections_SleepWait(0); // check on connections } // Remember drawing time and process net events lastdrawingtime = time_GetMilliseconds(); if (!luafuncs_ProcessNetEvents()) { // there was an error processing the events main_Quit(1); } #ifdef USE_GRAPHICS // check and trigger all sort of input events graphics_CheckEvents(&quitevent, &mousebuttonevent, &mousemoveevent, &keyboardevent, &textevent, &putinbackground); #endif doConsoleLog(); // call the step function and advance physics int physicsiterations = 0; int logiciterations = 0; time_t iterationStart = time(NULL); #if defined(USE_PHYSICS2D) int psteps2d_max = ((float)TIMESTEP/ (float)physics_getStepSize(physics2ddefaultworld)); psteps2d_max++; #endif while ( // allow maximum of iterations in an attempt to keep up: (logictimestamp < timeNow || physicstimestamp < timeNow) && (logiciterations < MAXLOGICITERATIONS #if defined(USE_PHYSICS2D) || defined(USE_PHYSICS3D) || physicsiterations < MAXPHYSICSITERATIONS #endif ) // .. unless we're already doing this for >2 seconds: && iterationStart + 2 >= time(NULL) ) { #ifdef USE_PHYSICS2D if (physicsiterations < MAXPHYSICSITERATIONS && physicstimestamp < timeNow && (physicstimestamp <= logictimestamp || logiciterations >= MAXLOGICITERATIONS)) { int psteps = psteps2d_max; while (psteps > 0) { physics_step(physics2ddefaultworld); physicstimestamp += physics_getStepSize( physics2ddefaultworld); psteps--; } physicsiterations++; } #else physicstimestamp = timeNow + 2000; #endif if (logiciterations < MAXLOGICITERATIONS && logictimestamp < timeNow && (logictimestamp <= physicstimestamp || physicsiterations >= MAXPHYSICSITERATIONS)) { // check how much logic we might want to do in a batch: int k = (timeNow-logictimestamp)/TIMESTEP; if (k > MAXBATCHEDLOGIC) { k = MAXBATCHEDLOGIC; } // call logic functions of all objects: int i = luacfuncs_object_doAllSteps(k); doConsoleLog(); // advance time step: logictimestamp += i * TIMESTEP; logiciterations += i; } } // check if we ran out of iterations: if (logiciterations >= MAXLOGICITERATIONS || physicsiterations >= MAXPHYSICSITERATIONS || iterationStart + 2 < time(NULL)) { if ( #if defined(USE_PHYSICS2D) || defined(USE_PHYSICS3D) physicstimestamp < timeNow || #endif logictimestamp < timeNow) { // we got a problem: we aren't finished, // but we hit the iteration limit physicstimestamp = time_GetMilliseconds(); logictimestamp = time_GetMilliseconds(); printwarning("Warning: logic is too slow, maximum logic iterations have been reached (%d)", (int)MAXLOGICITERATIONS); } else { // we don't need to iterate anymore -> everything is fine } } #ifdef USE_GRAPHICS // report visibility of sprites to texture manager: graphics2dsprites_reportVisibility(); #endif #ifdef USE_GRAPHICS // texture manager tick: texturemanager_tick(); #endif // update object graphics: luacfuncs_object_updateGraphics(); doConsoleLog(); #ifdef USE_GRAPHICS if (graphics_AreGraphicsRunning()) { #ifdef ANDROID if (!appinbackground) { #endif // draw a frame graphicsrender_Draw(); #ifdef ANDROID } #endif } #endif // we might want to quit if there is nothing else to do #ifdef USE_AUDIO if ( #ifdef USE_GRAPHICS !graphics_AreGraphicsRunning() && #endif connections_NoConnectionsOpen() && !listeners_HaveActiveListeners() && audiomixer_NoSoundsPlaying()) { #else if ( #ifdef USE_GRAPHICS !graphics_AreGraphicsRunning() && #endif connections_NoConnectionsOpen() && !listeners_HaveActiveListeners()) { #endif main_Quit(1); } #ifdef USE_GRAPHICS // be very sleepy if in background if (appinbackground) { #ifdef ANDROID time_Sleep(40); #endif } #endif // do some garbage collection: /*gcframecount++; if (gcframecount > 100) { // do a gc step once in a while luastate_GCCollect(); }*/ // new frame: #ifdef USE_GRAPHICS luacfuncs_objectgraphics_newFrame(); #endif } main_Quit(0); return 0; }
void APKProtocol::load() { auto resolvedFilename = this->resolvedFilename(); auto options = _options; auto protocolPrefixPosition = resolvedFilename.find("://"); if (protocolPrefixPosition != std::string::npos) { resolvedFilename = resolvedFilename.substr(protocolPrefixPosition + 3); } if (resolvedFilename.find("./") == 0u) { resolvedFilename = resolvedFilename.substr(2u); } _options = options; SDL_RWops* file = SDL_RWFromFile(resolvedFilename.c_str(), "rb"); auto loader = shared_from_this(); if (file) { if (_options->loadAsynchronously() && AbstractCanvas::defaultCanvas() != nullptr && AbstractCanvas::defaultCanvas()->isWorkerRegistered("apk-protocol")) { file->close(file); auto worker = AbstractCanvas::defaultCanvas()->getWorker("apk-protocol"); auto instance = std::static_pointer_cast<APKProtocol>(shared_from_this()); _workerSlot = worker->message()->connect( [this, instance](async::Worker::Ptr, async::Worker::Message message) { if (message.type == "complete") { data().assign(message.data.begin(), message.data.end()); complete()->execute(instance); _activeInstances.erase(instance); _workerSlot = nullptr; } else if (message.type == "progress") { // FIXME } else if (message.type == "error") { error()->execute(instance); _activeInstances.erase(instance); _workerSlot = nullptr; } } ); auto offset = options->seekingOffset(); auto length = options->seekedLength(); std::stringstream inputStream; inputStream.write(reinterpret_cast<const char*>(&offset), 4u); inputStream.write(reinterpret_cast<const char*>(&length), 4u); inputStream.write(resolvedFilename.data(), resolvedFilename.size()); const auto input = inputStream.str(); worker->start(std::vector<char>(input.begin(), input.end())); } else { auto offset = options->seekingOffset(); auto size = options->seekedLength() > 0 ? options->seekedLength() : file->size(file); _progress->execute(shared_from_this(), 0.0); data().resize(size); file->seek(file, offset, RW_SEEK_SET); file->read(file, (char*) &data()[0], size, 1); file->close(file); _progress->execute(loader, 1.0); _complete->execute(shared_from_this()); } } else { _error->execute(shared_from_this()); } }
int main(int argc, char *argv[]) { SDL_RWops *rwops = NULL; char test_buf[30]; cleanup(); rwops = SDL_RWFromFile(NULL,NULL); if (rwops) RWOP_ERR_QUIT(rwops); rwops = SDL_RWFromFile(NULL,"ab+"); if (rwops) RWOP_ERR_QUIT(rwops); rwops = SDL_RWFromFile(NULL,"sldfkjsldkfj"); if (rwops) RWOP_ERR_QUIT(rwops); rwops = SDL_RWFromFile("something",""); if (rwops) RWOP_ERR_QUIT(rwops); rwops = SDL_RWFromFile("something",NULL); if (rwops) RWOP_ERR_QUIT(rwops); printf("test1 OK\n"); rwops = SDL_RWFromFile(FBASENAME2,"rb"); if (rwops) RWOP_ERR_QUIT(rwops); rwops = SDL_RWFromFile(FBASENAME2,"rb+"); if (rwops) RWOP_ERR_QUIT(rwops); rwops = SDL_RWFromFile(FBASENAME2,"wb"); if (!rwops) RWOP_ERR_QUIT(rwops); rwops->close(rwops); unlink(FBASENAME2); rwops = SDL_RWFromFile(FBASENAME2,"wb+"); if (!rwops) RWOP_ERR_QUIT(rwops); rwops->close(rwops); unlink(FBASENAME2); rwops = SDL_RWFromFile(FBASENAME2,"ab"); if (!rwops) RWOP_ERR_QUIT(rwops); rwops->close(rwops); unlink(FBASENAME2); rwops = SDL_RWFromFile(FBASENAME2,"ab+"); if (!rwops) RWOP_ERR_QUIT(rwops); rwops->close(rwops); unlink(FBASENAME2); printf("test2 OK\n"); rwops = SDL_RWFromFile(FBASENAME1,"wb"); if (!rwops) RWOP_ERR_QUIT(rwops); if (1 != rwops->write(rwops,"1234567890",10,1) ) RWOP_ERR_QUIT(rwops); if (10 != rwops->write(rwops,"1234567890",1,10) ) RWOP_ERR_QUIT(rwops); if (7 != rwops->write(rwops,"1234567",1,7) ) RWOP_ERR_QUIT(rwops); if (0!=rwops->seek(rwops,0L,RW_SEEK_SET)) RWOP_ERR_QUIT(rwops); if (0!=rwops->read(rwops,test_buf,1,1)) RWOP_ERR_QUIT(rwops); rwops->close(rwops); rwops = SDL_RWFromFile(FBASENAME1,"rb"); if (!rwops) RWOP_ERR_QUIT(rwops); if (0!=rwops->seek(rwops,0L,RW_SEEK_SET)) RWOP_ERR_QUIT(rwops); if (20!=rwops->seek(rwops,-7,RW_SEEK_END)) RWOP_ERR_QUIT(rwops); if (7!=rwops->read(rwops,test_buf,1,7)) RWOP_ERR_QUIT(rwops); if (SDL_memcmp(test_buf,"1234567",7)) RWOP_ERR_QUIT(rwops); if (0!=rwops->read(rwops,test_buf,1,1)) RWOP_ERR_QUIT(rwops); if (0!=rwops->read(rwops,test_buf,10,100)) RWOP_ERR_QUIT(rwops); if (0!=rwops->seek(rwops,-27,RW_SEEK_CUR)) RWOP_ERR_QUIT(rwops); if (2!=rwops->read(rwops,test_buf,10,3)) RWOP_ERR_QUIT(rwops); if (SDL_memcmp(test_buf,"12345678901234567890",20)) RWOP_ERR_QUIT(rwops); if (0!=rwops->write(rwops,test_buf,1,1)) RWOP_ERR_QUIT(rwops); rwops->close(rwops); rwops = SDL_RWFromFile(FBASENAME1,"wb+"); if (!rwops) RWOP_ERR_QUIT(rwops); if (1 != rwops->write(rwops,"1234567890",10,1) ) RWOP_ERR_QUIT(rwops); if (10 != rwops->write(rwops,"1234567890",1,10) ) RWOP_ERR_QUIT(rwops); if (7 != rwops->write(rwops,"1234567",1,7) ) RWOP_ERR_QUIT(rwops); if (0!=rwops->seek(rwops,0L,RW_SEEK_SET)) RWOP_ERR_QUIT(rwops); if (1!=rwops->read(rwops,test_buf,1,1)) RWOP_ERR_QUIT(rwops); if (0!=rwops->seek(rwops,0L,RW_SEEK_SET)) RWOP_ERR_QUIT(rwops); if (20!=rwops->seek(rwops,-7,RW_SEEK_END)) RWOP_ERR_QUIT(rwops); if (7!=rwops->read(rwops,test_buf,1,7)) RWOP_ERR_QUIT(rwops); if (SDL_memcmp(test_buf,"1234567",7)) RWOP_ERR_QUIT(rwops); if (0!=rwops->read(rwops,test_buf,1,1)) RWOP_ERR_QUIT(rwops); if (0!=rwops->read(rwops,test_buf,10,100)) RWOP_ERR_QUIT(rwops); if (0!=rwops->seek(rwops,-27,RW_SEEK_CUR)) RWOP_ERR_QUIT(rwops); if (2!=rwops->read(rwops,test_buf,10,3)) RWOP_ERR_QUIT(rwops); if (SDL_memcmp(test_buf,"12345678901234567890",20)) RWOP_ERR_QUIT(rwops); rwops->close(rwops); printf("test3 OK\n"); rwops = SDL_RWFromFile(FBASENAME1,"rb+"); if (!rwops) RWOP_ERR_QUIT(rwops); if (1 != rwops->write(rwops,"1234567890",10,1) ) RWOP_ERR_QUIT(rwops); if (10 != rwops->write(rwops,"1234567890",1,10) ) RWOP_ERR_QUIT(rwops); if (7 != rwops->write(rwops,"1234567",1,7) ) RWOP_ERR_QUIT(rwops); if (0!=rwops->seek(rwops,0L,RW_SEEK_SET)) RWOP_ERR_QUIT(rwops); if (1!=rwops->read(rwops,test_buf,1,1)) RWOP_ERR_QUIT(rwops); if (0!=rwops->seek(rwops,0L,RW_SEEK_SET)) RWOP_ERR_QUIT(rwops); if (20!=rwops->seek(rwops,-7,RW_SEEK_END)) RWOP_ERR_QUIT(rwops); if (7!=rwops->read(rwops,test_buf,1,7)) RWOP_ERR_QUIT(rwops); if (SDL_memcmp(test_buf,"1234567",7)) RWOP_ERR_QUIT(rwops); if (0!=rwops->read(rwops,test_buf,1,1)) RWOP_ERR_QUIT(rwops); if (0!=rwops->read(rwops,test_buf,10,100)) RWOP_ERR_QUIT(rwops); if (0!=rwops->seek(rwops,-27,RW_SEEK_CUR)) RWOP_ERR_QUIT(rwops); if (2!=rwops->read(rwops,test_buf,10,3)) RWOP_ERR_QUIT(rwops); if (SDL_memcmp(test_buf,"12345678901234567890",20)) RWOP_ERR_QUIT(rwops); rwops->close(rwops); printf("test4 OK\n"); rwops = SDL_RWFromFile(FBASENAME1,"ab+"); if (!rwops) RWOP_ERR_QUIT(rwops); if (1 != rwops->write(rwops,"1234567890",10,1) ) RWOP_ERR_QUIT(rwops); if (10 != rwops->write(rwops,"1234567890",1,10) ) RWOP_ERR_QUIT(rwops); if (7 != rwops->write(rwops,"1234567",1,7) ) RWOP_ERR_QUIT(rwops); if (0!=rwops->seek(rwops,0L,RW_SEEK_SET)) RWOP_ERR_QUIT(rwops); if (1!=rwops->read(rwops,test_buf,1,1)) RWOP_ERR_QUIT(rwops); if (0!=rwops->seek(rwops,0L,RW_SEEK_SET)) RWOP_ERR_QUIT(rwops); if (20+27!=rwops->seek(rwops,-7,RW_SEEK_END)) RWOP_ERR_QUIT(rwops); if (7!=rwops->read(rwops,test_buf,1,7)) RWOP_ERR_QUIT(rwops); if (SDL_memcmp(test_buf,"1234567",7)) RWOP_ERR_QUIT(rwops); if (0!=rwops->read(rwops,test_buf,1,1)) RWOP_ERR_QUIT(rwops); if (0!=rwops->read(rwops,test_buf,10,100)) RWOP_ERR_QUIT(rwops); if (27!=rwops->seek(rwops,-27,RW_SEEK_CUR)) RWOP_ERR_QUIT(rwops); if (0!=rwops->seek(rwops,0L,RW_SEEK_SET)) RWOP_ERR_QUIT(rwops); if (3!=rwops->read(rwops,test_buf,10,3)) RWOP_ERR_QUIT(rwops); if (SDL_memcmp(test_buf,"123456789012345678901234567123",30)) RWOP_ERR_QUIT(rwops); rwops->close(rwops); printf("test5 OK\n"); cleanup(); return 0; }