diff options
author | Bjørn Lindeijer <bjorn@lindeijer.nl> | 2005-04-26 00:04:45 +0000 |
---|---|---|
committer | Bjørn Lindeijer <bjorn@lindeijer.nl> | 2005-04-26 00:04:45 +0000 |
commit | 8b0e30d3798cd5bdce2c3a34a3c384e90dceac99 (patch) | |
tree | 3fdca13a0cc138ed65b72de8cd3747cc79916818 /src | |
parent | a31ba215a3043ebd62d415a7d855a531239fb630 (diff) | |
download | mana-client-8b0e30d3798cd5bdce2c3a34a3c384e90dceac99.tar.gz mana-client-8b0e30d3798cd5bdce2c3a34a3c384e90dceac99.tar.bz2 mana-client-8b0e30d3798cd5bdce2c3a34a3c384e90dceac99.tar.xz mana-client-8b0e30d3798cd5bdce2c3a34a3c384e90dceac99.zip |
Changed keyboard control to integrate better with mouse walk, changed location
of packet.list and chatlog.txt and removed name from player chat "balloon".
Diffstat (limited to 'src')
-rw-r--r-- | src/being.cpp | 49 | ||||
-rw-r--r-- | src/being.h | 36 | ||||
-rw-r--r-- | src/engine.cpp | 14 | ||||
-rw-r--r-- | src/game.cpp | 174 | ||||
-rw-r--r-- | src/game.h | 1 | ||||
-rw-r--r-- | src/gui/chat.cpp | 14 | ||||
-rw-r--r-- | src/gui/chat.h | 8 | ||||
-rw-r--r-- | src/gui/gui.cpp | 13 | ||||
-rw-r--r-- | src/gui/window.h | 2 | ||||
-rw-r--r-- | src/main.cpp | 18 | ||||
-rw-r--r-- | src/map.cpp | 29 | ||||
-rw-r--r-- | src/map.h | 7 | ||||
-rw-r--r-- | src/net/protocol.h | 3 | ||||
-rw-r--r-- | src/resources/resourcemanager.cpp | 11 | ||||
-rw-r--r-- | src/resources/resourcemanager.h | 35 | ||||
-rw-r--r-- | src/sound.cpp | 44 | ||||
-rw-r--r-- | src/sound.h | 11 |
17 files changed, 246 insertions, 223 deletions
diff --git a/src/being.cpp b/src/being.cpp index 03649dc6..dd2b2333 100644 --- a/src/being.cpp +++ b/src/being.cpp @@ -148,7 +148,6 @@ void sort() { } Being::Being(): - damage(""), id(0), job(0), x(0), y(0), destX(0), destY(0), direction(0), type(0), action(0), frame(0), @@ -157,21 +156,23 @@ Being::Being(): speed(150), emotion(0), emotion_time(0), text_x(0), text_y(0), - hairStyle(1), hairColor(1), weapon(0), speech_time(0), damage_time(0), showSpeech(false), showDamage(false), - aspd(350) + aspd(350), + hairStyle(1), hairColor(1) { strcpy(name, ""); } -Being::~Being() { +Being::~Being() +{ clearPath(); } -void Being::clearPath() { +void Being::clearPath() +{ path.clear(); } @@ -182,6 +183,13 @@ void Being::setPath(std::list<PATH_NODE> path) walk_time = tick_time; } +void Being::setDestination(int destX, int destY) +{ + this->destX = destX; + this->destY = destY; + setPath(tiledMap->findPath(x, y, destX, destY)); +} + void Being::setHairColor(int color) { hairColor = color; @@ -261,6 +269,9 @@ void Being::nextStep() y = newY; action = WALK; walk_time += speed / 10; + if (this == player_node) { + walk_status = 1; + } } else { action = STAND; if (this == player_node) { @@ -274,16 +285,9 @@ void Being::drawSpeech(Graphics *graphics) { // Draw speech above this being if (showSpeech) { - //if (being->speech_color == makecol(255, 255, 255)) { - // guiGraphics->drawText(being->speech, - // being->text_x + 16, being->text_y - 60, - // gcn::Graphics::CENTER); - //} - //else { graphics->drawText(speech, text_x + 20, text_y - 60, gcn::Graphics::CENTER); - //} } if (showDamage) { graphics->drawText(damage, @@ -293,20 +297,17 @@ void Being::drawSpeech(Graphics *graphics) } } -bool Being::isPlayer() { - if (job < 10) - return true; - return false; +bool Being::isPlayer() +{ + return job < 10; } -bool Being::isNpc() { - if (job > 45 && job <126) - return true; - return false; +bool Being::isNpc() +{ + return job > 45 && job < 126; } -bool Being::isMonster() { - if (job > 200) - return true; - return false; +bool Being::isMonster() +{ + return job > 200; } diff --git a/src/being.h b/src/being.h index dc90942d..c246aeaa 100644 --- a/src/being.h +++ b/src/being.h @@ -37,13 +37,8 @@ struct PATH_NODE { unsigned short x, y; }; -class Being { - private: - std::list<PATH_NODE> path; - std::string speech; - std::string damage; - unsigned short hairStyle, hairColor; - +class Being +{ public: unsigned int id; unsigned short job; @@ -83,9 +78,9 @@ class Being { void clearPath(); /** - * Sets the new path for this being. + * Sets a new destination for this being to walk to. */ - void setPath(std::list<PATH_NODE> path); + void setDestination(int x, int y); /** * Puts a "speech balloon" above this being for the specified amount @@ -104,7 +99,7 @@ class Being { * @param time The amount of time the text should stay in milliseconds. */ void setDamage(const std::string &text, int time); - + /** * Sets the name for the being * @@ -121,12 +116,12 @@ class Being { * Sets the hair style for this being. */ void setHairStyle(int style); - + /** * Gets the hair color for this being. */ unsigned short getHairColor(); - + /** * Gets the hair style for this being. */ @@ -141,21 +136,32 @@ class Being { * Draws the speech text above the being. */ void drawSpeech(Graphics *graphics); - + /** * Checks if the being is a player. */ bool isPlayer(); - + /** * Checks if the being is a npc. */ bool isNpc(); - + /** * Checks if the being is a monster. */ bool isMonster(); + + private: + /** + * Sets the new path for this being. + */ + void setPath(std::list<PATH_NODE> path); + + std::list<PATH_NODE> path; + std::string speech; + std::string damage; + unsigned short hairStyle, hairColor; }; /** Add a Being to the list */ diff --git a/src/engine.cpp b/src/engine.cpp index bed0b1d1..e013041f 100644 --- a/src/engine.cpp +++ b/src/engine.cpp @@ -145,7 +145,7 @@ Engine::Engine() guiTop->add(debugInfo); // Create dialogs - chatWindow = new ChatWindow("./docs/chatlog.txt", 20); + chatWindow = new ChatWindow("chatlog.txt", 20); statusWindow = new StatusWindow(); buyDialog = new BuyDialog(); sellDialog = new SellDialog(); @@ -183,7 +183,7 @@ Engine::Engine() requestTradeDialog->setPosition(screen->w - statusWindow->getWidth() - requestTradeDialog->getWidth() - 10, chatWindow->getHeight() + 15); - + // Set initial window visibility chatWindow->setVisible(true); statusWindow->setVisible(true); @@ -204,7 +204,7 @@ Engine::Engine() requestTradeDialog->setVisible(false); // Do not focus any text field gui->focusNone(); - + // Load the sprite sets ResourceManager *resman = ResourceManager::getInstance(); Image *npcbmp = resman->getImage( @@ -225,7 +225,7 @@ Engine::Engine() emotionset = new Spriteset(emotionbmp, 19, 19); weaponset = new Spriteset(weaponbitmap, 160, 120); itemset = new Spriteset(itembitmap, 20, 20); - + // Loads all the monsters for (int i = 0; i < MONSTERS_NUMBER; i++) { @@ -289,7 +289,7 @@ void Engine::logic() break; } } - + if (get_elapsed_time(being->speech_time) > 5000) being->showSpeech = false; if (get_elapsed_time(being->damage_time) > 3000) @@ -427,7 +427,7 @@ void Engine::draw() being->text_y = sy * 32 - 65 + get_y_offset(being) - offset_y; int mf = being->frame + being->action; - + if (being->action == MONSTER_DEAD) { monsterset[being->job - 1002]->spriteset[dir + 4 * MONSTER_DEAD]->draw(screen, being->text_x + 30, being->text_y + 40); @@ -446,7 +446,7 @@ void Engine::draw() } } } - + beingIterator++; // nodes are ordered so if the next being y is > then the diff --git a/src/game.cpp b/src/game.cpp index ffc6ebd9..87c59354 100644 --- a/src/game.cpp +++ b/src/game.cpp @@ -182,7 +182,7 @@ void do_init() add_node(player_node); - remove("./docs/packet.list"); + remove("packet.list"); } void do_exit() @@ -402,13 +402,14 @@ void do_input() keys = SDL_GetKeyState(NULL); int xDirection = 0; int yDirection = 0; - int Direction = 0; + int Direction = DIR_NONE; if (walk_status == 0 && player_node->action != DEAD && current_npc == 0) { int x = player_node->x; int y = player_node->y; + // Translate pressed keys to movement if (keys[SDLK_UP] || keys[SDLK_KP8]) { yDirection = -1; @@ -446,92 +447,68 @@ void do_input() yDirection = -1; } - if ( xDirection == 1 && yDirection == 0 ) // Right + // Translate movement to direction + if (xDirection == 1 && yDirection == 0) // Right { Direction = EAST; } - if ( xDirection == -1 && yDirection == 0 ) // Left + if (xDirection == -1 && yDirection == 0) // Left { Direction = WEST; } - if ( xDirection == 0 && yDirection == -1 ) // Up + if (xDirection == 0 && yDirection == -1) // Up { Direction = NORTH; } - if ( xDirection == 0 && yDirection == 1 ) // Down + if (xDirection == 0 && yDirection == 1) // Down { Direction = SOUTH; } - if ( xDirection == 1 && yDirection == 1 ) // Bottom-Right + if (xDirection == 1 && yDirection == 1) // Bottom-Right { Direction = SE; } - if ( xDirection == -1 && yDirection == -1 ) // Top-left + if (xDirection == -1 && yDirection == -1) // Top-left { Direction = NW; } - if ( xDirection == 1 && yDirection == -1 ) // Top-Right + if (xDirection == 1 && yDirection == -1) // Top-Right { Direction = NE; } - if ( xDirection == -1 && yDirection == 1 ) // Bottom-Left + if (xDirection == -1 && yDirection == 1) // Bottom-Left { Direction = SW; } - if ( xDirection != 0 || yDirection != 0 ) + // Update the player direction to where he wants to walk + // Warning: Not communicated to the server yet + if (Direction != DIR_NONE) { + player_node->direction = Direction; + } + + // Prevent skipping corners over colliding tiles + if (xDirection != 0 && tiledMap->tileCollides(x + xDirection, y)) { + xDirection = 0; + } + if (yDirection != 0 && tiledMap->tileCollides(x, y + yDirection)) { + yDirection = 0; + } + + // Choose a straight direction when diagonal target is blocked + if (yDirection != 0 && xDirection != 0 && + !tiledMap->getWalk(x + xDirection, y + yDirection)) { + xDirection = 0; + } + + // Walk to where the player can actually go + if ((xDirection != 0 || yDirection != 0) && + tiledMap->getWalk(x + xDirection, y + yDirection)) { - if (tiledMap->getWalk(x + xDirection, y + yDirection) != 0) - { - walk(x + xDirection, y + yDirection, Direction); - walk_status = 1; - player_node->action = WALK; - player_node->walk_time = tick_time; - player_node->x = x + xDirection; - player_node->y = y + yDirection; - player_node->direction = Direction; - } - else if (tiledMap->getWalk(x + xDirection, y) != 0) - { // Going back to straight direction Left or right - if ( xDirection == 1 ) //right - { - Direction = EAST; - } - else // left - { - Direction = WEST; - } - yDirection = 0; - walk(x + xDirection, y + yDirection, Direction); - walk_status = 1; - player_node->action = WALK; - player_node->walk_time = tick_time; - player_node->x = x + xDirection; - player_node->y = y + yDirection; - player_node->direction = Direction; - } - else if (tiledMap->getWalk(x, y + yDirection) != 0) - { // Going back to straight direction up or down - if ( yDirection == 1 ) //Down - { - Direction = SOUTH; - } - else // Up - { - Direction = NORTH; - } - xDirection = 0; - walk(x + xDirection, y + yDirection, Direction); - walk_status = 1; - player_node->action = WALK; - player_node->walk_time = tick_time; - player_node->x = x + xDirection; - player_node->y = y + yDirection; - player_node->direction = Direction; - } - else player_node->direction = Direction; + walk(x + xDirection, y + yDirection, Direction); + player_node->setDestination(x + xDirection, y + yDirection); } - + if (player_node->action == STAND) { if (keys[SDLK_LCTRL]) @@ -541,24 +518,27 @@ void do_input() player_node->y, player_node->direction); player_node->walk_time = tick_time; - - if (player_node->weapon == 2) + + if (player_node->weapon == 2) { sound.playSfx("sfx/bow_shoot_1.ogg"); - else + } + else { sound.playSfx("sfx/fist-swish.ogg"); + } } } - - } // End if alive + } } -int get_packet_length(short id) { +int get_packet_length(short id) +{ int len = get_length(id); if (len == -1) len = RFIFOW(2); return len; } -void do_parse() { +void do_parse() +{ unsigned short id; char *temp; Being *being = NULL; @@ -585,7 +565,7 @@ void do_parse() { fclose(file); */ #ifdef __DEBUG - FILE *file = fopen("./docs/packet.list", "a"); + FILE *file = fopen("packet.list", "a"); fprintf(file, "%x\n", RFIFOW(0)); fclose(file); #endif @@ -597,32 +577,39 @@ void do_parse() { player_node->y = get_y(RFIFOP(6)); break; - // Received speech - case 0x008d: - temp = (char *)malloc(RFIFOW(2)-7); - memset(temp, '\0', RFIFOW(2)-7); - memcpy(temp, RFIFOP(8), RFIFOW(2)-8); + // Received speech from being + case SMSG_BEING_CHAT: being = findNode(RFIFOL(4)); if (being != NULL) { - // White - being->setSpeech(temp, SPEECH_TIME); + int length = RFIFOW(2) - 8; + temp = (char*)malloc(length + 1); + temp[length] = '\0'; + memcpy(temp, RFIFOP(8), length); + std::string msg = std::string(temp); + msg.erase(0, msg.find(" : ", 0) + 3); + + being->setSpeech(msg, SPEECH_TIME); chatWindow->chat_log(temp, BY_OTHER); + + free(temp); } - free(temp); break; - case 0x008e: - case 0x009a: - if (RFIFOW(2) > 4) { - // Receiving 1 byte less than expected, server might be - // sending garbage instead of '\0' /-kth5 - temp = (char *)malloc(RFIFOW(2) - 3); - memset(temp, '\0', RFIFOW(2) - 3); - memcpy(temp, RFIFOP(4), RFIFOW(2) - 4); - // White - player_node->setSpeech(temp, SPEECH_TIME); + case SMSG_MY_BEING_CHAT: + case SMSG_GM_CHAT: + if (RFIFOW(2) > 4) { + int length = RFIFOW(2) - 4; + temp = (char*)malloc(length + 1); + temp[length] = '\0'; + memcpy(temp, RFIFOP(4), length); + std::string msg = std::string(temp); + unsigned int pos = msg.find(" : ", 0); if (id == 0x008e) { + if (pos != std::string::npos) { + msg.erase(0, pos + 3); + } + player_node->setSpeech(msg, SPEECH_TIME); chatWindow->chat_log(temp, BY_PLAYER); } else { @@ -632,6 +619,7 @@ void do_parse() { free(temp); } break; + // Success to walk request case 0x0087: if (walk_status == 1) { @@ -734,9 +722,9 @@ void do_parse() { being->job = RFIFOW(14); being->weapon = RFIFOW(18); - being->setPath(tiledMap->findPath( - being->x, being->y, - being->destX, being->destY)); + being->setDestination( + get_dest_x(RFIFOP(50)), + get_dest_y(RFIFOP(50))); break; case SMSG_MOVE_PLAYER_BEING: @@ -759,9 +747,9 @@ void do_parse() { being->setHairStyle(RFIFOW(16)); being->setHairColor(RFIFOW(32)); - being->setPath(tiledMap->findPath( - being->x, being->y, - being->destX, being->destY)); + being->setDestination( + get_dest_x(RFIFOP(50)), + get_dest_y(RFIFOP(50))); break; // NPC dialog @@ -47,6 +47,7 @@ #define LOCK 254 #define IDLE 255 +#define DIR_NONE -1 #define SOUTH 0 #define SW 1 #define WEST 2 diff --git a/src/gui/chat.cpp b/src/gui/chat.cpp index b7051a3b..fac868c5 100644 --- a/src/gui/chat.cpp +++ b/src/gui/chat.cpp @@ -69,15 +69,15 @@ void ChatWindow::chat_log(std::string line, int own) pos = 0; pos = (int)line.find(" : ", 0); if (pos > 0) { - tmp.nick = line.substr(0,pos); + tmp.nick = line.substr(0, pos); switch (own) { - case ACT_IS : + case ACT_IS: tmp.nick += CAT_IS; break; - case ACT_WHISPER : + case ACT_WHISPER: tmp.nick += CAT_WHISPER; break; - default : + default: tmp.nick += CAT_NORMAL; } line.erase(0, pos + 3); @@ -85,7 +85,7 @@ void ChatWindow::chat_log(std::string line, int own) tmp.nick = ""; } tmp.own = own; - + // A try to get text sentences no too long... bool finished = false; unsigned int maxLength = 80; @@ -94,7 +94,7 @@ void ChatWindow::chat_log(std::string line, int own) { std::string tempText; if (line.length() > maxLength) - { + { tempText = line; if (line.length() > maxLength) @@ -108,7 +108,7 @@ void ChatWindow::chat_log(std::string line, int own) chatlog.push_front(tmp); } else // Normal message - { + { tmp.text = line; //chatlog_file << tmp.nick << tmp.text << "\n"; //chatlog_file.flush(); diff --git a/src/gui/chat.h b/src/gui/chat.h index ad3d5e39..4aabe4c2 100644 --- a/src/gui/chat.h +++ b/src/gui/chat.h @@ -136,14 +136,14 @@ class ChatWindow : public Window, public gcn::ActionListener { * Request focus. */ void requestFocus(); - + /** - * Checks wether ChatWindow is Focused or not + * Checks whether ChatWindow is Focused or not. */ bool isFocused(); - + /* - * Determines wether to send a command or an ordinary message, then + * Determines whether to send a command or an ordinary message, then * contructs packets & sends them * * @param nick The character's name to display in front. diff --git a/src/gui/gui.cpp b/src/gui/gui.cpp index 6a57f214..d9ab90bd 100644 --- a/src/gui/gui.cpp +++ b/src/gui/gui.cpp @@ -34,7 +34,8 @@ Graphics *guiGraphics; // Graphics driver gcn::SDLInput *guiInput; // GUI input WindowContainer *guiTop; // The top container -Gui::Gui(Graphics *graphics) +Gui::Gui(Graphics *graphics): + hostImageLoader(NULL) { // Set graphics guiGraphics = graphics; @@ -75,9 +76,9 @@ Gui::~Gui() delete guiFont; delete guiTop; delete imageLoader; -#ifdef USE_OPENGL - delete hostImageLoader; -#endif + if (hostImageLoader) { + delete hostImageLoader; + } delete guiInput; } @@ -108,9 +109,7 @@ void Gui::mousePress(int mx, int my, int button) if (state == GAME && tiledMap->getWalk(tilex, tiley)) { walk(tilex, tiley, 0); - player_node->setPath(tiledMap->findPath( - player_node->x, player_node->y, - tilex, tiley)); + player_node->setDestination(tilex, tiley); } } } diff --git a/src/gui/window.h b/src/gui/window.h index f2f87cc0..4a0f08c3 100644 --- a/src/gui/window.h +++ b/src/gui/window.h @@ -163,7 +163,7 @@ class Window : public gcn::Window, public ConfigListener Window *getParentWindow(); /** - * Returns wether this window is modal. This doesn't necessarily mean + * Returns whether this window is modal. This doesn't necessarily mean * that is gets input as a child modal window could get it. */ bool isModal(); diff --git a/src/main.cpp b/src/main.cpp index 5c62700f..0037e4f4 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -66,6 +66,7 @@ char map_name[16]; unsigned char state; unsigned char screen_mode; char *dir = NULL; +char *homeDir = NULL; int displayFlags, screenW, screenH, bitDepth; bool useOpenGL = false; @@ -120,11 +121,15 @@ void init_engine() dir = new char[400]; strcpy(dir, ""); + homeDir = new char[256]; #ifndef __USE_UNIX98 // WIN32 and others strcpy(dir, "config.xml"); + + // In Windows and other systems we currently store data next to executable. + strcpy(homeDir, ""); #else - // UNIX + // In UNIX we store data in ~/.manaworld/ char *userHome; char *name = getlogin(); passwd *pass; @@ -152,6 +157,8 @@ void init_engine() exit(1); } sprintf(dir, "%s/.manaworld/config.xml", userHome); + + //strcpy(homeDir, "%s/.manaworld/", userHome); #endif // Checking if the configuration file exists... otherwise creates it with @@ -177,18 +184,9 @@ void init_engine() config.setValue("screen", 0); config.setValue("sound", 1); config.setValue("guialpha", 0.8f); -#ifdef __USE_UNIX98 - char *chatlogFilename = new char[400]; - sprintf(chatlogFilename, "%s/.manaworld/chatlog.txt", userHome); - config.setValue("chatlog", chatlogFilename); - delete chatlogFilename; -#else - config.setValue("chatlog", "chatlog.txt"); -#endif config.setValue("remember", 1); config.setValue("sfxVolume", 100); config.setValue("musicVolume", 60); - config.write(dir); } } diff --git a/src/map.cpp b/src/map.cpp index df9aafc5..a658d8c6 100644 --- a/src/map.cpp +++ b/src/map.cpp @@ -222,27 +222,32 @@ void Map::setWalk(int x, int y, bool walkable) bool Map::getWalk(int x, int y) { - // You can't walk outside of the map - if (x < 0 || y < 0 || x >= width || y >= height) { - return false; - } - - // Check if the tile is walkable - bool ret = metaTiles[x + y * width].walkable; - // If walkable, check for colliding into a being - if (ret) { + if (!tileCollides(x, y)) { std::list<Being*>::iterator i = beings.begin(); - while (i != beings.end() && ret) { + while (i != beings.end()) { Being *being = (*i); if (being->x == x && being->y == y) { return false; } i++; } + return true; + } + else { + return false; + } +} + +bool Map::tileCollides(int x, int y) +{ + // You can't walk outside of the map + if (x < 0 || y < 0 || x >= width || y >= height) { + return true; } - return ret; + // Check if the tile is walkable + return !metaTiles[x + y * width].walkable; } void Map::setTile(int x, int y, int layer, Image *img) @@ -405,7 +410,7 @@ std::list<PATH_NODE> Map::findPath( } } - // Two new values to indicate wether a tile is on the open or closed list, + // Two new values to indicate whether a tile is on the open or closed list, // this way we don't have to clear all the values between each pathfinding. onClosedList += 2; onOpenList += 2; @@ -129,11 +129,16 @@ class Map void setWalk(int x, int y, bool walkable); /** - * Tell if a tile is walkable or not + * Tell if a tile is walkable or not, includes checking beings. */ bool getWalk(int x, int y); /** + * Tell if a tile collides, not including a check on beings. + */ + bool tileCollides(int x, int y); + + /** * Returns the width of this map. */ int getWidth(); diff --git a/src/net/protocol.h b/src/net/protocol.h index ea746412..9a755e63 100644 --- a/src/net/protocol.h +++ b/src/net/protocol.h @@ -32,6 +32,9 @@ #define SMSG_PLAYER_UPDATE_2 0x01d9 // #define SMSG_MOVE_PLAYER_BEING 0x01da // A nearby player moves #define SMSG_CHANGE_BEING_LOOKS 0x00c3 // +#define SMSG_BEING_CHAT 0x008d // A being talks +#define SMSG_MY_BEING_CHAT 0x008e // My being talks +#define SMSG_GM_CHAT 0x009a // GM announce /** Packet length by id */ diff --git a/src/resources/resourcemanager.cpp b/src/resources/resourcemanager.cpp index b26aeb5d..8606816e 100644 --- a/src/resources/resourcemanager.cpp +++ b/src/resources/resourcemanager.cpp @@ -286,16 +286,19 @@ void *ResourceManager::loadFile(const std::string &fileName, int &fileSize) PHYSFS_file* file = PHYSFS_openRead(fileName.c_str()); // If the handler is an invalid pointer indicate failure - if (file == NULL) return NULL; + if (file == NULL) { + logger.log("Warning: %s failed to load!", fileName.c_str()); + return NULL; + } - // Print file information message + // Get the size of the file fileSize = PHYSFS_fileLength(file); - // Allocate memory in the buffer and load the file + // Allocate memory and load the file void *buffer = malloc(fileSize); PHYSFS_read(file, buffer, 1, fileSize); - // Close the file and let the user deallocate the memory (safe?) + // Close the file and let the user deallocate the memory PHYSFS_close(file); return buffer; diff --git a/src/resources/resourcemanager.h b/src/resources/resourcemanager.h index d8f4cb90..3c72eb43 100644 --- a/src/resources/resourcemanager.h +++ b/src/resources/resourcemanager.h @@ -88,13 +88,36 @@ class ResourceManager int flags = 0); /** - * Convenience wrappers around ResourceManager::create. + * Convenience wrapper around ResourceManager::create for loading + * images. */ Image *getImage(const std::string &idPath, int flags = 0); + + /** + * Convenience wrapper around ResourceManager::create for loading + * songs. + */ Music *getMusic(const std::string &idPath); + + /** + * Convenience wrapper around ResourceManager::create for loading + * samples. + */ SoundEffect *getSoundEffect(const std::string &idPath); /** + * Allocates data into a buffer pointer for raw data loading. The + * returned data is expected to be freed using <code>free()</code>. + * + * @param fileName The name of the file to be loaded. + * @param fileSize The size of the file that was loaded. + * + * @return An allocated byte array containing the data that was loaded, + * or <code>NULL</code> on fail. + */ + void *loadFile(const std::string &fileName, int &fileSize); + + /** * Returns an instance of the class, creating one if it does not * already exist. */ @@ -111,16 +134,6 @@ class ResourceManager */ void searchAndAddZipFiles(); - /** - * Allocates data into a buffer pointer for raw data loading - * - * @param fileName The name of the file to be loaded - * @param buffer The empty buffer into which the data will be loaded - * - * @return The size of the file that was loaded - */ - void *loadFile(const std::string &fileName, int &fileSize); - static ResourceManager *instance; std::map<std::string, ResourceEntry> resources; diff --git a/src/sound.cpp b/src/sound.cpp index 9b16a063..332fc3a2 100644 --- a/src/sound.cpp +++ b/src/sound.cpp @@ -42,31 +42,31 @@ void Sound::init() { // Don't initialize sound engine twice if (installed) return; - + logger.log("Sound::init() Initializing sound..."); - + if (SDL_InitSubSystem(SDL_INIT_AUDIO) == -1) { logger.log("Sound::init() Failed to initialize audio subsystem"); return; } - const size_t audioBuffer = 4096; + const size_t audioBuffer = 4096; - const int res = Mix_OpenAudio(MIX_DEFAULT_FREQUENCY, MIX_DEFAULT_FORMAT, + const int res = Mix_OpenAudio(MIX_DEFAULT_FREQUENCY, MIX_DEFAULT_FORMAT, 2, audioBuffer); - if (res >= 0) { - Mix_AllocateChannels(16); - } else { - logger.log("Sound::init Could not initialize audio: %s", + if (res >= 0) { + Mix_AllocateChannels(16); + } else { + logger.log("Sound::init Could not initialize audio: %s", Mix_GetError()); return; - } - - info(); + } + + info(); music = NULL; - - installed = true; + + installed = true; } void Sound::info() { @@ -77,12 +77,12 @@ void Sound::info() { int rate = 0; Uint16 audioFormat = 0; int channels = 0; - + MIX_VERSION(&compiledVersion); linkedVersion = Mix_Linked_Version(); - + SDL_AudioDriverName(driver, 40); - + Mix_QuerySpec(&rate, &audioFormat, &channels); switch (audioFormat) { case AUDIO_U8: format = "U8"; break; @@ -92,7 +92,7 @@ void Sound::info() { case AUDIO_U16MSB: format = "U16MSB"; break; case AUDIO_S16MSB: format = "S16MSB"; break; } - + logger.log("Sound::info() SDL_mixer: %i.%i.%i (compiled)", compiledVersion.major, compiledVersion.minor, @@ -110,7 +110,7 @@ void Sound::info() { void Sound::setMusicVolume(int volume) { if (!installed) return; - + musicVolume = volume; Mix_VolumeMusic(volume); } @@ -118,7 +118,7 @@ void Sound::setMusicVolume(int volume) void Sound::setSfxVolume(int volume) { if (!installed) return; - + sfxVolume = volume; Mix_Volume(-1, volume); } @@ -126,11 +126,11 @@ void Sound::setSfxVolume(int volume) void Sound::playMusic(const char *path, int loop) { if (!installed) return; - + if (music != NULL) { stopMusic(); } - + logger.log("Sound::startMusic() Playing \"%s\" %i times", path, loop); music = Mix_LoadMUS(path); @@ -147,7 +147,7 @@ void Sound::stopMusic() if (!installed) return; logger.log("Sound::stopMusic()"); - + if (music != NULL) { Mix_HaltMusic(); Mix_FreeMusic(music); diff --git a/src/sound.h b/src/sound.h index 27748fb6..401a90f4 100644 --- a/src/sound.h +++ b/src/sound.h @@ -50,7 +50,7 @@ class Sound { * Installs the sound engine. */ void init(); - + /** * Logs various info about sound device. */ @@ -73,7 +73,7 @@ class Sound { * Stops currently running background music track. */ void stopMusic(); - + /** * Fades in background music. * @@ -89,7 +89,7 @@ class Sound { * \param ms Duration of fade-out effect (ms) */ void fadeOutMusic(int ms); - + /** * Sets music volume. * @@ -110,11 +110,12 @@ class Sound { * \param path Full path to file */ void playSfx(const char *path); - + private: bool installed; - int musicVolume, sfxVolume; + int sfxVolume; + int musicVolume; Mix_Music *music; }; |