Пример #1
0
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);
}
Пример #2
0
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;
    }
}
Пример #3
0
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);
    }
}