diff options
Diffstat (limited to 'src/game/Mail.cpp')
-rw-r--r-- | src/game/Mail.cpp | 150 |
1 files changed, 0 insertions, 150 deletions
diff --git a/src/game/Mail.cpp b/src/game/Mail.cpp index c50b16104f2..e52006b9c37 100644 --- a/src/game/Mail.cpp +++ b/src/game/Mail.cpp @@ -17,7 +17,6 @@ * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ - #include "Mail.h" #include "WorldPacket.h" #include "WorldSession.h" @@ -31,7 +30,6 @@ #include "Language.h" #include "AuctionHouseBot.h" #include "DBCStores.h" - enum MailShowFlags { MAIL_SHOW_UNK0 = 0x0001, @@ -40,19 +38,16 @@ enum MailShowFlags MAIL_SHOW_UNK2 = 0x0008, // unknown, COD will be shown even without that flag MAIL_SHOW_RETURN = 0x0010, }; - void MailItem::deleteItem( bool inDB ) { if(item) { if(inDB) CharacterDatabase.PExecute("DELETE FROM item_instance WHERE guid='%u'", item->GetGUIDLow()); - delete item; item=NULL; } } - void WorldSession::HandleSendMail(WorldPacket & recv_data ) { uint64 mailbox, unk3; @@ -61,28 +56,20 @@ void WorldSession::HandleSendMail(WorldPacket & recv_data ) uint8 unk4; recv_data >> mailbox; recv_data >> receiver; - if (!GetPlayer()->GetGameObjectIfCanInteractWith(mailbox, GAMEOBJECT_TYPE_MAILBOX)) return; - recv_data >> subject; - recv_data >> body; - recv_data >> unk1; // stationery? recv_data >> unk2; // 0x00000000 - MailItemsInfo mi; - uint8 items_count; recv_data >> items_count; // attached items count - if(items_count > 12) // client limit { GetPlayer()->SendMailResult(0, MAIL_SEND, MAIL_ERR_TOO_MANY_ATTACHMENTS); return; } - if(items_count) { for(uint8 i = 0; i < items_count; ++i) @@ -94,22 +81,16 @@ void WorldSession::HandleSendMail(WorldPacket & recv_data ) mi.AddItem(GUID_LOPART(item_guid), item_slot); } } - recv_data >> money >> COD; // money and cod recv_data >> unk3; // const 0 recv_data >> unk4; // const 0 - items_count = mi.size(); // this is the real size after the duplicates have been removed - if (receiver.empty()) return; - Player* pl = _player; - uint64 rc = 0; if(normalizePlayerName(receiver)) rc = objmgr.GetPlayerGUIDByName(receiver); - if (!rc) { sLog.outDetail("Player %u is sending mail to %s (GUID: not existed!) with subject %s and body %s includes %u items, %u copper and %u COD copper with unk1 = %u, unk2 = %u", @@ -117,30 +98,22 @@ void WorldSession::HandleSendMail(WorldPacket & recv_data ) pl->SendMailResult(0, MAIL_SEND, MAIL_ERR_RECIPIENT_NOT_FOUND); return; } - sLog.outDetail("Player %u is sending mail to %s (GUID: %u) with subject %s and body %s includes %u items, %u copper and %u COD copper with unk1 = %u, unk2 = %u", pl->GetGUIDLow(), receiver.c_str(), GUID_LOPART(rc), subject.c_str(), body.c_str(), items_count, money, COD, unk1, unk2); - if(pl->GetGUID() == rc) { pl->SendMailResult(0, MAIL_SEND, MAIL_ERR_CANNOT_SEND_TO_SELF); return; } - uint32 cost = items_count ? 30 * items_count : 30; // price hardcoded in client - uint32 reqmoney = cost + money; - if (pl->GetMoney() < reqmoney) { pl->SendMailResult(0, MAIL_SEND, MAIL_ERR_NOT_ENOUGH_MONEY); return; } - Player *receive = objmgr.GetPlayer(rc); - uint32 rc_team = 0; uint8 mails_count = 0; //do not allow to send to one player more than 100 mails - if(receive) { rc_team = receive->GetTeam(); @@ -169,25 +142,21 @@ void WorldSession::HandleSendMail(WorldPacket & recv_data ) pl->SendMailResult(0, MAIL_SEND, MAIL_ERR_NOT_YOUR_TEAM); return; } - uint32 rc_account = 0; if(receive) rc_account = receive->GetSession()->GetAccountId(); else rc_account = objmgr.GetPlayerAccountIdByGUID(rc); - if (items_count) { for(MailItemMap::iterator mailItemIter = mi.begin(); mailItemIter != mi.end(); ++mailItemIter) { MailItem& mailItem = mailItemIter->second; - if(!mailItem.item_guidlow) { pl->SendMailResult(0, MAIL_SEND, MAIL_ERR_MAIL_ATTACHMENT_INVALID); return; } - mailItem.item = pl->GetItemByGuid(MAKE_NEW_GUID(mailItem.item_guidlow, 0, HIGHGUID_ITEM)); // prevent sending bag with items (cheat: can be placed in bag after adding equipped empty bag to mail) if(!mailItem.item) @@ -195,25 +164,21 @@ void WorldSession::HandleSendMail(WorldPacket & recv_data ) pl->SendMailResult(0, MAIL_SEND, MAIL_ERR_MAIL_ATTACHMENT_INVALID); return; } - if(!mailItem.item->CanBeTraded(true)) { pl->SendMailResult(0, MAIL_SEND, MAIL_ERR_EQUIP_ERROR, EQUIP_ERR_MAIL_BOUND_ITEM); return; } - if(mailItem.item->IsBoundAccountWide() && mailItem.item->IsSoulBound() && pl->GetSession()->GetAccountId() != rc_account) { pl->SendMailResult(0, MAIL_SEND, MAIL_ERR_EQUIP_ERROR, EQUIP_ERR_ARTEFACTS_ONLY_FOR_OWN_CHARACTERS); return; } - if (mailItem.item->HasFlag(ITEM_FIELD_FLAGS, ITEM_FLAGS_CONJURED) || mailItem.item->GetUInt32Value(ITEM_FIELD_DURATION)) { pl->SendMailResult(0, MAIL_SEND, MAIL_ERR_EQUIP_ERROR, EQUIP_ERR_MAIL_BOUND_ITEM); return; } - if(COD && mailItem.item->HasFlag(ITEM_FIELD_FLAGS, ITEM_FLAGS_WRAPPED)) { pl->SendMailResult(0, MAIL_SEND, MAIL_ERR_CANT_SEND_WRAPPED_COD); @@ -222,18 +187,14 @@ void WorldSession::HandleSendMail(WorldPacket & recv_data ) } } pl->SendMailResult(0, MAIL_SEND, MAIL_OK); - uint32 itemTextId = 0; if (!body.empty()) { itemTextId = objmgr.CreateItemText( body ); } - pl->ModifyMoney( -int32(reqmoney) ); pl->GetAchievementMgr().UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_GOLD_SPENT_FOR_MAIL, cost); - bool needItemDelay = false; - if(items_count > 0 || money > 0) { if (items_count > 0) @@ -243,15 +204,12 @@ void WorldSession::HandleSendMail(WorldPacket & recv_data ) MailItem& mailItem = mailItemIter->second; if(!mailItem.item) continue; - mailItem.item_template = mailItem.item ? mailItem.item->GetEntry() : 0; - if( GetSecurity() > SEC_PLAYER && sWorld.getConfig(CONFIG_GM_LOG_TRADE) ) { sLog.outCommand(GetAccountId(), "GM %s (Account: %u) mail item: %s (Entry: %u Count: %u) to player: %s (Account: %u)", GetPlayerName(), GetAccountId(), mailItem.item->GetProto()->Name1, mailItem.item->GetEntry(), mailItem.item->GetCount(), receiver.c_str(), rc_account); } - pl->MoveItemFromInventory(mailItem.item->GetBagSlot(), mailItem.item->GetSlot(), true); CharacterDatabase.BeginTransaction(); mailItem.item->DeleteFromInventoryDB(); //deletes item from character's inventory @@ -260,39 +218,31 @@ void WorldSession::HandleSendMail(WorldPacket & recv_data ) CharacterDatabase.PExecute("UPDATE item_instance SET owner_guid = '%u' WHERE guid='%u'", GUID_LOPART(rc), mailItem.item->GetGUIDLow()); CharacterDatabase.CommitTransaction(); } - // if item send to character at another account, then apply item delivery delay needItemDelay = pl->GetSession()->GetAccountId() != rc_account; } - if(money > 0 && GetSecurity() > SEC_PLAYER && sWorld.getConfig(CONFIG_GM_LOG_TRADE)) { sLog.outCommand(GetAccountId(),"GM %s (Account: %u) mail money: %u to player: %s (Account: %u)", GetPlayerName(), GetAccountId(), money, receiver.c_str(), rc_account); } } - // If theres is an item, there is a one hour delivery delay if sent to another account's character. uint32 deliver_delay = needItemDelay ? sWorld.getConfig(CONFIG_MAIL_DELIVERY_DELAY) : 0; - // will delete item or place to receiver mail list WorldSession::SendMailTo(receive, MAIL_NORMAL, MAIL_STATIONERY_NORMAL, pl->GetGUIDLow(), GUID_LOPART(rc), subject, itemTextId, &mi, money, COD, MAIL_CHECK_MASK_NONE, deliver_delay); - CharacterDatabase.BeginTransaction(); pl->SaveInventoryAndGoldToDB(); CharacterDatabase.CommitTransaction(); } - //called when mail is read void WorldSession::HandleMailMarkAsRead(WorldPacket & recv_data ) { uint64 mailbox; uint32 mailId; recv_data >> mailbox; - if (!GetPlayer()->GetGameObjectIfCanInteractWith(mailbox, GAMEOBJECT_TYPE_MAILBOX)) return; - recv_data >> mailId; Player *pl = _player; Mail *m = pl->GetMail(mailId); @@ -306,7 +256,6 @@ void WorldSession::HandleMailMarkAsRead(WorldPacket & recv_data ) m->state = MAIL_STATE_CHANGED; } } - //called when client deletes mail void WorldSession::HandleMailDelete(WorldPacket & recv_data ) { @@ -314,10 +263,8 @@ void WorldSession::HandleMailDelete(WorldPacket & recv_data ) uint32 mailId; recv_data >> mailbox; recv_data >> mailId; - if (!GetPlayer()->GetGameObjectIfCanInteractWith(mailbox, GAMEOBJECT_TYPE_MAILBOX)) return; - Mail *m = _player->GetMail(mailId); Player* pl = _player; pl->m_mailsUpdated = true; @@ -329,21 +276,17 @@ void WorldSession::HandleMailDelete(WorldPacket & recv_data ) pl->SendMailResult(mailId, MAIL_DELETED, MAIL_ERR_INTERNAL_ERROR); return; } - m->state = MAIL_STATE_DELETED; } pl->SendMailResult(mailId, MAIL_DELETED, MAIL_OK); } - void WorldSession::HandleMailReturnToSender(WorldPacket & recv_data ) { uint64 mailbox; uint32 mailId; recv_data >> mailbox; - if (!GetPlayer()->GetGameObjectIfCanInteractWith(mailbox, GAMEOBJECT_TYPE_MAILBOX)) return; - recv_data >> mailId; Player *pl = _player; Mail *m = pl->GetMail(mailId); @@ -360,9 +303,7 @@ void WorldSession::HandleMailReturnToSender(WorldPacket & recv_data ) CharacterDatabase.PExecute("DELETE FROM mail_items WHERE mail_id = '%u'", mailId); CharacterDatabase.CommitTransaction(); pl->RemoveMail(mailId); - MailItemsInfo mi; - if(m->HasItems()) { for(std::vector<MailItemInfo>::iterator itr2 = m->items.begin(); itr2 != m->items.end(); ++itr2) @@ -374,11 +315,9 @@ void WorldSession::HandleMailReturnToSender(WorldPacket & recv_data ) { //WTF? } - pl->RemoveMItem(itr2->item_guid); } } - if (m->sender == auctionbot.GetAHBplayerGUID()) { SendReturnToSender(MAIL_CREATURE, GetAccountId(), m->receiver, m->sender, m->subject, m->itemTextId, &mi, m->money, m->mailTemplateId); @@ -387,11 +326,9 @@ void WorldSession::HandleMailReturnToSender(WorldPacket & recv_data ) { SendReturnToSender(MAIL_NORMAL, GetAccountId(), m->receiver, m->sender, m->subject, m->itemTextId, &mi, m->money, m->mailTemplateId); } - delete m; //we can deallocate old mail pl->SendMailResult(mailId, MAIL_RETURNED_TO_SENDER, MAIL_OK); } - void WorldSession::SendReturnToSender(uint8 messageType, uint32 sender_acc, uint32 sender_guid, uint32 receiver_guid, const std::string& subject, uint32 itemTextId, MailItemsInfo *mi, uint32 money, uint16 mailTemplateId ) { if(messageType != MAIL_NORMAL) // return only to players @@ -399,27 +336,21 @@ void WorldSession::SendReturnToSender(uint8 messageType, uint32 sender_acc, uint mi->deleteIncludedItems(true); return; } - Player *receiver = objmgr.GetPlayer(MAKE_NEW_GUID(receiver_guid, 0, HIGHGUID_PLAYER)); - uint32 rc_account = 0; if(!receiver) rc_account = objmgr.GetPlayerAccountIdByGUID(MAKE_NEW_GUID(receiver_guid, 0, HIGHGUID_PLAYER)); - if(!receiver && !rc_account) // sender not exist { mi->deleteIncludedItems(true); return; } - // prepare mail and send in other case bool needItemDelay = false; - if(mi && !mi->empty()) { // if item send to character at another account, then apply item delivery delay needItemDelay = sender_acc != rc_account; - // set owner to new receiver (to prevent delete item with sender char deleting) CharacterDatabase.BeginTransaction(); for(MailItemMap::iterator mailItemIter = mi->begin(); mailItemIter != mi->end(); ++mailItemIter) @@ -431,14 +362,11 @@ void WorldSession::SendReturnToSender(uint8 messageType, uint32 sender_acc, uint } CharacterDatabase.CommitTransaction(); } - // If theres is an item, there is a one hour delivery delay. uint32 deliver_delay = needItemDelay ? sWorld.getConfig(CONFIG_MAIL_DELIVERY_DELAY) : 0; - // will delete item or place to receiver mail list WorldSession::SendMailTo(receiver, MAIL_NORMAL, MAIL_STATIONERY_NORMAL, sender_guid, receiver_guid, subject, itemTextId, mi, money, 0, MAIL_CHECK_MASK_RETURNED,deliver_delay,mailTemplateId); } - //called when player takes item attached in mail void WorldSession::HandleMailTakeItem(WorldPacket & recv_data ) { @@ -446,44 +374,35 @@ void WorldSession::HandleMailTakeItem(WorldPacket & recv_data ) uint32 mailId; uint32 itemId; recv_data >> mailbox; - if (!GetPlayer()->GetGameObjectIfCanInteractWith(mailbox, GAMEOBJECT_TYPE_MAILBOX)) return; - recv_data >> mailId; recv_data >> itemId; // item guid low? Player* pl = _player; - Mail* m = pl->GetMail(mailId); if(!m || m->state == MAIL_STATE_DELETED || m->deliver_time > time(NULL)) { pl->SendMailResult(mailId, MAIL_ITEM_TAKEN, MAIL_ERR_INTERNAL_ERROR); return; } - // prevent cheating with skip client money check if(pl->GetMoney() < m->COD) { pl->SendMailResult(mailId, MAIL_ITEM_TAKEN, MAIL_ERR_NOT_ENOUGH_MONEY); return; } - Item *it = pl->GetMItem(itemId); - ItemPosCountVec dest; uint8 msg = _player->CanStoreItem( NULL_BAG, NULL_SLOT, dest, it, false ); if( msg == EQUIP_ERR_OK ) { m->RemoveItem(itemId); m->removedItems.push_back(itemId); - if (m->COD > 0) //if there is COD, take COD money from player and send them to sender by mail { uint64 sender_guid = MAKE_NEW_GUID(m->sender, 0, HIGHGUID_PLAYER); Player *receive = objmgr.GetPlayer(sender_guid); - uint32 sender_accId = 0; - if( GetSecurity() > SEC_PLAYER && sWorld.getConfig(CONFIG_GM_LOG_TRADE) ) { std::string sender_name; @@ -496,7 +415,6 @@ void WorldSession::HandleMailTakeItem(WorldPacket & recv_data ) { // can be calculated early sender_accId = objmgr.GetPlayerAccountIdByGUID(sender_guid); - if(!objmgr.GetPlayerNameByGUID(sender_guid,sender_name)) sender_name = objmgr.GetTrinityStringForDBCLocale(LANG_UNKNOWN); } @@ -505,104 +423,80 @@ void WorldSession::HandleMailTakeItem(WorldPacket & recv_data ) } else if(!receive) sender_accId = objmgr.GetPlayerAccountIdByGUID(sender_guid); - // check player existence if(receive || sender_accId) { WorldSession::SendMailTo(receive, MAIL_NORMAL, MAIL_STATIONERY_NORMAL, m->receiver, m->sender, m->subject, 0, NULL, m->COD, 0, MAIL_CHECK_MASK_COD_PAYMENT); } - pl->ModifyMoney( -int32(m->COD) ); } m->COD = 0; m->state = MAIL_STATE_CHANGED; pl->m_mailsUpdated = true; pl->RemoveMItem(it->GetGUIDLow()); - uint32 count = it->GetCount(); // save counts before store and possible merge with deleting pl->MoveItemToInventory(dest,it,true); - CharacterDatabase.BeginTransaction(); pl->SaveInventoryAndGoldToDB(); pl->_SaveMail(); CharacterDatabase.CommitTransaction(); - pl->SendMailResult(mailId, MAIL_ITEM_TAKEN, MAIL_OK, 0, itemId, count); } else pl->SendMailResult(mailId, MAIL_ITEM_TAKEN, MAIL_ERR_EQUIP_ERROR, msg); } - void WorldSession::HandleMailTakeMoney(WorldPacket & recv_data ) { uint64 mailbox; uint32 mailId; recv_data >> mailbox; recv_data >> mailId; - if (!GetPlayer()->GetGameObjectIfCanInteractWith(mailbox, GAMEOBJECT_TYPE_MAILBOX)) return; - Player *pl = _player; - Mail* m = pl->GetMail(mailId); if(!m || m->state == MAIL_STATE_DELETED || m->deliver_time > time(NULL)) { pl->SendMailResult(mailId, MAIL_MONEY_TAKEN, MAIL_ERR_INTERNAL_ERROR); return; } - pl->SendMailResult(mailId, MAIL_MONEY_TAKEN, MAIL_OK); - pl->ModifyMoney(m->money); m->money = 0; m->state = MAIL_STATE_CHANGED; pl->m_mailsUpdated = true; - // save money and mail to prevent cheating CharacterDatabase.BeginTransaction(); pl->SaveGoldToDB(); pl->_SaveMail(); CharacterDatabase.CommitTransaction(); } - //called when player lists his received mails void WorldSession::HandleGetMailList(WorldPacket & recv_data ) { uint64 mailbox; recv_data >> mailbox; - if (!GetPlayer()->GetGameObjectIfCanInteractWith(mailbox, GAMEOBJECT_TYPE_MAILBOX)) return; - Player* pl = _player; - //load players mails, and mailed items if(!pl->m_mailsLoaded) pl ->_LoadMail(); - // client can't work with packets > max int16 value const uint32 maxPacketSize = 32767; - uint32 mails_count = 0; // real send to client mails amount - WorldPacket data(SMSG_MAIL_LIST_RESULT, (200)); // guess size data << uint8(0); // mail's count time_t cur_time = time(NULL); - for(PlayerMails::iterator itr = pl->GetmailBegin(); itr != pl->GetmailEnd(); ++itr) { // skip deleted or not delivered (deliver delay not expired) mails if ((*itr)->state == MAIL_STATE_DELETED || cur_time < (*itr)->deliver_time) continue; - uint8 item_count = (*itr)->items.size(); // max count is MAX_MAIL_ITEMS (12) - size_t next_mail_size = 2+4+1+8+4*8+((*itr)->subject.size()+1)+1+item_count*(1+4+4+6*3*4+4+4+1+4+4+4); - if(data.wpos()+next_mail_size > maxPacketSize) break; - uint32 show_flags = 0; if ((*itr)->messageType != MAIL_NORMAL) show_flags |= MAIL_SHOW_DELETE; @@ -610,11 +504,9 @@ void WorldSession::HandleGetMailList(WorldPacket & recv_data ) show_flags |= MAIL_SHOW_AUCTION; if ((*itr)->HasItems() && (*itr)->messageType == MAIL_NORMAL) show_flags |= MAIL_SHOW_RETURN; - data << (uint16) 0x0040; // unknown 2.3.0, different values data << (uint32) (*itr)->messageID; // Message ID data << (uint8) (*itr)->messageType; // Message Type - switch((*itr)->messageType) { case MAIL_NORMAL: // sender guid @@ -628,7 +520,6 @@ void WorldSession::HandleGetMailList(WorldPacket & recv_data ) case MAIL_ITEM: // item entry (?) sender = "Unknown", NYI break; } - data << (uint32) (*itr)->COD; // COD data << (uint32) (*itr)->itemTextId; // sure about this data << (uint32) 0; // unknown @@ -639,9 +530,7 @@ void WorldSession::HandleGetMailList(WorldPacket & recv_data ) data << (float) ((*itr)->expire_time-time(NULL))/DAY; data << (uint32) (*itr)->mailTemplateId; // mail template (MailTemplate.dbc) data << (*itr)->subject; // Subject string - once 00, when mail type = 3 - data << (uint8) item_count; // client limit is 0x10 - for(uint8 i = 0; i < item_count; ++i) { Item *item = pl->GetMItem((*itr)->items[i].item_guid); @@ -675,68 +564,51 @@ void WorldSession::HandleGetMailList(WorldPacket & recv_data ) // unknown wotlk data << (uint8) 0; } - mails_count += 1; } - data.put<uint8>(0, mails_count); // set real send mails to client SendPacket(&data); - // recalculate m_nextMailDelivereTime and unReadMails _player->UpdateNextMailTimeAndUnreads(); } - ///this function is called when client needs mail message body, or when player clicks on item which has ITEM_FIELD_ITEM_TEXT_ID > 0 void WorldSession::HandleItemTextQuery(WorldPacket & recv_data ) { uint32 itemTextId; uint32 mailId; //this value can be item id in bag, but it is also mail id uint32 unk; //maybe something like state - 0x70000000 - recv_data >> itemTextId >> mailId >> unk; - //some check needed, if player has item with guid mailId, or has mail with id mailId - sLog.outDebug("CMSG_ITEM_TEXT_QUERY itemguid: %u, mailId: %u, unk: %u", itemTextId, mailId, unk); - WorldPacket data(SMSG_ITEM_TEXT_QUERY_RESPONSE, (4+10));// guess size data << itemTextId; data << objmgr.GetItemText( itemTextId ); SendPacket(&data); } - //used when player copies mail body to his inventory void WorldSession::HandleMailCreateTextItem(WorldPacket & recv_data ) { uint64 mailbox; uint32 mailId; - recv_data >> mailbox >> mailId; - if (!GetPlayer()->GetGameObjectIfCanInteractWith(mailbox, GAMEOBJECT_TYPE_MAILBOX)) return; - Player *pl = _player; - Mail* m = pl->GetMail(mailId); if(!m || !m->itemTextId || m->state == MAIL_STATE_DELETED || m->deliver_time > time(NULL)) { pl->SendMailResult(mailId, MAIL_MADE_PERMANENT, MAIL_ERR_INTERNAL_ERROR); return; } - Item *bodyItem = new Item; // This is not bag and then can be used new Item. if(!bodyItem->Create(objmgr.GenerateLowGuid(HIGHGUID_ITEM), MAIL_BODY_ITEM_TEMPLATE, pl)) { delete bodyItem; return; } - bodyItem->SetUInt32Value( ITEM_FIELD_ITEM_TEXT_ID , m->itemTextId ); bodyItem->SetUInt32Value( ITEM_FIELD_CREATOR, m->sender); - sLog.outDetail("HandleMailCreateTextItem mailid=%u",mailId); - ItemPosCountVec dest; uint8 msg = _player->CanStoreItem( NULL_BAG, NULL_SLOT, dest, bodyItem, false ); if( msg == EQUIP_ERR_OK ) @@ -744,7 +616,6 @@ void WorldSession::HandleMailCreateTextItem(WorldPacket & recv_data ) m->itemTextId = 0; m->state = MAIL_STATE_CHANGED; pl->m_mailsUpdated = true; - pl->StoreItem(dest, bodyItem, true); //bodyItem->SetState(ITEM_NEW, pl); is set automatically pl->SendMailResult(mailId, MAIL_MADE_PERMANENT, MAIL_OK); @@ -755,20 +626,16 @@ void WorldSession::HandleMailCreateTextItem(WorldPacket & recv_data ) delete bodyItem; } } - //TODO Fix me! ... this void has probably bad condition, but good data are sent void WorldSession::HandleQueryNextMailTime(WorldPacket & /*recv_data*/ ) { WorldPacket data(MSG_QUERY_NEXT_MAIL_TIME, 8); - if(!_player->m_mailsLoaded) _player->_LoadMail(); - if( _player->unReadMails > 0 ) { data << (uint32) 0; // float data << (uint32) 0; // count - uint32 count = 0; time_t now = time(NULL); for(PlayerMails::iterator itr = _player->GetmailBegin(); itr != _player->GetmailEnd(); ++itr) @@ -777,13 +644,10 @@ void WorldSession::HandleQueryNextMailTime(WorldPacket & /*recv_data*/ ) // must be not checked yet if(m->checked & MAIL_CHECK_MASK_READ) continue; - // and already delivered if(now < m->deliver_time) continue; - data << (uint64) m->sender; // sender guid - switch(m->messageType) { case MAIL_AUCTION: @@ -798,7 +662,6 @@ void WorldSession::HandleQueryNextMailTime(WorldPacket & /*recv_data*/ ) break; } data << (uint32) 0xC6000000; // float unk, time or something - ++count; if(count == 2) // do not display more than 2 mails break; @@ -812,7 +675,6 @@ void WorldSession::HandleQueryNextMailTime(WorldPacket & /*recv_data*/ ) } SendPacket(&data); } - void WorldSession::SendMailTo(Player* receiver, uint8 messageType, uint8 stationery, uint32 sender_guidlow_or_entry, uint32 receiver_guidlow, std::string subject, uint32 itemTextId, MailItemsInfo* mi, uint32 money, uint32 COD, uint32 checked, uint32 deliver_delay, uint16 mailTemplateId) { if (receiver_guidlow == auctionbot.GetAHBplayerGUID()) @@ -824,28 +686,22 @@ void WorldSession::SendMailTo(Player* receiver, uint8 messageType, uint8 station return; } uint32 mailId = objmgr.GenerateMailID(); - time_t deliver_time = time(NULL) + deliver_delay; - //expire time if COD 3 days, if no COD 30 days, if auction sale pending 1 hour uint32 expire_delay; if(messageType == MAIL_AUCTION && !mi && !money) // auction mail without any items and money expire_delay = sWorld.getConfig(CONFIG_MAIL_DELIVERY_DELAY); else expire_delay = (COD > 0) ? 3*DAY : 30*DAY; - time_t expire_time = deliver_time + expire_delay; - if(mailTemplateId && !sMailTemplateStore.LookupEntry(mailTemplateId)) { sLog.outError( "WorldSession::SendMailTo - Mail have not existed MailTemplateId (%u), remove at send", mailTemplateId); mailTemplateId = 0; } - if(receiver) { receiver->AddNewMailDeliverTime(deliver_time); - if ( receiver->IsMailsLoaded() ) { Mail * m = new Mail; @@ -857,19 +713,15 @@ void WorldSession::SendMailTo(Player* receiver, uint8 messageType, uint8 station m->receiver = receiver->GetGUIDLow(); m->subject = subject; m->itemTextId = itemTextId; - if(mi) m->AddAllItems(*mi); - m->expire_time = expire_time; m->deliver_time = deliver_time; m->money = money; m->COD = COD; m->checked = checked; m->state = MAIL_STATE_UNCHANGED; - receiver->AddMail(m); //to insert new mail to beginning of maillist - if(mi) { for(MailItemMap::iterator mailItemIter = mi->begin(); mailItemIter != mi->end(); ++mailItemIter) @@ -885,13 +737,11 @@ void WorldSession::SendMailTo(Player* receiver, uint8 messageType, uint8 station } else if(mi) mi->deleteIncludedItems(); - CharacterDatabase.BeginTransaction(); CharacterDatabase.escape_string(subject); CharacterDatabase.PExecute("INSERT INTO mail (id,messageType,stationery,mailTemplateId,sender,receiver,subject,itemTextId,has_items,expire_time,deliver_time,money,cod,checked) " "VALUES ('%u', '%u', '%u', '%u', '%u', '%u', '%s', '%u', '%u', '" UI64FMTD "','" UI64FMTD "', '%u', '%u', '%d')", mailId, messageType, stationery, mailTemplateId, sender_guidlow_or_entry, receiver_guidlow, subject.c_str(), itemTextId, (mi && !mi->empty() ? 1 : 0), (uint64)expire_time, (uint64)deliver_time, money, COD, checked); - if(mi) { for(MailItemMap::const_iterator mailItemIter = mi->begin(); mailItemIter != mi->end(); ++mailItemIter) |