void WorldSession::HandleLootMasterAskForRoll(WorldPacket& recvData) { ObjectGuid guid = 0; uint8 slot = 0; recvData >> slot; uint8 bitOrder[8] = {6, 0, 4, 3, 2, 7, 1, 5}; recvData.ReadBitInOrder(guid, bitOrder); uint8 byteOrder[8] = {2, 0, 7, 5, 3, 6, 1, 4}; recvData.ReadBytesSeq(guid, byteOrder); if (!_player->GetGroup() || _player->GetGroup()->GetLooterGuid() != _player->GetGUID()) { _player->SendLootRelease(GetPlayer()->GetLootGUID()); return; } Loot* loot = NULL; if (IS_CRE_OR_VEH_GUID(GetPlayer()->GetLootGUID())) { Creature* creature = GetPlayer()->GetMap()->GetCreature(guid); if (!creature) return; loot = &creature->loot; if (loot->isLinkedLoot(slot)) { LinkedLootInfo linkedLootInfo = loot->getLinkedLoot(slot); creature = GetPlayer()->GetCreature(*GetPlayer(), linkedLootInfo.creatureGUID); if (!creature) return; loot = &creature->loot; slot = linkedLootInfo.slot; } } else if (IS_GAMEOBJECT_GUID(GetPlayer()->GetLootGUID())) { GameObject* pGO = GetPlayer()->GetMap()->GetGameObject(guid); if (!pGO) return; loot = &pGO->loot; } if (!loot || loot->alreadyAskedForRoll) return; if (slot >= loot->items.size() + loot->quest_items.size()) { sLog->outDebug(LOG_FILTER_LOOT, "MasterLootItem: Player %s might be using a hack! (slot %d, size %lu)", GetPlayer()->GetName(), slot, (unsigned long)loot->items.size()); return; } LootItem& item = slot >= loot->items.size() ? loot->quest_items[slot - loot->items.size()] : loot->items[slot]; loot->alreadyAskedForRoll = true; _player->GetGroup()->DoRollForAllMembers(guid, slot, _player->GetMapId(), loot, item, _player); }
void WorldSession::HandleLootMasterGiveOpcode(WorldPacket& recvData) { ObjectGuid target_playerguid = 0; target_playerguid[6] = recvData.ReadBit(); target_playerguid[2] = recvData.ReadBit(); target_playerguid[5] = recvData.ReadBit(); target_playerguid[7] = recvData.ReadBit(); target_playerguid[3] = recvData.ReadBit(); target_playerguid[4] = recvData.ReadBit(); target_playerguid[0] = recvData.ReadBit(); uint32 count = recvData.ReadBits(23); if (count > 40) return; std::vector<ObjectGuid> guids(count); std::vector<uint8> types(count); uint8 bitOrder[8] = {1, 4, 3, 6, 0, 2, 7, 5}; for (uint32 i = 0; i < count; ++i) recvData.ReadBitInOrder(guids[i], bitOrder); target_playerguid[1] = recvData.ReadBit(); recvData.FlushBits(); recvData.ReadByteSeq(target_playerguid[5]); recvData.ReadByteSeq(target_playerguid[6]); uint8 byteOrder[8] = {3, 5, 0, 6, 2, 1, 4, 7}; for (uint32 i = 0; i < count; ++i) { recvData >> types[i]; recvData.ReadBytesSeq(guids[i], byteOrder); } recvData.ReadByteSeq(target_playerguid[3]); recvData.ReadByteSeq(target_playerguid[2]); recvData.ReadByteSeq(target_playerguid[0]); recvData.ReadByteSeq(target_playerguid[4]); recvData.ReadByteSeq(target_playerguid[1]); recvData.ReadByteSeq(target_playerguid[7]); //recvData >> lootguid >> slotid >> target_playerguid; if (!_player->GetGroup() || _player->GetGroup()->GetLooterGuid() != _player->GetGUID()) { _player->SendLootRelease(GetPlayer()->GetLootGUID()); return; } Player* target = ObjectAccessor::FindPlayer(MAKE_NEW_GUID(target_playerguid, 0, HIGHGUID_PLAYER)); if (!target) return; sLog->outDebug(LOG_FILTER_NETWORKIO, "WorldSession::HandleLootMasterGiveOpcode (CMSG_LOOT_MASTER_GIVE, 0x02A3) Target = [%s].", target->GetName()); for (uint32 i = 0; i < count; ++i) { ObjectGuid lootguid = guids[i]; uint8 slotid = types[i]; Loot* loot = NULL; if (IS_CRE_OR_VEH_GUID(GetPlayer()->GetLootGUID())) { Creature* creature = GetPlayer()->GetMap()->GetCreature(sObjectMgr->GetCreatureGUIDByLootViewGUID(lootguid)); if (!creature) return; loot = &creature->loot; if (loot->isLinkedLoot(slotid)) { LinkedLootInfo linkedLootInfo = loot->getLinkedLoot(slotid); creature = GetPlayer()->GetCreature(*GetPlayer(), linkedLootInfo.creatureGUID); if (!creature) return; loot = &creature->loot; slotid = linkedLootInfo.slot; } } else if (IS_GAMEOBJECT_GUID(GetPlayer()->GetLootGUID())) { GameObject* pGO = GetPlayer()->GetMap()->GetGameObject(GetPlayer()->GetLootGUID()); if (!pGO) return; loot = &pGO->loot; } if (!loot) return; if (slotid >= loot->items.size() + loot->quest_items.size()) { sLog->outDebug(LOG_FILTER_LOOT, "MasterLootItem: Player %s might be using a hack! (slot %d, size %lu)", GetPlayer()->GetName(), slotid, (unsigned long)loot->items.size()); return; } LootItem& item = slotid >= loot->items.size() ? loot->quest_items[slotid - loot->items.size()] : loot->items[slotid]; ItemPosCountVec dest; InventoryResult msg = target->CanStoreNewItem(NULL_BAG, NULL_SLOT, dest, item.itemid, item.count); if (item.follow_loot_rules && !item.AllowedForPlayer(target)) msg = EQUIP_ERR_CANT_EQUIP_EVER; if (msg != EQUIP_ERR_OK) { target->SendEquipError(msg, NULL, NULL, item.itemid); // send duplicate of error massage to master looter _player->SendEquipError(msg, NULL, NULL, item.itemid); 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, looters); target->SendNewItem(newitem, uint32(item.count), false, false, true); target->UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_LOOT_ITEM, item.itemid, item.count); target->UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_LOOT_TYPE, loot->loot_type, item.count); target->UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_LOOT_EPIC_ITEM, item.itemid, item.count); // mark as looted item.count=0; item.is_looted=true; loot->NotifyItemRemoved(slotid); --loot->unlootedCount; } }
void WorldSession::HandleAutostoreLootItemOpcode(WorldPacket & recvData) { sLog->outDebug(LOG_FILTER_NETWORKIO, "WORLD: CMSG_AUTOSTORE_LOOT_ITEM"); Player* player = GetPlayer(); uint64 lguid = player->GetLootGUID(); Loot* loot = NULL; uint8 lootSlot = 0; uint8 linkedLootSlot = 255; uint32 count = recvData.ReadBits(23); std::vector<ObjectGuid> guids; guids.resize(count); uint8 bitOrder[8] = { 2, 1, 5, 7, 4, 3, 0, 6 }; for (uint32 i = 0; i < count; i++) recvData.ReadBitInOrder(guids[i], bitOrder); recvData.FlushBits(); for (uint32 i = 0; i < count; i++) { recvData.ReadByteSeq(guids[i][0]); recvData.ReadByteSeq(guids[i][3]); recvData >> lootSlot; recvData.ReadByteSeq(guids[i][7]); recvData.ReadByteSeq(guids[i][2]); recvData.ReadByteSeq(guids[i][4]); recvData.ReadByteSeq(guids[i][1]); recvData.ReadByteSeq(guids[i][6]); recvData.ReadByteSeq(guids[i][5]); linkedLootSlot = 0xFF; if (IS_GAMEOBJECT_GUID(lguid)) { GameObject* go = player->GetMap()->GetGameObject(lguid); // not check distance for GO in case owned GO (fishing bobber case, for example) or Fishing hole GO if (!go || ((go->GetOwnerGUID() != _player->GetGUID() && go->GetGoType() != GAMEOBJECT_TYPE_FISHINGHOLE) && !go->IsWithinDistInMap(_player, INTERACTION_DISTANCE))) { player->SendLootRelease(lguid); return; } loot = &go->loot; } else if (IS_ITEM_GUID(lguid)) { Item* pItem = player->GetItemByGuid(lguid); if (!pItem) { player->SendLootRelease(lguid); return; } loot = &pItem->loot; } else if (IS_CORPSE_GUID(lguid)) { Corpse* bones = ObjectAccessor::GetCorpse(*player, lguid); if (!bones) { player->SendLootRelease(lguid); return; } loot = &bones->loot; } else { Creature* creature = GetPlayer()->GetMap()->GetCreature(lguid); bool lootAllowed = creature && creature->isAlive() == (player->getClass() == CLASS_ROGUE && creature->lootForPickPocketed); if (!lootAllowed || (!creature->IsWithinDistInMap(_player, INTERACTION_DISTANCE) && !_player->HasSpell(125048))) { player->SendLootRelease(lguid); return; } loot = &creature->loot; if (loot->isLinkedLoot(lootSlot)) { LinkedLootInfo linkedLootInfo = loot->getLinkedLoot(lootSlot); creature = player->GetCreature(*player, linkedLootInfo.creatureGUID); if (!creature) { player->SendLootRelease(lguid); return; } loot = &creature->loot; linkedLootSlot = lootSlot; lootSlot = linkedLootInfo.slot; } } player->StoreLootItem(lootSlot, loot, linkedLootSlot); } }