aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/game/Item.h21
-rw-r--r--src/game/ItemHandler.cpp85
-rw-r--r--src/game/Opcodes.cpp4
-rw-r--r--src/game/Opcodes.h6
-rw-r--r--src/game/Player.cpp30
-rw-r--r--src/game/WorldSession.h2
6 files changed, 140 insertions, 8 deletions
diff --git a/src/game/Item.h b/src/game/Item.h
index 0adf60bb57d..710e0a56d57 100644
--- a/src/game/Item.h
+++ b/src/game/Item.h
@@ -319,6 +319,21 @@ class TRINITY_DLL_SPEC Item : public Object
bool IsWeaponVellum() const { return GetProto()->IsWeaponVellum(); }
bool IsArmorVellum() const { return GetProto()->IsArmorVellum(); }
bool IsConjuredConsumable() const { return GetProto()->IsConjuredConsumable(); }
+
+ // Item Refund system
+ uint32 GetPaidHonorPoints() { return m_paidHonorPoints; }
+ uint32 GetPaidArenaPoints() { return m_paidArenaPoints; }
+ uint32 GetPaidExtendedCostId(uint32 pos) { return m_paidExtendedCostId[pos]; }
+ uint32 GetPaidExtendedCostCount(uint32 pos) { return m_paidExtendedCostCount[pos]; }
+ uint32 GetRefundExpiryTime() { return GetUInt32Value(ITEM_FIELD_CREATE_PLAYED_TIME); }
+ void SetRefundExpiryTime(uint32 timeval) { SetUInt32Value(ITEM_FIELD_CREATE_PLAYED_TIME, timeval); }
+ void SetPaidHonorPoints(uint32 value) { m_paidHonorPoints = value; }
+ void SetPaidArenaPoints(uint32 value) { m_paidArenaPoints = value; }
+ void SetPaidExtendedCost(uint32 pos, uint32 entry, uint32 count)
+ {
+ m_paidExtendedCostId[pos] = entry;
+ m_paidExtendedCostCount[pos] = count;
+ }
private:
uint8 m_slot;
@@ -326,5 +341,11 @@ class TRINITY_DLL_SPEC Item : public Object
ItemUpdateState uState;
int16 uQueuePos;
bool mb_in_trade; // true if item is currently in trade-window
+
+ // refund system
+ uint32 m_paidHonorPoints;
+ uint32 m_paidArenaPoints;
+ uint32 m_paidExtendedCostId[5];
+ uint32 m_paidExtendedCostCount[5];
};
#endif
diff --git a/src/game/ItemHandler.cpp b/src/game/ItemHandler.cpp
index f7f7ba9a9a5..b4b22fe90cc 100644
--- a/src/game/ItemHandler.cpp
+++ b/src/game/ItemHandler.cpp
@@ -1360,4 +1360,89 @@ void WorldSession::HandleItemRefundInfoRequest(WorldPacket& recv_data)
}
// item refund system not implemented yet
+ WorldPacket data(SMSG_ITEM_REFUND_TIMER, 8+4+4+4+4*4+4*4+4+4); // guess size
+ data << uint64(guid); // item guid
+ data << uint32(1); // unknown
+ data << uint32(item->GetPaidHonorPoints()); // honor point cost
+ data << uint32(item->GetPaidArenaPoints()); // arena point cost
+ for(uint32 i = 0; i < 5; ++i) // extended cost data
+ {
+ data << uint32(item->GetPaidExtendedCostId(i));
+ data << uint32(item->GetPaidExtendedCostCount(i));
+ }
+ data << uint32(0);
+ data << uint32(0);
+ SendPacket(&data);
+}
+
+void WorldSession::HandleItemRefund(WorldPacket &recv_data)
+{
+ sLog.outDebug("WORLD: CMSG_ITEM_REFUND");
+ uint64 guid;
+ recv_data >> guid; // item guid
+
+ Item *item = _player->GetItemByGuid(guid);
+ if(!item)
+ {
+ sLog.outDebug("Item refund: item not found!");
+ return;
+ }
+
+ if(!item->HasFlag(ITEM_FIELD_FLAGS, ITEM_FLAGS_REFUNDABLE))
+ {
+ sLog.outDebug("Item refund: item not refundable!");
+ return;
+ }
+
+ if(item->GetRefundExpiryTime() <= time(NULL)) // item refund has expired
+ {
+ WorldPacket data(SMSG_ITEM_REFUND);
+ data << uint64(guid); // guid
+ data << uint32(1); // error, abort refund
+ return;
+ }
+
+ WorldPacket data(SMSG_ITEM_REFUND);
+ data << uint64(guid); // guid?
+ data << uint32(0); // must be 0 or client side error in refund
+ data << uint32(0); // unk - message sent to client?
+ data << uint32(item->GetPaidHonorPoints()); // honor points refund
+ data << uint32(item->GetPaidArenaPoints()); // arena points refund
+ for(uint32 i = 0; i < 5; ++i) // extended cost?
+ {
+ data << uint32(item->GetPaidExtendedCostId(i));
+ data << uint32(item->GetPaidExtendedCostCount(i));
+ }
+ SendPacket(&data);
+
+ // Grant back extendedcost items
+ uint32 count = 0;
+ uint32 itemid = 0;
+ for(uint32 i = 0; i < 5; ++i)
+ {
+ count = item->GetPaidExtendedCostCount(i);
+ itemid = item->GetPaidExtendedCostId(i);
+ if (count && itemid)
+ {
+ ItemPosCountVec dest;
+ uint8 msg = _player->CanStoreNewItem(NULL_BAG, NULL_SLOT, dest, itemid, count);
+ if (msg == EQUIP_ERR_OK)
+ {
+ Item* it = _player->StoreNewItem(dest, itemid, true);
+ _player->SendNewItem(it, count, true, false, true);
+ }
+
+ // What to do if there's no space?
+ }
+ }
+ // Grant back Honor points
+ if (uint32 honorRefund = item->GetPaidHonorPoints() > 0)
+ _player->ModifyHonorPoints(honorRefund);
+
+ // Grant back Arena points
+ if (uint32 arenaRefund = item->GetPaidArenaPoints() > 0)
+ _player->ModifyArenaPoints(arenaRefund);
+
+ // Destroy item
+ _player->DestroyItemCount(item->GetEntry(), 1, true, true);
}
diff --git a/src/game/Opcodes.cpp b/src/game/Opcodes.cpp
index 3bb4691b0dd..6dc88c9d37a 100644
--- a/src/game/Opcodes.cpp
+++ b/src/game/Opcodes.cpp
@@ -1230,9 +1230,9 @@ OpcodeHandler opcodeTable[NUM_MSG_TYPES] =
/*0x4AF*/ { "UMSG_UNKNOWN_1199", STATUS_NEVER, &WorldSession::Handle_NULL },
/*0x4B0*/ { "UMSG_UNKNOWN_1200", STATUS_NEVER, &WorldSession::Handle_NULL },
/*0x4B1*/ { "UMSG_UNKNOWN_1201", STATUS_NEVER, &WorldSession::Handle_NULL },
- /*0x4B2*/ { "SMSG_UNKNOWN_1202", STATUS_NEVER, &WorldSession::Handle_ServerSide },
+ /*0x4B2*/ { "SMSG_ITEM_REFUND_TIMER", STATUS_NEVER, &WorldSession::Handle_ServerSide },
/*0x4B3*/ { "CMSG_ITEM_REFUND_INFO_REQUEST", STATUS_LOGGEDIN, &WorldSession::HandleItemRefundInfoRequest },
- /*0x4B4*/ { "CMSG_UNKNOWN_1204", STATUS_NEVER, &WorldSession::Handle_NULL },
+ /*0x4B4*/ { "CMSG_ITEM_REFUND", STATUS_LOGGEDIN, &WorldSession::HandleItemRefund },
/*0x4B5*/ { "SMSG_UNKNOWN_1205", STATUS_NEVER, &WorldSession::Handle_ServerSide },
/*0x4B6*/ { "CMSG_CORPSE_MAP_POSITION_QUERY", STATUS_LOGGEDIN, &WorldSession::HandleCorpseMapPositionQuery },
/*0x4B7*/ { "CMSG_CORPSE_MAP_POSITION_QUERY_RESPONSE", STATUS_NEVER, &WorldSession::Handle_ServerSide },
diff --git a/src/game/Opcodes.h b/src/game/Opcodes.h
index 54cc87d5e4f..007e17f1687 100644
--- a/src/game/Opcodes.h
+++ b/src/game/Opcodes.h
@@ -1238,10 +1238,10 @@ enum Opcodes
UMSG_UNKNOWN_1199 = 0x4AF, // not found
UMSG_UNKNOWN_1200 = 0x4B0, // not found
UMSG_UNKNOWN_1201 = 0x4B1, // not found
- SMSG_UNKNOWN_1202 = 0x4B2, // refund something
+ SMSG_ITEM_REFUND_TIMER = 0x4B2, // refund something
CMSG_ITEM_REFUND_INFO_REQUEST = 0x4B3, // refund request?
- CMSG_UNKNOWN_1204 = 0x4B4, // lua: ContainerRefundItemPurchase
- SMSG_UNKNOWN_1205 = 0x4B5, // refund something
+ CMSG_ITEM_REFUND = 0x4B4, // lua: ContainerRefundItemPurchase
+ SMSG_ITEM_REFUND = 0x4B5, // refund something
CMSG_CORPSE_MAP_POSITION_QUERY = 0x4B6, // CMSG, uint32
CMSG_CORPSE_MAP_POSITION_QUERY_RESPONSE = 0x4B7, // SMSG, 3*float+float
CMSG_LFG_SET_ROLES = 0x4B8, // CMSG, empty, lua: SetLFGRoles
diff --git a/src/game/Player.cpp b/src/game/Player.cpp
index 0e045699898..c1e4a9aa5ef 100644
--- a/src/game/Player.cpp
+++ b/src/game/Player.cpp
@@ -18463,17 +18463,32 @@ bool Player::BuyItemFromVendor(uint64 vendorguid, uint32 item, uint8 count, uint
}
ModifyMoney( -(int32)price );
+ uint32 arenaPoints = 0;
+ uint32 honorPoints = 0;
+ uint32 extendedCost[5] = {0,0,0,0,0};
+ uint32 extendedCostCount[5] = {0,0,0,0,0};
+
if (crItem->ExtendedCost) // case for new honor system
{
ItemExtendedCostEntry const* iece = sItemExtendedCostStore.LookupEntry(crItem->ExtendedCost);
if (iece->reqhonorpoints)
- ModifyHonorPoints( - int32(iece->reqhonorpoints * count));
+ {
+ honorPoints = iece->reqhonorpoints * count;
+ ModifyHonorPoints( - int32(honorPoints) );
+ }
if (iece->reqarenapoints)
- ModifyArenaPoints( - int32(iece->reqarenapoints * count));
+ {
+ arenaPoints = iece->reqarenapoints * count;
+ ModifyArenaPoints( - int32(arenaPoints) );
+ }
for (uint8 i = 0; i < 5; ++i)
{
if (iece->reqitem[i])
+ {
DestroyItemCount(iece->reqitem[i], (iece->reqitemcount[i] * count), true);
+ extendedCost[i] = iece->reqitem[i];
+ extendedCostCount[i] = iece->reqitemcount[i];
+ }
}
}
@@ -18487,8 +18502,17 @@ bool Player::BuyItemFromVendor(uint64 vendorguid, uint32 item, uint8 count, uint
data << uint32(crItem->maxcount > 0 ? new_count : 0xFFFFFFFF);
data << uint32(count);
GetSession()->SendPacket(&data);
-
SendNewItem(it, pProto->BuyCount*count, true, false, false);
+
+ // Item Refund system, only works for non stackable items with extendedcost
+ if(count == 1 && crItem->ExtendedCost )
+ {
+ it->SetPaidArenaPoints(arenaPoints);
+ it->SetPaidHonorPoints(honorPoints);
+ it->SetRefundExpiryTime( time(NULL)+(HOUR*2) );
+ for (uint8 i = 0; i < 5; ++i)
+ it->SetPaidExtendedCost(i, extendedCost[i], extendedCostCount[i]);
+ }
}
}
else if (IsEquipmentPos(bag, slot))
diff --git a/src/game/WorldSession.h b/src/game/WorldSession.h
index dcd5a9f86ee..7e81a3d338f 100644
--- a/src/game/WorldSession.h
+++ b/src/game/WorldSession.h
@@ -688,7 +688,9 @@ class TRINITY_DLL_SPEC WorldSession
void HandleSocketOpcode(WorldPacket& recv_data);
void HandleCancelTempEnchantmentOpcode(WorldPacket& recv_data);
+
void HandleItemRefundInfoRequest(WorldPacket& recv_data);
+ void HandleItemRefund(WorldPacket& recv_data);
void HandleChannelVoiceOnOpcode(WorldPacket & recv_data);
void HandleVoiceSessionEnableOpcode(WorldPacket& recv_data);