Core/Guilds: guild code was completely refactored and rewritten.

* OOP desing and implementation;
* all the queries are moved to prepared statements;
* guild loading is optimized;
* all the possible interaction with guild's data is done inside the guild class;
* added more hooks to GuildScript class;

WARNING: Make sure you backup your characters database before applying this change (just in case).

Known problems with guilds:
* when new member is added to the guild, MOTD is not displayed for him in guild tab of social window;
* if you add item with random property to guild bank visual representation of item below it becomes wrong (it displays wrong stack number);
* packets order differs from official: currently guild bank packet traffic is twice as more than on offy.

--HG--
branch : trunk
This commit is contained in:
azazel
2010-10-17 19:54:13 +06:00
parent f5911917b4
commit c0faed2251
27 changed files with 3892 additions and 3538 deletions
@@ -105,9 +105,9 @@ void Bag::SaveToDB(SQLTransaction& trans)
Item::SaveToDB(trans);
}
bool Bag::LoadFromDB(uint32 guid, uint64 owner_guid, PreparedQueryResult result, uint32 entry)
bool Bag::LoadFromDB(uint32 guid, uint64 owner_guid, Field* fields, uint32 entry)
{
if (!Item::LoadFromDB(guid, owner_guid, result, entry))
if (!Item::LoadFromDB(guid, owner_guid, fields, entry))
return false;
ItemPrototype const* itemProto = GetProto(); // checked in Item::LoadFromDB
@@ -54,7 +54,7 @@ class Bag : public Item
// overwrite virtual Item::SaveToDB
void SaveToDB(SQLTransaction& trans);
// overwrite virtual Item::LoadFromDB
bool LoadFromDB(uint32 guid, uint64 owner_guid, PreparedQueryResult result, uint32 entry);
bool LoadFromDB(uint32 guid, uint64 owner_guid, Field* fields, uint32 entry);
// overwrite virtual Item::DeleteFromDB
void DeleteFromDB(SQLTransaction& trans);
+1 -9
View File
@@ -383,7 +383,7 @@ void Item::SaveToDB(SQLTransaction& trans)
SetState(ITEM_UNCHANGED);
}
bool Item::LoadFromDB(uint32 guid, uint64 owner_guid, PreparedQueryResult result, uint32 entry)
bool Item::LoadFromDB(uint32 guid, uint64 owner_guid, Field* fields, uint32 entry)
{
// 0 1 2 3 4 5 6 7 8 9 10
//result = CharacterDatabase.PQuery("SELECT creatorGuid, giftCreatorGuid, count, duration, charges, flags, enchantments, randomPropertyId, durability, playedTime, text FROM item_instance WHERE guid = '%u'", guid);
@@ -400,14 +400,6 @@ bool Item::LoadFromDB(uint32 guid, uint64 owner_guid, PreparedQueryResult result
if (!proto)
return false;
if (!result)
{
sLog.outError("Item (GUID: %u owner: %u) not found in table `item_instance`, can't load. ", guid, GUID_LOPART(owner_guid));
return false;
}
Field* fields = result->Fetch();
// set owner (not if item is only loaded for gbank/auction/mail
if (owner_guid != 0)
SetOwnerGUID(owner_guid);
+1 -1
View File
@@ -245,7 +245,7 @@ class Item : public Object
bool IsBindedNotWith(Player const* player) const;
bool IsBoundByEnchant() const;
virtual void SaveToDB(SQLTransaction& trans);
virtual bool LoadFromDB(uint32 guid, uint64 owner_guid, PreparedQueryResult result, uint32 entry);
virtual bool LoadFromDB(uint32 guid, uint64 owner_guid, Field* fields, uint32 entry);
virtual void DeleteFromDB(SQLTransaction& trans);
void DeleteFromInventoryDB(SQLTransaction& trans);
void SaveRefundDataToDB();
+11 -30
View File
@@ -4458,8 +4458,8 @@ void Player::DeleteFromDB(uint64 playerguid, uint32 accountId, bool updateRealmC
sObjectAccessor.ConvertCorpseForPlayer(playerguid);
if (uint32 guildId = GetGuildIdFromDB(playerguid))
if (Guild* guild = sObjectMgr.GetGuildById(guildId))
guild->DelMember(guid);
if (Guild* pGuild = sObjectMgr.GetGuildById(guildId))
pGuild->DeleteMember(guid);
// remove from arena teams
LeaveAllArenaTeams(playerguid);
@@ -4522,8 +4522,9 @@ void Player::DeleteFromDB(uint64 playerguid, uint32 accountId, bool updateRealmC
{
do
{
uint32 item_guidlow = (*resultItems)[11].GetUInt32();
uint32 item_template = (*resultItems)[12].GetUInt32();
Field* fields = resultItems->Fetch();
uint32 item_guidlow = fields[11].GetUInt32();
uint32 item_template = fields[12].GetUInt32();
ItemPrototype const* itemProto = sObjectMgr.GetItemPrototype(item_template);
if (!itemProto)
@@ -4535,7 +4536,7 @@ void Player::DeleteFromDB(uint64 playerguid, uint32 accountId, bool updateRealmC
}
Item *pItem = NewItemOrBag(itemProto);
if (!pItem->LoadFromDB(item_guidlow, MAKE_NEW_GUID(guid, 0, HIGHGUID_PLAYER), resultItems, item_template))
if (!pItem->LoadFromDB(item_guidlow, MAKE_NEW_GUID(guid, 0, HIGHGUID_PLAYER), fields, item_template))
{
pItem->FSetState(ITEM_REMOVED);
pItem->SaveToDB(trans); // it also deletes item object!
@@ -5117,28 +5118,8 @@ uint32 Player::DurabilityRepair(uint16 pos, bool cost, float discountMod, bool g
if (!pGuild)
return TotalCost;
if (!pGuild->HasRankRight(GetRank(), GR_RIGHT_WITHDRAW_REPAIR))
{
sLog.outStaticDebug("You do not have rights to withdraw for repairs");
if (!pGuild->HandleMemberWithdrawMoney(GetSession(), costs, true))
return TotalCost;
}
if (pGuild->GetMemberMoneyWithdrawRem(GetGUIDLow()) < costs)
{
sLog.outStaticDebug("You do not have enough money withdraw amount remaining");
return TotalCost;
}
if (pGuild->GetGuildBankMoney() < costs)
{
sLog.outStaticDebug("There is not enough money in bank");
return TotalCost;
}
//- TODO: Fix bad function call design
SQLTransaction trans = CharacterDatabase.BeginTransaction();
pGuild->MemberMoneyWithdraw(costs, GetGUIDLow(), trans);
CharacterDatabase.CommitTransaction(trans);
TotalCost = costs;
}
@@ -7004,12 +6985,12 @@ uint32 Player::GetGuildIdFromDB(uint64 guid)
return id;
}
uint32 Player::GetRankFromDB(uint64 guid)
uint8 Player::GetRankFromDB(uint64 guid)
{
QueryResult result = CharacterDatabase.PQuery("SELECT rank FROM guild_member WHERE guid='%u'", GUID_LOPART(guid));
if (result)
{
uint32 v = result->Fetch()[0].GetUInt32();
uint32 v = result->Fetch()[0].GetUInt8();
return v;
}
else
@@ -16896,7 +16877,7 @@ void Player::_LoadInventory(PreparedQueryResult result, uint32 timediff)
Item *item = NewItemOrBag(proto);
if (!item->LoadFromDB(item_guid, GetGUID(), result, item_id))
if (!item->LoadFromDB(item_guid, GetGUID(), fields, item_id))
{
sLog.outError("Player::_LoadInventory: Player %s has broken item (id: #%u) in inventory, deleted.", GetName(),item_id);
PreparedStatement* stmt = CharacterDatabase.GetPreparedStatement(CHAR_DEL_INVENTORY_ITEM);
@@ -17115,7 +17096,7 @@ void Player::_LoadMailedItems(Mail *mail)
Item *item = NewItemOrBag(proto);
if (!item->LoadFromDB(item_guid_low, MAKE_NEW_GUID(fields[13].GetUInt32(), 0, HIGHGUID_PLAYER), result, item_template))
if (!item->LoadFromDB(item_guid_low, MAKE_NEW_GUID(fields[13].GetUInt32(), 0, HIGHGUID_PLAYER), fields, item_template))
{
sLog.outError("Player::_LoadMailedItems - Item in mail (%u) doesn't exist !!!! - item guid: %u, deleted from mail", mail->messageID, item_guid_low);
CharacterDatabase.PExecute("DELETE FROM mail_items WHERE item_guid = '%u'", item_guid_low);
+3 -3
View File
@@ -1715,12 +1715,12 @@ class Player : public Unit, public GridObject<Player>
void SendUpdateToOutOfRangeGroupMembers();
void SetInGuild(uint32 GuildId) { SetUInt32Value(PLAYER_GUILDID, GuildId); }
void SetRank(uint32 rankId){ SetUInt32Value(PLAYER_GUILDRANK, rankId); }
void SetRank(uint8 rankId) { SetUInt32Value(PLAYER_GUILDRANK, rankId); }
uint8 GetRank() { return uint8(GetUInt32Value(PLAYER_GUILDRANK)); }
void SetGuildIdInvited(uint32 GuildId) { m_GuildIdInvited = GuildId; }
uint32 GetGuildId() { return GetUInt32Value(PLAYER_GUILDID); }
static uint32 GetGuildIdFromDB(uint64 guid);
uint32 GetRank(){ return GetUInt32Value(PLAYER_GUILDRANK); }
static uint32 GetRankFromDB(uint64 guid);
static uint8 GetRankFromDB(uint64 guid);
int GetGuildIdInvited() { return m_GuildIdInvited; }
static void RemovePetitionsAndSigns(uint64 guid, uint32 type);