//: //Being(OBJECT_CHARACTER), //mClient(NULL), //mTransactionHandler(NULL), //mRechargePerSpecial(0), //mSpecialUpdateNeeded(false), //mDatabaseID(-1), //mHairStyle(0), //mHairColor(0), //mLevel(1), //mLevelProgress(0), //mUpdateLevelProgress(false), //mRecalculateLevel(true), //mParty(0), //mTransaction(TRANS_NONE) public Character(MessageIn msg) : base(ThingType.OBJECT_CHARACTER) { //const AttributeScope &attr = // attributeManager.getAttributeScope(CharacterScope); //LOG_DEBUG("Character creation: initialisation of " // << attr.size() << " attributes."); //for (AttributeScope::const_iterator it1 = attr.begin(), // it1_end = attr.end(); it1 != it1_end; ++it1) // mAttributes.insert(std::make_pair(it1.first, Attribute(*it1.second))); //// Get character data. //mDatabaseID = msg.readInt32(); //setName(msg.readString()); //deserializeCharacterData(*this, msg); //mOld = getPosition(); //Inventory(this).initialize(); //modifiedAllAttribute(); //setSize(16); //// Give the character some specials for testing. ////TODO: Get from quest vars and equipment //giveSpecial(1); //giveSpecial(2); //giveSpecial(3); }
public void handlePartyInvite(MessageIn msg) { string inviterName = msg.readString(); string inviteeName = msg.readString(); ChatClient inviter = getClient(inviterName); ChatClient invitee = getClient(inviteeName); if (inviter==null|| invitee==null) return; removeExpiredPartyInvites(); int maxInvitesPerTimeframe = 10; int num = mNumInvites[inviterName]; if (num >= maxInvitesPerTimeframe) { MessageOut @out=new MessageOut(Protocol.CPMSG_PARTY_REJECTED); @out.writeString(inviterName); @out.writeInt8((int)ErrorMessage.ERRMSG_LIMIT_REACHED); inviter.send(@out); return; } ++num; if (invitee.party!=null) { MessageOut @out=new MessageOut(Protocol.CPMSG_PARTY_REJECTED); @out.writeString(inviterName); @out.writeInt8((int)ErrorMessage.ERRMSG_FAILURE); inviter.send(@out); return; } mInvitations.Add(new PartyInvite(inviterName, inviteeName)); MessageOut msgout=new MessageOut(Protocol.CPMSG_PARTY_INVITED); msgout.writeString(inviterName); invitee.send(msgout); }
void handleAttack(GameClient client, MessageIn message) { //int id = message.readInt16(); //LOG_DEBUG("Character " << client.character.getPublicID() // << " attacked being " << id); //Actor *o = findActorNear(client.character, id); //if (o && o.getType() != OBJECT_NPC) //{ // Being *being = static_cast<Being*>(o); // client.character.setTarget(being); // client.character.setAction(ATTACK); //} }
void sendPost(Character c, MessageIn msg) { // send message to account server with id of sending player, // the id of receiving player, the letter receiver and contents, and attachments Logger.Write(LogLevel.Debug, "Sending GCMSG_STORE_POST."); MessageOut outmsg=new MessageOut(Protocol.GCMSG_STORE_POST); outmsg.writeInt32(c.getDatabaseID()); outmsg.writeString(msg.readString()); // name of receiver outmsg.writeString(msg.readString()); // content of letter while(msg.getUnreadLength()>0) // attachments { // write the item id and amount for each attachment outmsg.writeInt32(msg.readInt16()); outmsg.writeInt32(msg.readInt16()); } send(outmsg); }
// internal GameServer getGameServerFromMap(int); //internal void GameServerHandler::dumpStatistics(std::ostream &); /// <summary> /// Processes server messages. /// </summary> /// <param name="computer"></param> /// <param name="message"></param> protected override void processMessage(NetComputer computer, MessageIn message) { MessageOut result=new MessageOut(); GameServer server=(GameServer)(computer); switch(message.getId()) { case Protocol.GAMSG_REGISTER: { Logger.Write(LogLevel.Debug, "GAMSG_REGISTER"); // TODO: check the credentials of the game server server.address=message.readString(); server.port=message.readInt16(); string password=message.readString(); // checks the version of the remote item database with our local copy uint dbversion=(uint)message.readInt32(); Logger.Write(LogLevel.Information, "Game server uses itemsdatabase with version {0}", dbversion); Logger.Write(LogLevel.Debug, "AGMSG_REGISTER_RESPONSE"); MessageOut outmessage=new MessageOut(Protocol.AGMSG_REGISTER_RESPONSE); if(dbversion==Program.storage.getItemDatabaseVersion()) { Logger.Write(LogLevel.Debug, "Item databases between account server and gameserver are in sync"); outmessage.writeInt16((int)DataVersion.DATA_VERSION_OK); } else { Logger.Write(LogLevel.Debug, "Item database of game server has a wrong version"); outmessage.writeInt16((int)DataVersion.DATA_VERSION_OUTDATED); } if(password==Configuration.getValue("net_password", "changeMe")) { outmessage.writeInt16((int)Password.PASSWORD_OK); computer.send(outmessage); // transmit global world state variables Dictionary<string, string> variables; variables=Program.storage.getAllWorldStateVars(0); foreach(KeyValuePair<string, string> pair in variables) { outmessage.writeString(pair.Key); outmessage.writeString(pair.Value); } } else { Logger.Write(LogLevel.Information, "The password given by {0}:{1} was bad.", server.address, server.port); outmessage.writeInt16((int)Password.PASSWORD_BAD); computer.disconnect(outmessage); break; } Logger.Write(LogLevel.Information, "Game server {0}:{1} wants to register {2} maps.", server.address, server.port, (message.getUnreadLength()/2)); while(message.getUnreadLength()!=0) { int id=message.readInt16(); Logger.Write(LogLevel.Information, "Registering map {0}.", id); GameServer s=GameServerHandler.getGameServerFromMap(id); if(s!=null) { Logger.Write(LogLevel.Error, "Server Handler: map is already registered by {0}:{1}.", s.address, s.port); } else { MessageOut tmpOutMsg=new MessageOut(Protocol.AGMSG_ACTIVE_MAP); // Map variables tmpOutMsg.writeInt16(id); Dictionary<string, string> variables; variables=Program.storage.getAllWorldStateVars(id); // Map vars number tmpOutMsg.writeInt16(variables.Count); foreach(KeyValuePair<string, string> pair in variables) { tmpOutMsg.writeString(pair.Key); tmpOutMsg.writeString(pair.Value); } // Persistent Floor Items List<FloorItem> items=Program.storage.getFloorItemsFromMap(id); tmpOutMsg.writeInt16(items.Count); //number of floor items // Send each map item: item_id, amount, pos_x, pos_y foreach(FloorItem i in items) { tmpOutMsg.writeInt32(i.getItemId()); tmpOutMsg.writeInt16(i.getItemAmount()); tmpOutMsg.writeInt16(i.getPosX()); tmpOutMsg.writeInt16(i.getPosY()); } computer.send(tmpOutMsg); //MapStatistics m=server.maps[(ushort)id]; //Auskommentiert da nicht klar ist wo dieser Wert gesetzt wird //m.nbThings=0; //m.nbMonsters=0; } } } break; case Protocol.GAMSG_PLAYER_DATA: { Logger.Write(LogLevel.Debug, "GAMSG_PLAYER_DATA"); int id=message.readInt32(); try { Character ptr=Program.storage.getCharacter(id, null); CharacterData.deserializeCharacterData(ptr, message); if(!Program.storage.updateCharacter(ptr)) { Logger.Write(LogLevel.Error, "Failed to update character {0}.", id); } } catch { Logger.Write(LogLevel.Error, "Received data for non-existing character {0}.", id); } } break; case Protocol.GAMSG_PLAYER_SYNC: { Logger.Write(LogLevel.Debug, "GAMSG_PLAYER_SYNC"); GameServerHandler.syncDatabase(message); } break; case Protocol.GAMSG_REDIRECT: { Logger.Write(LogLevel.Debug, "GAMSG_REDIRECT"); int id=message.readInt32(); //string magic_token(utils::getMagicToken()); string magic_token=Various.GetUniqueID(); try { Character ptr=Program.storage.getCharacter(id, null); int mapId=ptr.getMapId(); try { GameServer s=GameServerHandler.getGameServerFromMap(mapId); GameServerHandler.registerGameClient(s, magic_token, ptr); result.writeInt16((int)Protocol.AGMSG_REDIRECT_RESPONSE); result.writeInt32(id); result.writeString(magic_token); result.writeString(s.address); result.writeInt16(s.port); } catch { Logger.Write(LogLevel.Error, "Server Change: No game server for map {0}.", mapId); } } catch { Logger.Write(LogLevel.Error, "Received data for non-existing character {0}.", id); } } break; case Protocol.GAMSG_PLAYER_RECONNECT: { Logger.Write(LogLevel.Debug, "GAMSG_PLAYER_RECONNECT"); int id=message.readInt32(); string magic_token=message.readString(); //string magic_token=message.readString(ManaServ.MAGIC_TOKEN_LENGTH); try { Character ptr=Program.storage.getCharacter(id, null); int accountID=ptr.getAccountID(); AccountClientHandler.prepareReconnect(magic_token, accountID); } catch { Logger.Write(LogLevel.Error, "Received data for non-existing character {0}.", id); } } break; case Protocol.GAMSG_GET_VAR_CHR: { int id=message.readInt32(); string name=message.readString(); string value=Program.storage.getQuestVar(id, name); result.writeInt16((Int16)Protocol.AGMSG_GET_VAR_CHR_RESPONSE); result.writeInt32(id); result.writeString(name); result.writeString(value); } break; case Protocol.GAMSG_SET_VAR_CHR: { int id=message.readInt32(); string name=message.readString(); string value=message.readString(); Program.storage.setQuestVar(id, name, value); } break; case Protocol.GAMSG_SET_VAR_WORLD: { string name=message.readString(); string value=message.readString(); // save the new value to the database Program.storage.setWorldStateVar(name, value); // relay the new value to all gameservers foreach(NetComputer client in clients) { MessageOut varUpdateMessage=new MessageOut(Protocol.AGMSG_SET_VAR_WORLD); varUpdateMessage.writeString(name); varUpdateMessage.writeString(value); client.send(varUpdateMessage); } } break; case Protocol.GAMSG_SET_VAR_MAP: { int mapid=message.readInt32(); string name=message.readString(); string value=message.readString(); Program.storage.setWorldStateVar(name, mapid, value); } break; case Protocol.GAMSG_BAN_PLAYER: { int id=message.readInt32(); int duration=message.readInt32(); Program.storage.banCharacter(id, duration); } break; case Protocol.GAMSG_CHANGE_PLAYER_LEVEL: { int id=message.readInt32(); int level=message.readInt16(); Program.storage.setPlayerLevel(id, level); } break; case Protocol.GAMSG_CHANGE_ACCOUNT_LEVEL: { int id=message.readInt32(); int level=message.readInt16(); // get the character so we can get the account id Character c=Program.storage.getCharacter(id, null); if(c!=null) { Program.storage.setAccountLevel(c.getAccountID(), level); } } break; case Protocol.GAMSG_STATISTICS: { //while (message.getUnreadLength()!=0) //{ // int mapId = message.readInt16(); // ServerStatistics::iterator i = server.maps.find(mapId); // if (i == server.maps.end()) // { // Logger.Add(LogLevel.Error, "Server {0}:{1} should not be sending statistics for map {2}.", server.address, server.port, mapId); // // Skip remaining data. // break; // } // MapStatistics m = i.second; // m.nbThings =(ushort) message.readInt16(); // m.nbMonsters=(ushort)message.readInt16(); // int nb = message.readInt16(); // m.players.resize(nb); // for (int j = 0; j < nb; ++j) // { // m.players[j] = message.readInt32(); // } //} } break; case Protocol.GCMSG_REQUEST_POST: { // Retrieve the post for user Logger.Write(LogLevel.Debug, "GCMSG_REQUEST_POST"); result.writeInt16((int)Protocol.CGMSG_POST_RESPONSE); // get the character id int characterId=message.readInt32(); // send the character id of sender result.writeInt32(characterId); // get the character based on the id Character ptr=Program.storage.getCharacter(characterId, null); if(ptr!=null) { // Invalid character Logger.Write(LogLevel.Error, "Error finding character id for post"); break; } // get the post for that character Post post=Program.postalManager.getPost(ptr); // send the post if valid if(post!=null) { for(int i=0; i<post.getNumberOfLetters(); ++i) { // get each letter, send the sender's name, // the contents and any attachments Letter letter=post.getLetter(i); result.writeString(letter.getSender().getName()); result.writeString(letter.getContents()); List<InventoryItem> items=letter.getAttachments(); for(uint j=0; j<items.Count; ++j) { result.writeInt16((int)items[(int)j].itemId); result.writeInt16((int)items[(int)j].amount); } } // clean up Program.postalManager.clearPost(ptr); } } break; case Protocol.GCMSG_STORE_POST: { //// Store the letter for the user //Logger.Add(LogLevel.Debug, "GCMSG_STORE_POST"); //result.writeInt16((int)Protocol.CGMSG_STORE_POST_RESPONSE); //// get the sender and receiver //int senderId = message.readInt32(); //string receiverName = message.readString(); //// for sending it back //result.writeInt32(senderId); //// get their characters //Character sender = Program.storage.getCharacter(senderId, null); //Character receiver=Program.storage.getCharacter(receiverName); //if (sender!=null || receiver!=null) //{ // // Invalid character // Logger.Add(LogLevel.Error, "Error finding character id for post"); // result.writeInt8(ManaServ.ERRMSG_INVALID_ARGUMENT); // break; //} //// get the letter contents //string contents = message.readString(); //List<Pair<int>> items; //while (message.getUnreadLength()!=0) //{ // items.Add(new Pair<int>(message.readInt16(), message.readInt16())); //} //// save the letter //Logger.Add(LogLevel.Debug, "Creating letter"); //Letter letter = new Letter(0, sender, receiver); //letter.addText(contents); //for (uint i = 0; i < items.Count; ++i) //{ // InventoryItem item; // item.itemId = items[i].first; // item.amount = items[i].second; // letter.addAttachment(item); //} //Program.postalManager.addLetter(letter); //result.writeInt8(ManaServ.ERRMSG_OK); } break; case Protocol.GAMSG_TRANSACTION: { Logger.Write(LogLevel.Debug, "TRANSACTION"); int id=message.readInt32(); int action=message.readInt32(); string messageS=message.readString(); Transaction trans=new Transaction(); trans.mCharacterId=(uint)id; trans.mAction=(uint)action; trans.mMessage=messageS; Program.storage.addTransaction(trans); } break; case Protocol.GCMSG_PARTY_INVITE: Program.chatHandler.handlePartyInvite(message); break; case Protocol.GAMSG_CREATE_ITEM_ON_MAP: { int mapId=message.readInt32(); int itemId=message.readInt32(); int amount=message.readInt16(); int posX=message.readInt16(); int posY=message.readInt16(); Logger.Write(LogLevel.Debug, "Gameserver create item {0} on map {1} ", itemId, mapId); Program.storage.addFloorItem(mapId, itemId, amount, posX, posY); } break; case Protocol.GAMSG_REMOVE_ITEM_ON_MAP: { int mapId=message.readInt32(); int itemId=message.readInt32(); int amount=message.readInt16(); int posX=message.readInt16(); int posY=message.readInt16(); Logger.Write(LogLevel.Debug, "Gameserver removed item {0} from map {1}", itemId, mapId); Program.storage.removeFloorItem(mapId, itemId, amount, posX, posY); } break; default: { Logger.Write(LogLevel.Warning, "ServerHandler::processMessage, Invalid message type: {0}", message.getId()); result.writeInt16((int)Protocol.XXMSG_INVALID); break; } } // return result if(result.getLength()>0) { computer.send(result); } }
// /** Sets the value of a base attribute of the character. */ // void setAttribute(unsigned int id, double value) // { mAttributes[id].base = value; } // // void setModAttribute(unsigned int id, double value) // { mAttributes[id].modified = value; } public void deserializeCharacterData(MessageIn msg) { // general character properties setAccountLevel(msg.readInt8()); setGender((BeingGender)msg.readInt8()); setHairStyle(msg.readInt8()); setHairColor(msg.readInt8()); setLevel(msg.readInt16()); setCharacterPoints(msg.readInt16()); setCorrectionPoints(msg.readInt16()); // character attributes uint attrSize=(uint)msg.readInt16(); for(uint i = 0;i < attrSize;++i) { uint id=(uint)msg.readInt16(); double @base=msg.readDouble(), mod=msg.readDouble(); setAttribute(id, @base); setModAttribute(id, mod); } // character skills int skillSize=msg.readInt16(); for(int i = 0;i < skillSize;++i) { int skill=msg.readInt16(); int level=msg.readInt32(); setExperience(skill, level); } // status effects currently affecting the character int statusSize=msg.readInt16(); for(int i = 0;i < statusSize;i++) { int status=msg.readInt16(); int time=msg.readInt16(); applyStatusEffect(status, time); } // location setMapId(msg.readInt16()); Point temporaryPoint=new Point(); temporaryPoint.x=msg.readInt16(); temporaryPoint.y=msg.readInt16(); setPosition(temporaryPoint); // kill count int killSize=msg.readInt16(); for(int i = 0;i < killSize;i++) { int monsterId=msg.readInt16(); int kills=msg.readInt32(); setKillCount(monsterId, kills); } // character specials int specialSize=msg.readInt16(); clearSpecials(); for(int i = 0;i < specialSize;i++) { giveSpecial(msg.readInt32()); } Possessions poss=getPossessions(); Dictionary< uint, EquipmentItem > equipData=new Dictionary<uint, EquipmentItem>(); int equipSlotsSize=msg.readInt16(); uint eqSlot; EquipmentItem equipItem=new EquipmentItem(); for(int j = 0;j < equipSlotsSize;++j) { eqSlot=(uint)msg.readInt16(); equipItem.itemId=(uint)msg.readInt16(); equipItem.itemInstance=(uint)msg.readInt16(); equipData.Add(eqSlot, equipItem); } poss.setEquipment(equipData); // Loads inventory - must be last because size isn't transmitted Dictionary<uint, InventoryItem > inventoryData=new Dictionary<uint, InventoryItem>(); while(msg.getUnreadLength()>0) { InventoryItem i=new InventoryItem(); int slotId=msg.readInt16(); i.itemId=(uint)msg.readInt16(); i.amount=(uint)msg.readInt16(); inventoryData.Add((uint)slotId, i); } poss.setInventory(inventoryData); }
void processMessage(MessageIn msg) { //switch (msg.getId()) //{ // case AGMSG_REGISTER_RESPONSE: // { // if (msg.readInt16() != DATA_VERSION_OK) // { // LOG_ERROR("Item database is outdated! Please update to " // "prevent inconsistencies"); // stop(); // Disconnect gracefully from account server. // // Stop gameserver to prevent inconsistencies. // exit(EXIT_DB_EXCEPTION); // } // else // { // LOG_DEBUG("Local item database is " // "in sync with account server."); // } // if (msg.readInt16() != PASSWORD_OK) // { // LOG_ERROR("This game server sent a invalid password"); // stop(); // exit(EXIT_BAD_CONFIG_PARAMETER); // } // // read world state variables // while (msg.getUnreadLength()) // { // std::string key = msg.readString(); // std::string value = msg.readString(); // if (!key.empty() && !value.empty()) // { // GameState::setVariableFromDbserver(key, value); // } // } // } break; // case AGMSG_PLAYER_ENTER: // { // std::string token = msg.readString(MAGIC_TOKEN_LENGTH); // Character *ptr = new Character(msg); // gameHandler.addPendingCharacter(token, ptr); // } break; // case AGMSG_ACTIVE_MAP: // { // int mapId = msg.readInt16(); // if (MapManager::activateMap(mapId)) // { // // Set map variables // MapComposite *m = MapManager::getMap(mapId); // int mapVarsNumber = msg.readInt16(); // for(int i = 0; i < mapVarsNumber; ++i) // { // std::string key = msg.readString(); // std::string value = msg.readString(); // if (!key.empty() && !value.empty()) // m.setVariableFromDbserver(key, value); // } // // Recreate potential persistent floor items // LOG_DEBUG("Recreate persistant items on map " << mapId); // int floorItemsNumber = msg.readInt16(); // for(int i = 0; i < floorItemsNumber; i += 4) // { // int itemId = msg.readInt32(); // int amount = msg.readInt16(); // int posX = msg.readInt16(); // int posY = msg.readInt16(); // if (ItemClass *ic = itemManager.getItem(itemId)) // { // Item *item = new Item(ic, amount); // item.setMap(m); // Point dst(posX, posY); // item.setPosition(dst); // if (!GameState::insertOrDelete(item)) // { // // The map is full. // LOG_WARN("Couldn't add floor item(s) " << itemId // << " into map " << mapId); // return; // } // } // } // } // } break; // case AGMSG_SET_VAR_WORLD: // { // std::string key = msg.readString(); // std::string value = msg.readString(); // GameState::setVariableFromDbserver(key, value); // LOG_DEBUG("Global variable \"" << key << "\" has changed to \"" // << value << "\""); // } break; // case AGMSG_REDIRECT_RESPONSE: // { // int id = msg.readInt32(); // std::string token = msg.readString(MAGIC_TOKEN_LENGTH); // std::string address = msg.readString(); // int port = msg.readInt16(); // gameHandler.completeServerChange(id, token, address, port); // } break; // case AGMSG_GET_VAR_CHR_RESPONSE: // { // int id = msg.readInt32(); // std::string name = msg.readString(); // std::string value = msg.readString(); // recoveredQuestVar(id, name, value); // } break; // case CGMSG_CHANGED_PARTY: // { // // Character DB id // int charid = msg.readInt32(); // // Party id, 0 for none // int partyid = msg.readInt32(); // gameHandler.updateCharacter(charid, partyid); // } break; // case CGMSG_POST_RESPONSE: // { // // get the character // Character *character = postMan.getCharacter(msg.readInt32()); // // check character is still valid // if (!character) // { // break; // } // std::string sender = msg.readString(); // std::string letter = msg.readString(); // postMan.gotPost(character, sender, letter); // } break; // case CGMSG_STORE_POST_RESPONSE: // { // // get character // Character *character = postMan.getCharacter(msg.readInt32()); // // check character is valid // if (!character) // { // break; // } // // TODO: Get NPC to tell character if the sending of post // // was successful or not // } break; // default: // LOG_WARN("Invalid message type"); // break; //} }
void handleWalk(GameClient client, MessageIn message) { //const int x = message.readInt16(); //const int y = message.readInt16(); //Point dst(x, y); //client.character.setDestination(dst); }
void handleNpcPostSend(GameClient client, MessageIn message) { //// add the character so that the post man knows them //postMan.addCharacter(client.character); //accountHandler.sendPost(client.character, message); }
void handleNpcBuySell(GameClient client, MessageIn message) { //BuySell *t = client.character.getBuySell(); //if (!t) // return; //const int id = message.readInt16(); //const int amount = message.readInt16(); //t.perform(id, amount); }
void handleNpc(GameClient client, MessageIn message) { //int id = message.readInt16(); //Actor *actor = findActorNear(client.character, id); //if (!actor || actor.getType() != OBJECT_NPC) //{ // sendNpcError(client, id, "Not close enough to NPC\n"); // return; //} //NPC *npc = static_cast<NPC *>(actor); //switch (message.getId()) //{ // case PGMSG_NPC_SELECT: // npc.select(client.character, message.readInt8()); // break; // case PGMSG_NPC_NUMBER: // npc.integerReceived(client.character, message.readInt32()); // break; // case PGMSG_NPC_STRING: // npc.stringReceived(client.character, message.readString()); // break; // case PGMSG_NPC_TALK: // case PGMSG_NPC_TALK_NEXT: // default: // npc.prompt(client.character, message.getId() == PGMSG_NPC_TALK); //} }
void handleMoveItem(GameClient client, MessageIn message) { //const int slot1 = message.readInt16(); //const int slot2 = message.readInt16(); //const int amount = message.readInt16(); //Inventory(client.character).move(slot1, slot2, amount); //// log transaction //std::stringstream str; //str << "User moved item " // << " from slot " << slot1 << " to slot " << slot2; //accountHandler.sendTransaction(client.character.getDatabaseID(), // TRANS_ITEM_MOVE, str.str()); }
void handleDrop(GameClient client, MessageIn message) { //const int slot = message.readInt16(); //const int amount = message.readInt16(); //Inventory inv(client.character); //if (ItemClass *ic = itemManager.getItem(inv.getItem(slot))) //{ // int nb = inv.removeFromSlot(slot, amount); // Item *item = new Item(ic, amount - nb); // item.setMap(client.character.getMap()); // item.setPosition(client.character.getPosition()); // if (!GameState::insert(item)) // { // // The map is full. Put back into inventory. // inv.insert(ic.getDatabaseID(), amount - nb); // delete item; // return; // } // Point pt = client.character.getPosition(); // // We store the item in database only when the floor items are meant // // to be persistent between two server restarts. // if (!Configuration::getValue("game_floorItemDecayTime", 0)) // { // // Create the floor item on map // accountHandler.createFloorItems(client.character.getMap().getID(), // ic.getDatabaseID(), // amount, pt.x, pt.y); // } // // log transaction // std::stringstream str; // str << "User dropped item " << ic.getDatabaseID() // << " at " << pt.x << "x" << pt.y; // accountHandler.sendTransaction(client.character.getDatabaseID(), // TRANS_ITEM_DROP, str.str()); //} }
void handleDisconnect(GameClient client, MessageIn message) { //const bool reconnectAccount = (bool) message.readInt8(); //MessageOut result(GPMSG_DISCONNECT_RESPONSE); //result.writeInt8(ERRMSG_OK); // It is, when control reaches here //if (reconnectAccount) //{ // std::string magic_token(utils::getMagicToken()); // result.writeString(magic_token, MAGIC_TOKEN_LENGTH); // // No accountserver data, the client should remember that // accountHandler.playerReconnectAccount( // client.character.getDatabaseID(), // magic_token); //} //// TODO: implement a delayed remove //GameState::remove(client.character); //accountHandler.sendCharacterData(client.character); //// Done with the character //client.character.disconnected(); //delete client.character; //client.character = 0; //client.status = CLIENT_LOGIN; //client.send(result); }
void handleDirectionChange(GameClient client, MessageIn message) { //const BeingDirection direction = (BeingDirection) message.readInt8(); //client.character.setDirection(direction); }
void handleUseItem(GameClient client, MessageIn message) { //const int slot = message.readInt16(); //Inventory inv(client.character); //if (ItemClass *ic = itemManager.getItem(inv.getItem(slot))) //{ // if (ic.hasTrigger(ITT_ACTIVATE)) // { // std::stringstream str; // str << "User activated item " << ic.getDatabaseID() // << " from slot " << slot; // accountHandler.sendTransaction(client.character.getDatabaseID(), // TRANS_ITEM_USED, str.str()); // if (ic.useTrigger(client.character, ITT_ACTIVATE)) // inv.removeFromSlot(slot, 1); // } //} }
void handleUseSpecial(GameClient client, MessageIn message) { //const int specialID = message.readInt8(); //LOG_DEBUG("Character " << client.character.getPublicID() // << " tries to use his special attack " << specialID); //client.character.useSpecial(specialID); }
void handlePartyInvite(GameClient client, MessageIn message) { //MapComposite *map = client.character.getMap(); //const int visualRange = Configuration::getValue("game_visualRange", 448); //std::string invitee = message.readString(); //if (invitee == client.character.getName()) // return; //for (CharacterIterator it(map.getWholeMapIterator()); it; ++it) //{ // if ((*it).getName() == invitee) // { // // calculate if the invitee is within the visual range // const int xInviter = client.character.getPosition().x; // const int yInviter = client.character.getPosition().y; // const int xInvitee = (*it).getPosition().x; // const int yInvitee = (*it).getPosition().y; // const int dx = std::abs(xInviter - xInvitee); // const int dy = std::abs(yInviter - yInvitee); // if (visualRange > std::max(dx, dy)) // { // MessageOut out(GCMSG_PARTY_INVITE); // out.writeString(client.character.getName()); // out.writeString(invitee); // accountHandler.send(out); // return; // } // break; // } //} //// Invitee was not found or is too far away //MessageOut out(GPMSG_PARTY_INVITE_ERROR); //out.writeString(invitee); //client.send(out); }
void processMessage(NetComputer computer, MessageIn message) { //GameClient &client = *static_cast<GameClient *>(computer); //if (client.status == CLIENT_LOGIN) //{ // if (message.getId() != PGMSG_CONNECT) // return; // std::string magic_token = message.readString(MAGIC_TOKEN_LENGTH); // client.status = CLIENT_QUEUED; // Before the addPendingClient // mTokenCollector.addPendingClient(magic_token, &client); // return; //} //else if (client.status != CLIENT_CONNECTED) //{ // return; //} //switch (message.getId()) //{ // case PGMSG_SAY: // handleSay(client, message); // break; // case PGMSG_NPC_TALK: // case PGMSG_NPC_TALK_NEXT: // case PGMSG_NPC_SELECT: // case PGMSG_NPC_NUMBER: // case PGMSG_NPC_STRING: // handleNpc(client, message); // break; // case PGMSG_PICKUP: // handlePickup(client, message); // break; // case PGMSG_USE_ITEM: // handleUseItem(client, message); // break; // case PGMSG_DROP: // handleDrop(client, message); // break; // case PGMSG_WALK: // handleWalk(client, message); // break; // case PGMSG_EQUIP: // handleEquip(client, message); // break; // case PGMSG_UNEQUIP: // handleUnequip(client, message); // break; // case PGMSG_MOVE_ITEM: // handleMoveItem(client, message); // break; // case PGMSG_ATTACK: // handleAttack(client, message); // break; // case PGMSG_USE_SPECIAL: // handleUseSpecial(client, message); // break; // case PGMSG_ACTION_CHANGE: // handleActionChange(client, message); // break; // case PGMSG_DIRECTION_CHANGE: // handleDirectionChange(client, message); // break; // case PGMSG_DISCONNECT: // handleDisconnect(client, message); // break; // case PGMSG_TRADE_REQUEST: // handleTradeRequest(client, message); // break; // case PGMSG_TRADE_CANCEL: // case PGMSG_TRADE_AGREED: // case PGMSG_TRADE_CONFIRM: // case PGMSG_TRADE_ADD_ITEM: // case PGMSG_TRADE_SET_MONEY: // handleTrade(client, message); // break; // case PGMSG_NPC_BUYSELL: // handleNpcBuySell(client, message); // break; // case PGMSG_RAISE_ATTRIBUTE: // handleRaiseAttribute(client, message); // break; // case PGMSG_LOWER_ATTRIBUTE: // handleLowerAttribute(client, message); // break; // case PGMSG_RESPAWN: // // plausibility check is done by character class // client.character.respawn(); // break; // case PGMSG_NPC_POST_SEND: // handleNpcPostSend(client, message); // break; // case PGMSG_PARTY_INVITE: // handlePartyInvite(client, message); // break; // default: // LOG_WARN("Invalid message type"); // client.send(MessageOut(XXMSG_INVALID)); // break; //} }
void handlePickup(GameClient client, MessageIn message) { //const int x = message.readInt16(); //const int y = message.readInt16(); //const Point ppos = client.character.getPosition(); //// TODO: use a less arbitrary value. //if (std::abs(x - ppos.x) + std::abs(y - ppos.y) < 48) //{ // MapComposite *map = client.character.getMap(); // Point ipos(x, y); // for (FixedActorIterator i(map.getAroundPointIterator(ipos, 0)); i; ++i) // { // Actor *o = *i; // Point opos = o.getPosition(); // if (o.getType() == OBJECT_ITEM && opos.x == x && opos.y == y) // { // Item *item = static_cast< Item * >(o); // ItemClass *ic = item.getItemClass(); // int amount = item.getAmount(); // if (!Inventory(client.character).insert(ic.getDatabaseID(), // amount)) // { // GameState::remove(item); // // We only do this when items are to be kept in memory // // between two server restart. // if (!Configuration::getValue("game_floorItemDecayTime", 0)) // { // // Remove the floor item from map // accountHandler.removeFloorItems(map.getID(), // ic.getDatabaseID(), // amount, x, y); // } // // log transaction // std::stringstream str; // str << "User picked up item " << ic.getDatabaseID() // << " at " << opos.x << "x" << opos.y; // accountHandler.sendTransaction( // client.character.getDatabaseID(), // TRANS_ITEM_PICKUP, str.str() // ); // } // break; // } // } //} }
void sendPost(Character c, MessageIn msg) { //// send message to account server with id of sending player, //// the id of receiving player, the letter receiver and contents, and attachments //LOG_DEBUG("Sending GCMSG_STORE_POST."); //MessageOut out(GCMSG_STORE_POST); //out.writeInt32(c.getDatabaseID()); //out.writeString(msg.readString()); // name of receiver //out.writeString(msg.readString()); // content of letter //while (msg.getUnreadLength()) // attachments //{ // // write the item id and amount for each attachment // out.writeInt32(msg.readInt16()); // out.writeInt32(msg.readInt16()); //} //send(out); }
void handleRaiseAttribute(GameClient client, MessageIn message) { //const int attribute = message.readInt32(); //AttribmodResponseCode retCode; //retCode = client.character.useCharacterPoint(attribute); //MessageOut result(GPMSG_RAISE_ATTRIBUTE_RESPONSE); //result.writeInt8(retCode); //result.writeInt32(attribute); //client.send(result); //if (retCode == ATTRIBMOD_OK) //{ // accountHandler.updateCharacterPoints( // client.character.getDatabaseID(), // client.character.getCharacterPoints(), // client.character.getCorrectionPoints()); // // log transaction // std::stringstream str; // str << "User increased attribute " << attribute; // accountHandler.sendTransaction(client.character.getDatabaseID(), // TRANS_ATTR_INCREASE, str.str()); //} }
bool mUpdateLevelProgress; /**< Flag raised when percent to next level changed */ #endregion Fields #region Constructors public Character(MessageIn msg) : base(ThingType.OBJECT_CHARACTER) { //mTransactionHandler(NULL), mDatabaseID=-1; mLevel=1; mRecalculateLevel=true; mTransaction=TransactionType.TRANS_NONE; mExperience=new Dictionary<int, int>(); Dictionary<int, List<AttributeInfoType>> attr=Program.attributeManager.getAttributeScope(ScopeType.CharacterScope); Logger.Write(LogLevel.Debug, "Character creation: initialisation of {0} attributes.", attr.Count); foreach(KeyValuePair<int, List<AttributeInfoType>> pair in attr) { mAttributes.Add((uint)pair.Key, new Attribute(pair.Value)); } // Get character data. mDatabaseID=msg.readInt32(); setName(msg.readString()); deserializeCharacterData(msg); mOld=getPosition(); //TODO Ermitteln was hier eigentlich passieren sollte //Inventory(this).initialize(); modifiedAllAttribute(); setSize(16); // Give the character some specials for testing. //TODO: Get from quest vars and equipment giveSpecial(1); giveSpecial(2); giveSpecial(3); }
void handleSay(GameClient client, MessageIn message) { //const std::string say = message.readString(); //if (say.empty()) // return; //if (say[0] == '@') //{ // CommandHandler::handleCommand(client.character, say); // return; //} //if (!client.character.isMuted()) //{ // GameState::sayAround(client.character, say); // std::string msg = client.character.getName() + " said " + say; // accountHandler.sendTransaction(client.character.getDatabaseID(), // TRANS_MSG_PUBLIC, msg); //} //else //{ // GameState::sayTo(client.character, NULL, // "You are not allowed to talk right now."); //} }
protected override void processMessage(MessageIn msg) { switch(msg.getId()) { case Protocol.AGMSG_REGISTER_RESPONSE: { if(msg.readInt16()!=(short)DataVersion.DATA_VERSION_OK) { Logger.Write(LogLevel.Error, "Item database is outdated! Please update to prevent inconsistencies"); stop(); //Disconnect gracefully from account server. //Stop gameserver to prevent inconsistencies. System.Environment.Exit((int)ExitValue.EXIT_DB_EXCEPTION); } else { Logger.Write(LogLevel.Debug, "Local item database is in sync with account server."); } if(msg.readInt16()!=(short)Password.PASSWORD_OK) { Logger.Write(LogLevel.Error, "This game server sent a invalid password"); stop(); System.Environment.Exit((int)ExitValue.EXIT_BAD_CONFIG_PARAMETER); } //read world state variables while(msg.getUnreadLength()>0) { string key=msg.readString(); string @value=msg.readString(); if(key!=""&&@value!="") { GameState.setVariableFromDbserver(key, @value); } } } break; case Protocol.AGMSG_PLAYER_ENTER: { string token=msg.readString(); Character ptr=new Character(msg); Program.gameHandler.addPendingCharacter(token, ptr); } break; case Protocol.AGMSG_ACTIVE_MAP: { int mapId=msg.readInt16(); if(MapManager.activateMap(mapId)) { // Set map variables MapComposite m=MapManager.getMap(mapId); int mapVarsNumber=msg.readInt16(); for(int i = 0;i < mapVarsNumber;++i) { string key=msg.readString(); string @value=msg.readString(); if(key!=""&&@value!="") { m.setVariableFromDbserver(key, @value); } } //Recreate potential persistent floor items Logger.Write(LogLevel.Debug, "Recreate persistant items on map {0}", mapId); int floorItemsNumber=msg.readInt16(); for(int i = 0;i < floorItemsNumber;i += 4) { int itemId=msg.readInt32(); int amount=msg.readInt16(); int posX=msg.readInt16(); int posY=msg.readInt16(); ItemClass ic=Program.itemManager.getItem(itemId); if(ic!=null) { Item item=new Item(ic, amount); item.setMap(m); Point dst=new Point(posX, posY); item.setPosition(dst); if(!GameState.insertOrDelete((Thing)item)) { // The map is full. Logger.Write(LogLevel.Debug, "Couldn't add floor item(s) {0} into map {1}", itemId, mapId); return; } } } } break; } case Protocol.AGMSG_SET_VAR_WORLD: { string key=msg.readString(); string @value=msg.readString(); GameState.setVariableFromDbserver(key, value); Logger.Write(LogLevel.Debug, "Global variable \"{0}\" has changed to \"{1}\"", key, @value); } break; case Protocol.AGMSG_REDIRECT_RESPONSE: { int id=msg.readInt32(); string token=msg.readString(); string address=msg.readString(); int port=msg.readInt16(); Program.gameHandler.completeServerChange(id, token, address, port); } break; case Protocol.AGMSG_GET_VAR_CHR_RESPONSE: { int id=msg.readInt32(); string name=msg.readString(); string @value=msg.readString(); Quest.recoveredQuestVar(id, name, @value); } break; case Protocol.CGMSG_CHANGED_PARTY: { // Character DB id int charid=msg.readInt32(); // Party id, 0 for none int partyid=msg.readInt32(); Program.gameHandler.updateCharacter(charid, partyid); } break; case Protocol.CGMSG_POST_RESPONSE: { // get the character Character character=Program.postMan.getCharacter(msg.readInt32()); // check character is still valid if(character==null) { break; } string sender=msg.readString(); string letter=msg.readString(); Program.postMan.gotPost(character, sender, letter); } break; case Protocol.CGMSG_STORE_POST_RESPONSE: { // get character Character character=Program.postMan.getCharacter(msg.readInt32()); // check character is valid if(character==null) { break; } //TODO: Get NPC to tell character if the sending of post //was successful or not } break; default: { Logger.Write(LogLevel.Warning, "Invalid message type"); break; } } }
void handleTrade(GameClient client, MessageIn message) { //std::stringstream str; //Trade *t = client.character.getTrading(); //if (!t) // return; //switch (message.getId()) //{ // case PGMSG_TRADE_CANCEL: // t.cancel(); // break; // case PGMSG_TRADE_CONFIRM: // t.confirm(client.character); // break; // case PGMSG_TRADE_AGREED: // t.agree(client.character); // // log transaction // accountHandler.sendTransaction(client.character.getDatabaseID(), // TRANS_TRADE_END, // "User finished trading"); // break; // case PGMSG_TRADE_SET_MONEY: // { // int money = message.readInt32(); // t.setMoney(client.character, money); // // log transaction // str << "User added " << money << " money to trade."; // accountHandler.sendTransaction(client.character.getDatabaseID(), // TRANS_TRADE_MONEY, str.str()); // } break; // case PGMSG_TRADE_ADD_ITEM: // { // int slot = message.readInt8(); // t.addItem(client.character, slot, message.readInt8()); // // log transaction // str << "User add item from slot " << slot; // accountHandler.sendTransaction(client.character.getDatabaseID(), // TRANS_TRADE_ITEM, str.str()); // } break; //} }
public static void syncDatabase(MessageIn msg) { // It is safe to perform the following updates in a transaction //dal::PerformTransaction transaction(storage.database()); while(msg.getUnreadLength()>0) { int msgType=msg.readInt8(); switch((Sync)msgType) { case Sync.SYNC_CHARACTER_POINTS: { Logger.Write(LogLevel.Debug, "received SYNC_CHARACTER_POINTS"); int charId=msg.readInt32(); int charPoints=msg.readInt32(); int corrPoints=msg.readInt32(); Program.storage.updateCharacterPoints(charId, charPoints, corrPoints); break; } case Sync.SYNC_CHARACTER_ATTRIBUTE: { Logger.Write(LogLevel.Debug, "received SYNC_CHARACTER_ATTRIBUTE"); int charId=msg.readInt32(); int attrId=msg.readInt32(); double @base=msg.readDouble(); double mod=msg.readDouble(); Program.storage.updateAttribute(charId, (uint)attrId, @base, mod); break; } case Sync.SYNC_CHARACTER_SKILL: { Logger.Write(LogLevel.Debug, "received SYNC_CHARACTER_SKILL"); int charId=msg.readInt32(); int skillId=msg.readInt8(); int skillValue=msg.readInt32(); Program.storage.updateExperience(charId, skillId, skillValue); break; } case Sync.SYNC_ONLINE_STATUS: { Logger.Write(LogLevel.Debug, "received SYNC_ONLINE_STATUS"); int charId=msg.readInt32(); bool online=(msg.readInt8()==1); Program.storage.setOnlineStatus(charId, online); break; } } } //transaction.commit(); }
void handleTradeRequest(GameClient client, MessageIn message) { //const int id = message.readInt16(); //if (Trade *t = client.character.getTrading()) // if (t.request(client.character, id)) // return; //Character *q = findCharacterNear(client.character, id); //if (!q || q.isBusy()) //{ // client.send(MessageOut(GPMSG_TRADE_CANCEL)); // return; //} //new Trade(client.character, q); //// log transaction //std::string str; //str = "User requested trade with " + q.getName(); //accountHandler.sendTransaction(client.character.getDatabaseID(), // TRANS_TRADE_REQUEST, str); }
protected virtual void processMessage(NetComputer comp, MessageIn msg) { throw new NotImplementedException("These function must be overloaded from derived class."); }
void handleUnequip(GameClient client, MessageIn message) { //const int itemInstance = message.readInt16(); //if (!Inventory(client.character).unequip(itemInstance)) //{ // MessageOut msg(GPMSG_SAY); // msg.writeInt16(0); // From the server // msg.writeString("Unable to unequip."); // client.send(msg); //} }