/* Copyright (C) 2006 Parallel Realities This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ #include "init.h" void checkForLicense(); /* Show the GNU Public License the first time the game is played. Waits 4 seconds and then proceeds. THIS MUST NOT BE REMOVED!!!!! */ void showLicense() { } void showViolenceWarning() { Texture *texture = graphics->loadTexture("gfx/game/violenceWarning.jpg"); mouse->setBusy(true); graphics->setMode(MODE_2D); graphics->clearScreen(); graphics->delay(1000, false); renderScaledTexture(texture); graphics->updateScreen(); graphics->delay(4000, false); delete texture; } void setupUserHomeDirectory() { char *userHome = getenv("HOME"); if ((!userHome) || (userHome == NULL)) { printf("Couldn't determine user home directory! Exitting.\n"); exit(1); } String dir; dir.setText("%s/.parallelrealities", userHome); if ((mkdir(dir.getText(), S_IRWXU|S_IRWXG|S_IROTH|S_IXOTH) != 0) && (errno != EEXIST)) { printf("Couldn't create required directory '%s'\n", dir.getText()); exit(1); } dir.setText("%s/.parallelrealities/blobAndConquer", userHome); if ((mkdir(dir.getText(), S_IRWXU|S_IRWXG|S_IROTH|S_IXOTH) != 0) && (errno != EEXIST)) { printf("Couldn't create required directory '%s'\n", dir.getText()); exit(1); } engine->userHomeDirectory.setText("%s/.parallelrealities/blobAndConquer", userHome); } void loadSaveGameHeaders() { String filename; filename.setText("%s/savedata", engine->userHomeDirectory.getText()); List *list = loadProperties(filename.getText(), false); if (list == NULL) { return; } int slot = 0; for (Properties *props = (Properties*)list->getFirstElement() ; props != NULL ; props = (Properties*)props->next) { engine->saveSlot[slot++].load(props); } delete list; } bool loadConfig() { String string; string.setText("%s/config", engine->userHomeDirectory.getText()); List *list = loadProperties(string.getText(), false); if ((list == NULL) || (list->getSize() == 0)) { return false; } Properties *props = (Properties*)list->getFirstElement(); graphics->fullscreen = props->getInt("fullscreen", 0); audio->soundVolume = props->getInt("soundVolume", 128); audio->musicVolume = props->getInt("musicVolume", 90); audio->ambientVolume = props->getInt("ambientVolume", 65); audio->environmentVolume = props->getInt("environmentVolume", 50); graphics->gamma = props->getFloat("brightness", 100); Math::limit(&graphics->gamma, 50, 200); int w, h, c; sscanf(props->getString("resolution", "0 x 0"), "%d %*s %d", &w, &h); for (unsigned i = 0 ; i < MAX_RESOLUTIONS ; i++) { if ((graphics->screenMode[i].w == w) && (graphics->screenMode[i].h == h)) { graphics->currentScreenResolution = i; } } for (int i = 0 ; i < CTRL_MAXIMUM ; i++) { string.setText("keyboard%d", i); sscanf(props->getString(string.getText(), "-1"), "%d", &c); game->keyboard[i] = c; string.setText("joystick%d", i); sscanf(props->getString(string.getText(), "-1"), "%d", &c); game->joystick[i] = c; string.setText("mouse%d", i); sscanf(props->getString(string.getText(), "-1"), "%d", &c); game->mouseCtrl[i] = c; } game->joystickDeadZone = props->getInt("joystickDeadZone", 4500); game->mouseSensitivity = props->getInt("mouseSensitivity", 100); mouse->grab = props->getInt("grabMouse", 1); game->bloodPolicy = props->getInt("bloodPolicy", BLOOD_POLICY_ON); game->shadowPolicy = props->getInt("shadowPolicy", SHADOW_POLICY_ON); game->decalPolicy = props->getInt("decalPolicy", DECAL_POLICY_ON); delete list; return true; } void saveConfig() { if (graphics->screen == NULL) { return; } String savePath; savePath.setText("%s/config", engine->userHomeDirectory.getText()); FILE *fp = fopen(savePath.getText(), "wb"); if (!fp) { return; } Properties props; props.setName("Config"); String string; string.setText("%d x %d", graphics->screen->w, graphics->screen->h); props.setProperty("resolution", string.getText()); props.setProperty("fullscreen", graphics->fullscreen); props.setProperty("soundVolume", audio->soundVolume); props.setProperty("musicVolume", audio->musicVolume); props.setProperty("ambientVolume", audio->ambientVolume); props.setProperty("environmentVolume", audio->environmentVolume); props.setProperty("brightness", graphics->gamma); for (int i = 0 ; i < CTRL_MAXIMUM ; i++) { string.setText("keyboard%d", i); props.setProperty(string.getText(), game->keyboard[i]); string.setText("joystick%d", i); props.setProperty(string.getText(), game->joystick[i]); string.setText("mouse%d", i); props.setProperty(string.getText(), game->mouseCtrl[i]); } props.setProperty("joystickDeadZone", game->joystickDeadZone); props.setProperty("mouseSensitivity", game->mouseSensitivity); props.setProperty("grabMouse", mouse->grab); props.setProperty("bloodPolicy", game->bloodPolicy); props.setProperty("shadowPolicy", game->shadowPolicy); props.setProperty("decalPolicy", game->decalPolicy); props.save(fp); fprintf(fp, "@END@\n"); fclose(fp); } void initOpenGL() { debug(("initOpenGL()\n")) glBlendFunc(GL_SRC_ALPHA, GL_ONE); glShadeModel(GL_SMOOTH); glClearDepth(1.0f); glHint(GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST); glDisable(GL_LIGHTING); glEnable(GL_DEPTH_TEST); glEnable(GL_COLOR_MATERIAL); glEnable(GL_TEXTURE_2D); glEnable(GL_BLEND); glDepthFunc(GL_LEQUAL); glTexGeni(GL_S, GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP); glTexGeni(GL_T, GL_TEXTURE_GEN_MODE, GL_SPHERE_MAP); String extensions = (char*)glGetString(GL_EXTENSIONS); if (!strstr(extensions.getText(), "GL_ARB_multitexture")) { graphics->showErrorAndExit("OpenGL multitexturing is not supported"); } if (!strstr(extensions.getText(), "GL_ARB_multitexture")) { graphics->showErrorAndExit("OpenGL multitexturing is not supported"); } GLint stencil; glGetIntegerv(GL_STENCIL_BITS, &stencil); /* update queried hasStencils value with the real thing */ graphics->hasStencils = stencil; if (!graphics->hasStencils) { printf("Warning: Stencil Buffering is not supported,\n"); #ifdef __unix__ printf(" try changing your X-windows colordepth to 32bpp,\n"); #endif printf(" disabling shadows!\n"); game->shadowPolicy = SHADOW_POLICY_OFF; } /* char *ext = strtok(extensions.getText(), " "); while (ext) { debug(("initOpenGL() - Extension '%s' Available\n", ext)); ext = strtok(NULL, " "); } */ debug(("Vendor : %s\n", glGetString(GL_VENDOR))); debug(("Version : %s\n", glGetString(GL_VERSION))); debug(("Renderer : %s\n", glGetString(GL_RENDERER))); debug(("initOpenGL() :: Done\n")) } void initSystem() { debug(("initSystem()\n")) setupUserHomeDirectory(); loadSaveGameHeaders(); /* Initialize the SDL library */ if (SDL_Init(SDL_INIT_VIDEO|SDL_INIT_AUDIO|SDL_INIT_JOYSTICK) < 0) { printf("Couldn't initialize SDL: %s\n", SDL_GetError()); exit(1); } graphics->queryStencilSupport(); SDL_GL_SetAttribute(SDL_GL_DOUBLEBUFFER, 1); if (graphics->hasStencils) { SDL_GL_SetAttribute(SDL_GL_STENCIL_SIZE, 8); } else { SDL_GL_SetAttribute(SDL_GL_STENCIL_SIZE, 0); } SDL_GL_SetAttribute(SDL_GL_SWAP_CONTROL, 1); graphics->getAvailableScreenModes(); bool displayLicense = loadConfig(); debug(("User Home = %s\n", engine->userHomeDirectory.getText())); graphics->setResolution(graphics->currentScreenResolution); if (TTF_Init() < 0) { printf("Couldn't initialize SDL TTF: %s\n", SDL_GetError()); exit(1); } //audio->useAudio = false; if (audio->useAudio) { debug(("Opening Audio...\n")); if (Mix_OpenAudio(22050, AUDIO_S16, 1, 1024) < 0) { printf("Warning: Couldn't set 22050 Hz 16-bit audio - Reason: %s\n", Mix_GetError()); printf("Sound and Music will be disabled\n"); audio->useAudio = 0; } else { debug(("Audio OK...\n")); int result = 0; result = Mix_AllocateChannels(MAX_CHANNELS); debug(("Allocated %d sound channels\n", result)); result = Mix_ReserveChannels(CH_EFFECT1); debug(("Reserved first %d sound channels\n", result)); } } if (SDL_NumJoysticks() > 0) { debug(("Found a joystick...\n")); SDL_JoystickEventState(SDL_ENABLE); debug(("Opening Joystick %s...\n", SDL_JoystickName(0))); engine->joystick = SDL_JoystickOpen(0); engine->buttonState = new char[SDL_JoystickNumButtons(engine->joystick)]; debug(("Number of Analog Sticks: %d\n", SDL_JoystickNumAxes(engine->joystick))); } else { debug(("No joystick available.\n")); } srand(time(NULL)); graphics->mapColors(); SDL_SetGamma(graphics->gamma / 100, graphics->gamma / 100, graphics->gamma / 100); graphics->loadFont(FONT_NORMAL, "data/fonts/vera.ttf", 12); graphics->loadFont(FONT_LARGE, "data/fonts/vera.ttf", 32); graphics->loadFont(FONT_DIGITAL, "data/fonts/909.ttf", 32); graphics->loadFont(FONT_LARGE_DIGITAL, "data/fonts/909.ttf", 5); graphics->loadFont(FONT_NUMBER, "data/fonts/vera.ttf", 5); graphics->loadTimerDigits(); uiManager->upArrow = graphics->loadTexture("gfx/gui/upArrow.png"); uiManager->downArrow = graphics->loadTexture("gfx/gui/downArrow.png"); uiManager->minus = graphics->loadTexture("gfx/gui/minus.png"); uiManager->plus = graphics->loadTexture("gfx/gui/plus.png"); uiManager->unchecked = graphics->loadTexture("gfx/gui/unchecked.png"); uiManager->checked = graphics->loadTexture("gfx/gui/checked.png"); uiManager->awaitingButton = graphics->getGLString("???"); //SDL_WM_SetIcon(device, NULL); SDL_WM_SetCaption("Blob Wars : Blob and Conquer", "Blob And Conquer"); SDL_EnableKeyRepeat(500, 30); // force defaults or loaded audio->setSoundVolume(audio->soundVolume); audio->setMusicVolume(audio->musicVolume); audio->setAmbientVolume(audio->ambientVolume); audio->setEnvironmentVolume(audio->environmentVolume); RandomNameGenerator::getInstance()->loadFrequencyTable("data/misc/letterFrequencyTable"); engine->loadDefines(); // Always needed audio->loadSound(SND_BUTTONCLICK, "sound/gui/buttonClick.ogg"); if (displayLicense) { #if !DEV #endif } #if !DEV showViolenceWarning(); #endif graphics->clearScreen(); graphics->updateScreen(); debug(("initSystem() :: Done\n")); } /* Removes [hopefully] all the resources that has been loaded and created during the game. This is called by atexit(); */ void cleanup() { //BoundingBoxManager::getInstance()->dump(); mouse->setBusy(false); debug(("Cleaning Up...\n")); debug(("Deleting Tracer...\n")); delete tracer; debug(("Freeing Audio...\n")); audio->destroy(); debug(("Removing Music...\n")); remove(TEMPDIR"music.mod"); debug(("Saving Config...\n")); saveConfig(); debug(("Removing Font File...\n")); remove(TEMPDIR"font.ttf"); debug(("Removing PAK File Data...\n")); //Pak::getInstance()->clear(); debug(("Closing Audio...\n")); if (audio->useAudio) { Mix_CloseAudio(); } debug(("Freeing Game Data...\n")); game->destroy(); debug(("Freeing Remaining Entities...\n")); entityManager->destroy(); debug(("Freeing Widgets...\n")); uiManager->clearWidgetList(); debug(("Freeing Sprites and Fonts\n")); graphics->destroy(); debug(("Freeing Textures...\n")); textureManager->clear(); debug(("Freeing Models...\n")); modelManager->clear(); debug(("Closing TTF...\n")); TTF_Quit(); if (engine->joystick != NULL) { SDL_JoystickEventState(SDL_DISABLE); debug(("Closing Joystick %s...\n", SDL_JoystickName(0))); SDL_JoystickClose(engine->joystick); } SDL_Quit(); debug(("All Done.\n")); }