diff options
Diffstat (limited to 'src/net')
-rw-r--r-- | src/net/charhandler.cpp | 38 | ||||
-rw-r--r-- | src/net/charhandler.h | 60 | ||||
-rw-r--r-- | src/net/ea/charserverhandler.cpp | 137 | ||||
-rw-r--r-- | src/net/ea/charserverhandler.h | 26 | ||||
-rw-r--r-- | src/net/ea/playerhandler.cpp | 4 | ||||
-rw-r--r-- | src/net/ea/playerhandler.h | 12 | ||||
-rw-r--r-- | src/net/manaserv/beinghandler.cpp | 2 | ||||
-rw-r--r-- | src/net/manaserv/charhandler.cpp | 305 | ||||
-rw-r--r-- | src/net/manaserv/charhandler.h | 57 | ||||
-rw-r--r-- | src/net/manaserv/inventoryhandler.cpp | 6 | ||||
-rw-r--r-- | src/net/manaserv/inventoryhandler.h | 5 | ||||
-rw-r--r-- | src/net/manaserv/itemhandler.cpp | 15 | ||||
-rw-r--r-- | src/net/manaserv/loginhandler.cpp | 2 | ||||
-rw-r--r-- | src/net/manaserv/playerhandler.cpp | 4 | ||||
-rw-r--r-- | src/net/manaserv/playerhandler.h | 12 | ||||
-rw-r--r-- | src/net/playerhandler.h | 4 |
16 files changed, 364 insertions, 325 deletions
diff --git a/src/net/charhandler.cpp b/src/net/charhandler.cpp new file mode 100644 index 00000000..8cf756ba --- /dev/null +++ b/src/net/charhandler.cpp @@ -0,0 +1,38 @@ +/* + * The Mana World + * Copyright (C) 2010 The Mana World Development Team + * + * This file is part of The Mana World. + * + * 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 + * 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 "net/charhandler.h" + +#include "gui/charselectdialog.h" + +using namespace Net; + +void CharHandler::updateCharSelectDialog() +{ + if (mCharSelectDialog) + mCharSelectDialog->setCharacters(mCharacters); +} + +void CharHandler::unlockCharSelectDialog() +{ + if (mCharSelectDialog) + mCharSelectDialog->unlock(); +} diff --git a/src/net/charhandler.h b/src/net/charhandler.h index a55e8d86..dfe0882f 100644 --- a/src/net/charhandler.h +++ b/src/net/charhandler.h @@ -23,7 +23,6 @@ #define CHARHANDLER_H #include "localplayer.h" -#include "lockedarray.h" #include "logindata.h" #include <iosfwd> @@ -35,34 +34,73 @@ class LocalPlayer; namespace Net { +/** + * A structure to hold information about a character. + */ +struct Character +{ + Character() : + slot(0), + dummy(new LocalPlayer) + { + } + + ~Character() + { + delete dummy; + } + + int slot; /**< The index in the list of characters */ + LocalPlayer *dummy; /**< A dummy representing this character */ +}; + +typedef std::list<Character*> Characters; + class CharHandler { public: - virtual void setCharInfo(LockedArray<LocalPlayer*> *charInfo) = 0; - virtual void setCharSelectDialog(CharSelectDialog *window) = 0; virtual void setCharCreateDialog(CharCreateDialog *window) = 0; - virtual void getCharacters() = 0; + virtual void requestCharacters() = 0; - virtual void chooseCharacter(int slot, LocalPlayer *character) = 0; + virtual void chooseCharacter(Net::Character *character) = 0; virtual void newCharacter(const std::string &name, int slot, - bool gender, int hairstyle, int hairColor, - std::vector<int> stats) = 0; + bool gender, int hairstyle, int hairColor, + const std::vector<int> &stats) = 0; - virtual void deleteCharacter(int slot, LocalPlayer* character) = 0; + virtual void deleteCharacter(Net::Character *character) = 0; virtual void switchCharacter() = 0; - virtual unsigned int baseSprite() const = 0; + virtual int baseSprite() const = 0; - virtual unsigned int hairSprite() const = 0; + virtual int hairSprite() const = 0; - virtual unsigned int maxSprite() const = 0; + virtual int maxSprite() const = 0; virtual ~CharHandler() {} + + protected: + CharHandler(): + mSelectedCharacter(0), + mCharSelectDialog(0), + mCharCreateDialog(0) + {} + + void updateCharSelectDialog(); + void unlockCharSelectDialog(); + + /** The list of available characters. */ + Net::Characters mCharacters; + + /** The selected character. */ + Net::Character *mSelectedCharacter; + + CharSelectDialog *mCharSelectDialog; + CharCreateDialog *mCharCreateDialog; }; } // namespace Net diff --git a/src/net/ea/charserverhandler.cpp b/src/net/ea/charserverhandler.cpp index 106d0c8e..a49a55ac 100644 --- a/src/net/ea/charserverhandler.cpp +++ b/src/net/ea/charserverhandler.cpp @@ -39,6 +39,7 @@ #include "resources/colordb.h" +#include "utils/dtor.h" #include "utils/gettext.h" #include "utils/stringutils.h" @@ -49,9 +50,7 @@ namespace EAthena { extern ServerInfo charServer; extern ServerInfo mapServer; -CharServerHandler::CharServerHandler(): - mCharSelectDialog(0), - mCharCreateDialog(0) +CharServerHandler::CharServerHandler() { static const Uint16 _messages[] = { SMSG_CHAR_LOGIN, @@ -69,30 +68,32 @@ CharServerHandler::CharServerHandler(): void CharServerHandler::handleMessage(Net::MessageIn &msg) { - int count, slot; - LocalPlayer *tempPlayer; - logger->log("CharServerHandler: Packet ID: %x, Length: %d", - msg.getId(), msg.getLength()); + msg.getId(), msg.getLength()); + switch (msg.getId()) { - case SMSG_CHAR_LOGIN: - msg.skip(2); // Length word - msg.skip(20); // Unused + case SMSG_CHAR_LOGIN: + { + msg.skip(2); // Length word + msg.skip(20); // Unused - // Derive number of characters from message length - count = (msg.getLength() - 24) / 106; + // Derive number of characters from message length + const int count = (msg.getLength() - 24) / 106; - for (int i = 0; i < count; i++) - { - tempPlayer = readPlayerData(msg, slot); - mCharInfo->select(slot); - mCharInfo->setEntry(tempPlayer); - logger->log("CharServer: Player: %s (%d)", - tempPlayer->getName().c_str(), slot); - } + for (int i = 0; i < count; ++i) + { + Net::Character *character = new Net::Character; + int slot; + character->dummy = readPlayerData(msg, &slot); + character->slot = slot; + mCharacters.push_back(character); + logger->log("CharServer: Player: %s (%d)", + character->dummy->getName().c_str(), slot); + } - state = STATE_CHAR_SELECT; + state = STATE_CHAR_SELECT; + } break; case SMSG_CHAR_LOGIN_ERROR: @@ -108,81 +109,75 @@ void CharServerHandler::handleMessage(Net::MessageIn &msg) errorMessage = _("Unknown failure to select character."); break; } - mCharInfo->unlock(); + unlockCharSelectDialog(); break; case SMSG_CHAR_CREATE_SUCCEEDED: - tempPlayer = readPlayerData(msg, slot); - mCharInfo->unlock(); - mCharInfo->select(slot); - mCharInfo->setEntry(tempPlayer); - - // Close the character create dialog - if (mCharCreateDialog) { - mCharCreateDialog->success(); - mCharCreateDialog->scheduleDelete(); - mCharCreateDialog = 0; + Net::Character *character = new Net::Character; + int slot; + character->dummy = readPlayerData(msg, &slot); + character->slot = slot; + mCharacters.push_back(character); + + updateCharSelectDialog(); + + // Close the character create dialog + if (mCharCreateDialog) + { + mCharCreateDialog->scheduleDelete(); + mCharCreateDialog = 0; + } } break; case SMSG_CHAR_CREATE_FAILED: new OkDialog(_("Error"), _("Failed to create character. Most " "likely the name is already taken.")); - if (mCharCreateDialog) mCharCreateDialog->unlock(); break; case SMSG_CHAR_DELETE_SUCCEEDED: - tempPlayer = mCharInfo->getEntry(); - mCharInfo->setEntry(0); - mCharInfo->unlock(); - if (mCharSelectDialog) - mCharSelectDialog->update(mCharInfo->getPos()); + delete mSelectedCharacter; + mCharacters.remove(mSelectedCharacter); + mSelectedCharacter = 0; + updateCharSelectDialog(); + unlockCharSelectDialog(); new OkDialog(_("Info"), _("Character deleted.")); - delete tempPlayer; break; case SMSG_CHAR_DELETE_FAILED: - mCharInfo->unlock(); + unlockCharSelectDialog(); new OkDialog(_("Error"), _("Failed to delete character.")); break; case SMSG_CHAR_MAP_INFO: - player_node = mCharInfo->getEntry(); - slot = mCharInfo->getPos(); msg.skip(4); // CharID, must be the same as player_node->charID map_path = msg.readString(16); mapServer.hostname = ipToString(msg.readInt32()); mapServer.port = msg.readInt16(); - mCharInfo->unlock(); - mCharInfo->select(0); - // Clear unselected players infos - do - { - LocalPlayer *tmp = mCharInfo->getEntry(); - if (tmp != player_node) - { - delete tmp; - mCharInfo->setEntry(0); - } - mCharInfo->next(); - } while (mCharInfo->getPos()); - mCharInfo->select(slot); + // Prevent the selected local player from being deleted + player_node = mSelectedCharacter->dummy; + mSelectedCharacter->dummy = 0; + + delete_all(mCharacters); + mCharacters.clear(); + updateCharSelectDialog(); + mNetwork->disconnect(); state = STATE_CONNECT_GAME; break; } } -LocalPlayer *CharServerHandler::readPlayerData(Net::MessageIn &msg, int &slot) +LocalPlayer *CharServerHandler::readPlayerData(Net::MessageIn &msg, int *slot) { const Token &token = static_cast<LoginHandler*>(Net::getLoginHandler())->getToken(); - LocalPlayer *tempPlayer = new LocalPlayer(msg.readInt32(), 0, NULL); + LocalPlayer *tempPlayer = new LocalPlayer(msg.readInt32(), 0); tempPlayer->setGender(token.sex); tempPlayer->setExp(msg.readInt32()); @@ -219,7 +214,7 @@ LocalPlayer *CharServerHandler::readPlayerData(Net::MessageIn &msg, int &slot) tempPlayer->setName(msg.readString(24)); for (int i = 0; i < 6; i++) tempPlayer->setAttributeBase(i + STR, msg.readInt8(), false); - slot = msg.readInt8(); // character slot + *slot = msg.readInt8(); // character slot msg.readInt8(); // unknown return tempPlayer; @@ -228,6 +223,7 @@ LocalPlayer *CharServerHandler::readPlayerData(Net::MessageIn &msg, int &slot) void CharServerHandler::setCharSelectDialog(CharSelectDialog *window) { mCharSelectDialog = window; + updateCharSelectDialog(); } void CharServerHandler::setCharCreateDialog(CharCreateDialog *window) @@ -252,19 +248,22 @@ void CharServerHandler::setCharCreateDialog(CharCreateDialog *window) mCharCreateDialog->setFixedGender(true, token.sex); } -void CharServerHandler::getCharacters() +void CharServerHandler::requestCharacters() { connect(); } -void CharServerHandler::chooseCharacter(int slot, LocalPlayer *) +void CharServerHandler::chooseCharacter(Net::Character *character) { + mSelectedCharacter = character; + MessageOut outMsg(CMSG_CHAR_SELECT); - outMsg.writeInt8(slot); + outMsg.writeInt8(mSelectedCharacter->slot); } void CharServerHandler::newCharacter(const std::string &name, int slot, - bool gender, int hairstyle, int hairColor, std::vector<int> stats) + bool gender, int hairstyle, int hairColor, + const std::vector<int> &stats) { MessageOut outMsg(CMSG_CHAR_CREATE); outMsg.writeString(name, 24); @@ -277,10 +276,12 @@ void CharServerHandler::newCharacter(const std::string &name, int slot, outMsg.writeInt16(hairstyle); } -void CharServerHandler::deleteCharacter(int slot, LocalPlayer *character) +void CharServerHandler::deleteCharacter(Net::Character *character) { + mSelectedCharacter = character; + MessageOut outMsg(CMSG_CHAR_DELETE); - outMsg.writeInt32(character->getId()); + outMsg.writeInt32(mSelectedCharacter->dummy->getId()); outMsg.writeString("a@a.com", 40); } @@ -291,17 +292,17 @@ void CharServerHandler::switchCharacter() outMsg.writeInt8(1); } -unsigned int CharServerHandler::baseSprite() const +int CharServerHandler::baseSprite() const { return SPRITE_BASE; } -unsigned int CharServerHandler::hairSprite() const +int CharServerHandler::hairSprite() const { return SPRITE_HAIR; } -unsigned int CharServerHandler::maxSprite() const +int CharServerHandler::maxSprite() const { return SPRITE_VECTOREND; } diff --git a/src/net/ea/charserverhandler.h b/src/net/ea/charserverhandler.h index b159c63b..d96da452 100644 --- a/src/net/ea/charserverhandler.h +++ b/src/net/ea/charserverhandler.h @@ -42,9 +42,6 @@ class CharServerHandler : public MessageHandler, public Net::CharHandler virtual void handleMessage(Net::MessageIn &msg); - void setCharInfo(LockedArray<LocalPlayer*> *charInfo) - { mCharInfo = charInfo; } - void setCharSelectDialog(CharSelectDialog *window); /** @@ -54,31 +51,28 @@ class CharServerHandler : public MessageHandler, public Net::CharHandler */ void setCharCreateDialog(CharCreateDialog *window); - void getCharacters(); + void requestCharacters(); - void chooseCharacter(int slot, LocalPlayer* character); + void chooseCharacter(Net::Character *character); void newCharacter(const std::string &name, int slot, bool gender, - int hairstyle, int hairColor, std::vector<int> stats); + int hairstyle, int hairColor, + const std::vector<int> &stats); - void deleteCharacter(int slot, LocalPlayer* character); + void deleteCharacter(Net::Character *character); void switchCharacter(); - unsigned int baseSprite() const; + int baseSprite() const; - unsigned int hairSprite() const; + int hairSprite() const; - unsigned int maxSprite() const; + int maxSprite() const; void connect(); - protected: - LockedArray<LocalPlayer*> *mCharInfo; - CharSelectDialog *mCharSelectDialog; - CharCreateDialog *mCharCreateDialog; - - LocalPlayer *readPlayerData(Net::MessageIn &msg, int &slot); + private: + LocalPlayer *readPlayerData(Net::MessageIn &msg, int *slot); }; } // namespace EAthena diff --git a/src/net/ea/playerhandler.cpp b/src/net/ea/playerhandler.cpp index 34e0daf4..8de15d2b 100644 --- a/src/net/ea/playerhandler.cpp +++ b/src/net/ea/playerhandler.cpp @@ -556,7 +556,7 @@ void PlayerHandler::emote(int emoteId) outMsg.writeInt8(emoteId); } -void PlayerHandler::increaseAttribute(size_t attr) +void PlayerHandler::increaseAttribute(int attr) { if (attr >= STR && attr <= LUK) { @@ -566,7 +566,7 @@ void PlayerHandler::increaseAttribute(size_t attr) } } -void PlayerHandler::decreaseAttribute(size_t attr) +void PlayerHandler::decreaseAttribute(int attr) { // Supported by eA? } diff --git a/src/net/ea/playerhandler.h b/src/net/ea/playerhandler.h index 9e7e9ac3..bbfbc74c 100644 --- a/src/net/ea/playerhandler.h +++ b/src/net/ea/playerhandler.h @@ -37,31 +37,23 @@ class PlayerHandler : public MessageHandler, public Net::PlayerHandler void handleMessage(Net::MessageIn &msg); void attack(int id); - void emote(int emoteId); - void increaseAttribute(size_t attr); - - void decreaseAttribute(size_t attr); - + void increaseAttribute(int attr); + void decreaseAttribute(int attr); void increaseSkill(int skillId); void pickUp(FloorItem *floorItem); - void setDirection(char direction); - void setDestination(int x, int y, int direction = -1); - void changeAction(Being::Action action); void respawn(); void ignorePlayer(const std::string &player, bool ignore); - void ignoreAll(bool ignore); bool canUseMagic(); - bool canCorrectAttributes(); int getJobLocation(); diff --git a/src/net/manaserv/beinghandler.cpp b/src/net/manaserv/beinghandler.cpp index 5f9d1586..ae5bbc0e 100644 --- a/src/net/manaserv/beinghandler.cpp +++ b/src/net/manaserv/beinghandler.cpp @@ -114,7 +114,7 @@ Vector BeingHandler::giveSpeedInPixelsPerTicks(float speedInTilesPerSeconds) { speedInTicks.x = speedInTicks.y = 0; logger->log("Manaserv::BeingHandler: Speed wasn't given back" - " because game/Map not initialized."); + " because game/Map not initialized."); } // We don't use z for now. speedInTicks.z = 0; diff --git a/src/net/manaserv/charhandler.cpp b/src/net/manaserv/charhandler.cpp index 122ee10b..7a75e38d 100644 --- a/src/net/manaserv/charhandler.cpp +++ b/src/net/manaserv/charhandler.cpp @@ -41,25 +41,10 @@ #include "resources/colordb.h" +#include "utils/dtor.h" #include "utils/gettext.h" extern Net::CharHandler *charHandler; - -struct CharInfo { - unsigned char slot; - std::string name; - Gender gender; - int hs, hc; - unsigned short level; - unsigned short charPoints; - unsigned short corrPoints; - unsigned int money; - unsigned char attr[7]; -}; - -typedef std::vector<CharInfo> CharInfos; -CharInfos chars; - extern ManaServ::GameHandler *gameHandler; namespace ManaServ { @@ -71,9 +56,7 @@ extern std::string netToken; extern ServerInfo gameServer; extern ServerInfo chatServer; -CharHandler::CharHandler(): - mCharSelectDialog(0), - mCharCreateDialog(0) +CharHandler::CharHandler() { static const Uint16 _messages[] = { APMSG_CHAR_CREATE_RESPONSE, @@ -91,104 +74,54 @@ void CharHandler::handleMessage(Net::MessageIn &msg) switch (msg.getId()) { case APMSG_CHAR_CREATE_RESPONSE: - handleCharCreateResponse(msg); + handleCharacterCreateResponse(msg); break; case APMSG_CHAR_DELETE_RESPONSE: - { - int errMsg = msg.readInt8(); - // Character deletion successful - if (errMsg == ERRMSG_OK) - { - LocalPlayer *tempPlayer = mCharInfo->getEntry(); - mCharInfo->setEntry(0); - mCharInfo->unlock(); - if (mCharSelectDialog) - mCharSelectDialog->update(mCharInfo->getPos()); - new OkDialog(_("Info"), _("Player deleted.")); - delete tempPlayer; - } - // Character deletion failed - else - { - std::string errorMessage = ""; - switch (errMsg) - { - case ERRMSG_NO_LOGIN: - errorMessage = _("Not logged in."); - break; - case ERRMSG_INVALID_ARGUMENT: - errorMessage = _("Selection out of range."); - break; - default: - errorMessage = _("Unknown error."); - } - mCharInfo->unlock(); - new OkDialog(_("Error"), errorMessage); - } - } + handleCharacterDeleteResponse(msg); break; case APMSG_CHAR_INFO: - { - CharInfo info; - info.slot = msg.readInt8(); // character slot - info.name = msg.readString(); - info.gender = msg.readInt8() == GENDER_MALE ? GENDER_MALE : - GENDER_FEMALE; - info.hs = msg.readInt8(); - info.hc = msg.readInt8(); - info.level = msg.readInt16(); - info.charPoints = msg.readInt16(); - info.corrPoints = msg.readInt16(); - info.money = msg.readInt32(); - - for (int i = 0; i < 7; i++) - { - info.attr[i] = msg.readInt8(); - } - - chars.push_back(info); - - if (mCharSelectDialog) - { - mCharInfo->select(info.slot); - - LocalPlayer *tempPlayer = new LocalPlayer(); - tempPlayer->setName(info.name); - tempPlayer->setGender(info.gender); - tempPlayer->setSprite(SPRITE_HAIR, info.hs * -1, - ColorDB::get(info.hc)); - tempPlayer->setLevel(info.level); - tempPlayer->setCharacterPoints(info.charPoints); - tempPlayer->setCorrectionPoints(info.corrPoints); - tempPlayer->setMoney(info.money); - - for (int i = 0; i < 7; i++) - { - tempPlayer->setAttributeBase(i, info.attr[i], false); - } - - mCharInfo->setEntry(tempPlayer); - - mCharSelectDialog->update(info.slot); - } - } + handleCharacterInfo(msg); break; case APMSG_CHAR_SELECT_RESPONSE: - handleCharSelectResponse(msg); + handleCharacterSelectResponse(msg); break; } } -void CharHandler::handleCharCreateResponse(Net::MessageIn &msg) +void CharHandler::handleCharacterInfo(Net::MessageIn &msg) { - int errMsg = msg.readInt8(); + CachedCharacterInfo info; + info.slot = msg.readInt8(); + info.name = msg.readString(); + info.gender = msg.readInt8() == GENDER_MALE ? GENDER_MALE : + GENDER_FEMALE; + info.hairStyle = msg.readInt8(); + info.hairColor = msg.readInt8(); + info.level = msg.readInt16(); + info.characterPoints = msg.readInt16(); + info.correctionPoints = msg.readInt16(); + info.money = msg.readInt32(); + + for (int i = 0; i < 7; i++) + { + info.attribute[i] = msg.readInt8(); + } + + mCachedCharacterInfos.push_back(info); + + updateCharacters(); +} + +void CharHandler::handleCharacterCreateResponse(Net::MessageIn &msg) +{ + const int errMsg = msg.readInt8(); - // Character creation failed if (errMsg != ERRMSG_OK) { + // Character creation failed std::string errorMessage = ""; switch (errMsg) { @@ -233,17 +166,48 @@ void CharHandler::handleCharCreateResponse(Net::MessageIn &msg) } else { + // Close the character create dialog if (mCharCreateDialog) { - mCharCreateDialog->success(); mCharCreateDialog->scheduleDelete(); mCharCreateDialog = 0; } } +} +void CharHandler::handleCharacterDeleteResponse(Net::MessageIn &msg) +{ + int errMsg = msg.readInt8(); + if (errMsg == ERRMSG_OK) + { + // Character deletion successful + delete mSelectedCharacter; + mCharacters.remove(mSelectedCharacter); + updateCharSelectDialog(); + unlockCharSelectDialog(); + new OkDialog(_("Info"), _("Player deleted.")); + } + else + { + // Character deletion failed + std::string errorMessage = ""; + switch (errMsg) + { + case ERRMSG_NO_LOGIN: + errorMessage = _("Not logged in."); + break; + case ERRMSG_INVALID_ARGUMENT: + errorMessage = _("Selection out of range."); + break; + default: + errorMessage = strprintf(_("Unknown error (%d)."), errMsg); + } + new OkDialog(_("Error"), errorMessage); + } + mSelectedCharacter = 0; } -void CharHandler::handleCharSelectResponse(Net::MessageIn &msg) +void CharHandler::handleCharacterSelectResponse(Net::MessageIn &msg) { int errMsg = msg.readInt8(); @@ -265,31 +229,20 @@ void CharHandler::handleCharSelectResponse(Net::MessageIn &msg) gameServerConnection->connect(gameServer.hostname, gameServer.port); chatServerConnection->connect(chatServer.hostname, chatServer.port); - // Keep the selected character and delete the others - player_node = mCharInfo->getEntry(); - int slot = mCharInfo->getPos(); - mCharInfo->unlock(); - mCharInfo->select(0); - - do { - LocalPlayer *tmp = mCharInfo->getEntry(); - if (tmp != player_node) - { - delete tmp; - mCharInfo->setEntry(0); - } - mCharInfo->next(); - } while (mCharInfo->getPos()); - mCharInfo->select(slot); - - mCharInfo->clear(); //player_node will be deleted by ~Game + // Prevent the selected local player from being deleted + player_node = mSelectedCharacter->dummy; + mSelectedCharacter->dummy = 0; + + mCachedCharacterInfos.clear(); + updateCharacters(); state = STATE_CONNECT_GAME; } - else if(errMsg == ERRMSG_FAILURE) + else if (errMsg == ERRMSG_FAILURE) { errorMessage = _("No gameservers are available."); - mCharInfo->clear(); + delete_all(mCharacters); + mCharacters.clear(); state = STATE_ERROR; } } @@ -297,13 +250,15 @@ void CharHandler::handleCharSelectResponse(Net::MessageIn &msg) void CharHandler::setCharSelectDialog(CharSelectDialog *window) { mCharSelectDialog = window; + updateCharacters(); } void CharHandler::setCharCreateDialog(CharCreateDialog *window) { mCharCreateDialog = window; - if (!mCharCreateDialog) return; + if (!mCharCreateDialog) + return; std::vector<std::string> attributes; attributes.push_back(_("Strength:")); @@ -316,59 +271,34 @@ void CharHandler::setCharCreateDialog(CharCreateDialog *window) mCharCreateDialog->setAttributes(attributes, 60, 1, 20); } -void CharHandler::getCharacters() +void CharHandler::requestCharacters() { if (!accountServerConnection->isConnected()) + { Net::getLoginHandler()->connect(); + } else { - mCharInfo->unlock(); - LocalPlayer *tempPlayer; - for (CharInfos::const_iterator it = chars.begin(); it != chars.end(); it++) - { - const CharInfo info = (CharInfo) (*it); - mCharInfo->select(info.slot); - - tempPlayer = new LocalPlayer(); - tempPlayer->setName(info.name); - tempPlayer->setGender(info.gender); - tempPlayer->setSprite(SPRITE_HAIR, info.hs * -1, - ColorDB::get(info.hc)); - tempPlayer->setLevel(info.level); - tempPlayer->setCharacterPoints(info.charPoints); - tempPlayer->setCorrectionPoints(info.corrPoints); - tempPlayer->setMoney(info.money); - - for (int i = 0; i < 7; i++) - { - tempPlayer->setAttributeBase(i, info.attr[i], false); - } - - mCharInfo->setEntry(tempPlayer); - } - - // Close the character create dialog - if (mCharCreateDialog) - { - mCharCreateDialog->scheduleDelete(); - mCharCreateDialog = 0; - } - + // The characters are already there, continue to character selection state = STATE_CHAR_SELECT; } } -void CharHandler::chooseCharacter(int slot, LocalPlayer* character) +void CharHandler::chooseCharacter(Net::Character *character) { - MessageOut msg(PAMSG_CHAR_SELECT); - - msg.writeInt8(slot); + mSelectedCharacter = character; + MessageOut msg(PAMSG_CHAR_SELECT); + msg.writeInt8(mSelectedCharacter->slot); accountServerConnection->send(msg); } -void CharHandler::newCharacter(const std::string &name, int slot, bool gender, - int hairstyle, int hairColor, std::vector<int> stats) +void CharHandler::newCharacter(const std::string &name, + int /* slot */, + bool gender, + int hairstyle, + int hairColor, + const std::vector<int> &stats) { MessageOut msg(PAMSG_CHAR_CREATE); @@ -386,12 +316,12 @@ void CharHandler::newCharacter(const std::string &name, int slot, bool gender, accountServerConnection->send(msg); } -void CharHandler::deleteCharacter(int slot, LocalPlayer* character) +void CharHandler::deleteCharacter(Net::Character *character) { - MessageOut msg(PAMSG_CHAR_DELETE); - - msg.writeInt8(slot); + mSelectedCharacter = character; + MessageOut msg(PAMSG_CHAR_DELETE); + msg.writeInt8(mSelectedCharacter->slot); accountServerConnection->send(msg); } @@ -400,19 +330,56 @@ void CharHandler::switchCharacter() gameHandler->quit(true); } -unsigned int CharHandler::baseSprite() const +int CharHandler::baseSprite() const { return SPRITE_BASE; } -unsigned int CharHandler::hairSprite() const +int CharHandler::hairSprite() const { return SPRITE_HAIR; } -unsigned int CharHandler::maxSprite() const +int CharHandler::maxSprite() const { return SPRITE_VECTOREND; } +void CharHandler::updateCharacters() +{ + // Delete previous characters + delete_all(mCharacters); + mCharacters.clear(); + + if (!mCharSelectDialog) + return; + + // Create new characters and initialize them from the cached infos + for (unsigned i = 0; i < mCachedCharacterInfos.size(); ++i) + { + const CachedCharacterInfo &info = mCachedCharacterInfos.at(i); + + Net::Character *character = new Net::Character; + character->slot = info.slot; + LocalPlayer *player = character->dummy; + player->setName(info.name); + player->setGender(info.gender); + player->setSprite(SPRITE_HAIR, info.hairStyle * -1, + ColorDB::get(info.hairColor)); + player->setLevel(info.level); + player->setCharacterPoints(info.characterPoints); + player->setCorrectionPoints(info.correctionPoints); + player->setMoney(info.money); + + for (int i = 0; i < 7; i++) + { + player->setAttributeBase(i, info.attribute[i], false); + } + + mCharacters.push_back(character); + } + + updateCharSelectDialog(); +} + } // namespace ManaServ diff --git a/src/net/manaserv/charhandler.h b/src/net/manaserv/charhandler.h index 74f68f55..4a1af307 100644 --- a/src/net/manaserv/charhandler.h +++ b/src/net/manaserv/charhandler.h @@ -42,11 +42,6 @@ class CharHandler : public MessageHandler, public Net::CharHandler void handleMessage(Net::MessageIn &msg); - void setCharInfo(LockedArray<LocalPlayer*> *charInfo) - { - mCharInfo = charInfo; - } - void setCharSelectDialog(CharSelectDialog *window); /** @@ -56,32 +51,52 @@ class CharHandler : public MessageHandler, public Net::CharHandler */ void setCharCreateDialog(CharCreateDialog *window); - void getCharacters(); + void requestCharacters(); - void chooseCharacter(int slot, LocalPlayer* character); + void chooseCharacter(Net::Character *character); void newCharacter(const std::string &name, int slot, - bool gender, int hairstyle, int hairColor, - std::vector<int> stats); + bool gender, int hairstyle, int hairColor, + const std::vector<int> &stats); - void deleteCharacter(int slot, LocalPlayer* character); + void deleteCharacter(Net::Character *character); void switchCharacter(); - unsigned int baseSprite() const; - - unsigned int hairSprite() const; - - unsigned int maxSprite() const; + int baseSprite() const; - protected: - void handleCharCreateResponse(Net::MessageIn &msg); + int hairSprite() const; - void handleCharSelectResponse(Net::MessageIn &msg); + int maxSprite() const; - LockedArray<LocalPlayer*> *mCharInfo; - CharSelectDialog *mCharSelectDialog; - CharCreateDialog *mCharCreateDialog; + private: + /** + * Character information needs to be cached since we receive it before + * we have loaded the dynamic data, so we can't resolve load any + * sprites yet. + */ + struct CachedCharacterInfo { + int slot; + std::string name; + Gender gender; + int hairStyle; + int hairColor; + int level; + int characterPoints; + int correctionPoints; + int money; + int attribute[7]; + }; + + void handleCharacterInfo(Net::MessageIn &msg); + void handleCharacterCreateResponse(Net::MessageIn &msg); + void handleCharacterDeleteResponse(Net::MessageIn &msg); + void handleCharacterSelectResponse(Net::MessageIn &msg); + + void updateCharacters(); + + /** Cached character information */ + std::vector<CachedCharacterInfo> mCachedCharacterInfos; }; } // namespace ManaServ diff --git a/src/net/manaserv/inventoryhandler.cpp b/src/net/manaserv/inventoryhandler.cpp index 0020a4e7..3ce1aa6f 100644 --- a/src/net/manaserv/inventoryhandler.cpp +++ b/src/net/manaserv/inventoryhandler.cpp @@ -61,7 +61,7 @@ void InventoryHandler::handleMessage(Net::MessageIn &msg) { case GPMSG_INVENTORY_FULL: player_node->clearInventory(); - player_node->mEquipment->setBackend(&mEqiups); + player_node->mEquipment->setBackend(&mEquips); // no break! case GPMSG_INVENTORY: @@ -77,7 +77,7 @@ void InventoryHandler::handleMessage(Net::MessageIn &msg) int id = msg.readInt16(); if (slot < EQUIPMENT_SIZE) { - mEqiups.setEquipment(slot, id); + mEquips.setEquipment(slot, id); } else if (slot >= 32 && slot < 32 + getSize(INVENTORY)) { @@ -105,7 +105,7 @@ void InventoryHandler::unequipItem(const Item *item) // Tidy equipment directly to avoid weapon still shown bug, for instance int equipSlot = item->getInvIndex(); logger->log("Unequipping %d", equipSlot); - mEqiups.setEquipment(equipSlot, 0); + mEquips.setEquipment(equipSlot, 0); } void InventoryHandler::useItem(const Item *item) diff --git a/src/net/manaserv/inventoryhandler.h b/src/net/manaserv/inventoryhandler.h index 362e392a..402af3b5 100644 --- a/src/net/manaserv/inventoryhandler.h +++ b/src/net/manaserv/inventoryhandler.h @@ -30,7 +30,8 @@ namespace ManaServ { -class EquipBackend : public Equipment::Backend { +class EquipBackend : public Equipment::Backend +{ public: EquipBackend() { memset(mEquipment, 0, sizeof(mEquipment)); } @@ -97,7 +98,7 @@ class InventoryHandler : public MessageHandler, Net::InventoryHandler size_t getSize(StorageType type) const; private: - EquipBackend mEqiups; + EquipBackend mEquips; }; } // namespace ManaServ diff --git a/src/net/manaserv/itemhandler.cpp b/src/net/manaserv/itemhandler.cpp index 802f9303..c939589e 100644 --- a/src/net/manaserv/itemhandler.cpp +++ b/src/net/manaserv/itemhandler.cpp @@ -58,12 +58,9 @@ void ItemHandler::handleMessage(Net::MessageIn &msg) if (itemId) { - Game *game = Game::instance(); - Map *map = 0; - if (game) + if (Game *game = Game::instance()) { - map = game->getCurrentMap(); - if (map) + if (Map *map = game->getCurrentMap()) { floorItemManager->create(id, itemId, @@ -71,9 +68,11 @@ void ItemHandler::handleMessage(Net::MessageIn &msg) y / map->getTileHeight()); } else - logger->log( - "ItemHandler: An item wasn't created because of" - "Game/Map not initialized..."); + { + logger->log( + "ItemHandler: An item wasn't created " + "because of Game/Map not initialized..."); + } } } else if (FloorItem *item = floorItemManager->findById(id)) diff --git a/src/net/manaserv/loginhandler.cpp b/src/net/manaserv/loginhandler.cpp index 63195816..9d8bc0e2 100644 --- a/src/net/manaserv/loginhandler.cpp +++ b/src/net/manaserv/loginhandler.cpp @@ -64,9 +64,11 @@ void LoginHandler::handleMessage(Net::MessageIn &msg) case APMSG_LOGIN_RESPONSE: handleLoginResponse(msg); break; + case APMSG_REGISTER_RESPONSE: handleRegisterResponse(msg); break; + case APMSG_RECONNECT_RESPONSE: { int errMsg = msg.readInt8(); diff --git a/src/net/manaserv/playerhandler.cpp b/src/net/manaserv/playerhandler.cpp index bff9512e..56502ec1 100644 --- a/src/net/manaserv/playerhandler.cpp +++ b/src/net/manaserv/playerhandler.cpp @@ -306,14 +306,14 @@ void PlayerHandler::emote(int emoteId) // TODO } -void PlayerHandler::increaseAttribute(size_t attr) +void PlayerHandler::increaseAttribute(int attr) { MessageOut msg(PGMSG_RAISE_ATTRIBUTE); msg.writeInt8(attr); gameServerConnection->send(msg); } -void PlayerHandler::decreaseAttribute(size_t attr) +void PlayerHandler::decreaseAttribute(int attr) { MessageOut msg(PGMSG_LOWER_ATTRIBUTE); msg.writeInt8(attr); diff --git a/src/net/manaserv/playerhandler.h b/src/net/manaserv/playerhandler.h index 6edc96bb..65170d63 100644 --- a/src/net/manaserv/playerhandler.h +++ b/src/net/manaserv/playerhandler.h @@ -44,31 +44,23 @@ class PlayerHandler : public MessageHandler, public Net::PlayerHandler void handleMessage(Net::MessageIn &msg); void attack(int id); - void emote(int emoteId); - void increaseAttribute(size_t attr); - - void decreaseAttribute(size_t attr); - + void increaseAttribute(int attr); + void decreaseAttribute(int attr); void increaseSkill(int skillId); void pickUp(FloorItem *floorItem); - void setDirection(char direction); - void setDestination(int x, int y, int direction = -1); - void changeAction(Being::Action action); void respawn(); void ignorePlayer(const std::string &player, bool ignore); - void ignoreAll(bool ignore); bool canUseMagic(); - bool canCorrectAttributes(); int getJobLocation(); diff --git a/src/net/playerhandler.h b/src/net/playerhandler.h index 0174ede2..c2ecd2d0 100644 --- a/src/net/playerhandler.h +++ b/src/net/playerhandler.h @@ -35,9 +35,9 @@ class PlayerHandler virtual void emote(int emoteId) = 0; - virtual void increaseAttribute(size_t attr) = 0; + virtual void increaseAttribute(int attr) = 0; - virtual void decreaseAttribute(size_t attr) = 0; + virtual void decreaseAttribute(int attr) = 0; virtual void increaseSkill(int skillId) = 0; |