Core/Items: Implemented trading soulbound loot items

Core/DBLayer: Converted more more player-related queries into prepared statements
Core/Items: Fixed loading of enchantments

Closes issue #4130.

--HG--
branch : trunk
This commit is contained in:
Shauren
2010-09-21 21:55:16 +02:00
parent 5eb0fd80ac
commit d8ddf38453
18 changed files with 323 additions and 56 deletions
@@ -1338,6 +1338,8 @@ void WorldSession::HandleSocketOpcode(WorldPacket& recv_data)
}
_player->ToggleMetaGemsActive(slot, true); //turn on all metagems (except for target item)
itemTarget->SetSoulboundTradeable(NULL, _player, false); // clear tradeable flag
}
void WorldSession::HandleCancelTempEnchantmentOpcode(WorldPacket& recv_data)
@@ -473,8 +473,11 @@ void WorldSession::HandleLootMasterGiveOpcode(WorldPacket & recv_data)
return;
}
// list of players allowed to receive this item in trade
AllowedLooterSet* looters = item.GetAllowedLooters();
// not move item from loot to target inventory
Item * newitem = target->StoreNewItem(dest, item.itemid, true, item.randomPropertyId);
Item * newitem = target->StoreNewItem(dest, item.itemid, true, item.randomPropertyId, (looters->size() > 1) ? looters : NULL);
target->SendNewItem(newitem, uint32(item.count), false, false, true);
target->GetAchievementMgr().UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_LOOT_ITEM, item.itemid, item.count);
target->GetAchievementMgr().UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_LOOT_TYPE, pLoot->loot_type, item.count);
@@ -55,6 +55,7 @@ void WorldSession::SendTradeStatus(TradeStatus status)
data << uint32(0);
break;
case TRADE_STATUS_ONLY_CONJURED:
case TRADE_STATUS_NOT_ELIGIBLE:
data.Initialize(SMSG_TRADE_STATUS, 4+1);
data << uint32(status);
data << uint8(0);
@@ -162,6 +163,8 @@ void WorldSession::moveItems(Item* myItems[], Item* hisItems[])
// store
trader->MoveItemToInventory(traderDst, myItems[i], true, true);
if (myItems[i]->HasFlag(ITEM_FIELD_FLAGS, ITEM_FLAG_BOP_TRADEABLE))
myItems[i]->SetUInt32Value(ITEM_FIELD_CREATE_PLAYED_TIME, trader->GetTotalPlayedTime()-(_player->GetTotalPlayedTime()-myItems[i]->GetUInt32Value(ITEM_FIELD_CREATE_PLAYED_TIME)));
}
if (hisItems[i])
{
@@ -177,6 +180,8 @@ void WorldSession::moveItems(Item* myItems[], Item* hisItems[])
// store
_player->MoveItemToInventory(playerDst, hisItems[i], true, true);
if (hisItems[i]->HasFlag(ITEM_FIELD_FLAGS, ITEM_FLAG_BOP_TRADEABLE))
hisItems[i]->SetUInt32Value(ITEM_FIELD_CREATE_PLAYED_TIME, _player->GetTotalPlayedTime()-(trader->GetTotalPlayedTime()-hisItems[i]->GetUInt32Value(ITEM_FIELD_CREATE_PLAYED_TIME)));
}
}
else
@@ -291,20 +296,32 @@ void WorldSession::HandleAcceptTradeOpcode(WorldPacket& /*recvPacket*/)
{
if (Item* item = my_trade->GetItem(TradeSlots(i)))
{
if (!item->CanBeTraded())
if (!item->CanBeTraded(false, true))
{
SendTradeStatus(TRADE_STATUS_TRADE_CANCELED);
return;
}
if (item->IsBindedNotWith(trader))
{
SendTradeStatus(TRADE_STATUS_NOT_ELIGIBLE);
SendTradeStatus(TRADE_STATUS_CLOSE_WINDOW/*TRADE_STATUS_TRADE_CANCELED*/);
return;
}
}
if (Item* item = his_trade->GetItem(TradeSlots(i)))
{
if (!item->CanBeTraded())
if (!item->CanBeTraded(false, true))
{
SendTradeStatus(TRADE_STATUS_TRADE_CANCELED);
return;
}
//if (item->IsBindedNotWith(_player)) // dont mark as invalid when his item isnt good (not exploitable because if item is invalid trade will fail anyway later on the same check)
//{
// SendTradeStatus(TRADE_STATUS_NOT_ELIGIBLE);
// his_trade->SetAccepted(false, true);
// return;
//}
}
}
@@ -674,7 +691,7 @@ void WorldSession::HandleSetTradeItemOpcode(WorldPacket& recvPacket)
// check cheating, can't fail with correct client operations
Item* item = _player->GetItemByPos(bag, slot);
if (!item || (tradeSlot != TRADE_SLOT_NONTRADED && !item->CanBeTraded()))
if (!item || (tradeSlot != TRADE_SLOT_NONTRADED && !item->CanBeTraded(false, true)))
{
SendTradeStatus(TRADE_STATUS_TRADE_CANCELED);
return;