void WorldSession::HandleQuestgiverAcceptQuestOpcode( WorldPacket & recv_data ) { ObjectGuid guid; uint32 quest; uint32 unk1; recv_data >> guid >> quest >> unk1; if (!GetPlayer()->isAlive()) { if (Unit * pQuestNPC = GetPlayer()->GetMap()->GetUnit(guid)) if (!pQuestNPC->isInvisibleForAlive()) return; } DEBUG_LOG("WORLD: Received CMSG_QUESTGIVER_ACCEPT_QUEST npc = %s, quest = %u, unk1 = %u", guid.GetString().c_str(), quest, unk1 ); Object* pObject = _player->GetObjectByTypeMask(guid, TYPEMASK_CREATURE_GAMEOBJECT_PLAYER_OR_ITEM); // no or incorrect quest giver if(!pObject || (pObject->GetTypeId()!=TYPEID_PLAYER && !pObject->HasQuest(quest)) || (pObject->GetTypeId()==TYPEID_PLAYER && !((Player*)pObject)->CanShareQuest(quest)) ) { _player->PlayerTalkClass->CloseGossip(); _player->SetDivider( 0 ); return; } Quest const* qInfo = sObjectMgr.GetQuestTemplate(quest); if ( qInfo ) { // prevent cheating if(!GetPlayer()->CanTakeQuest(qInfo,true) ) { _player->PlayerTalkClass->CloseGossip(); _player->SetDivider( 0 ); return; } if( _player->GetDivider() != 0 ) { Player *pPlayer = ObjectAccessor::FindPlayer( _player->GetDivider() ); if( pPlayer ) { pPlayer->SendPushToPartyResponse( _player, QUEST_PARTY_MSG_ACCEPT_QUEST ); _player->SetDivider( 0 ); } } if( _player->CanAddQuest( qInfo, true ) ) { _player->AddQuest( qInfo, pObject ); if (qInfo->HasQuestFlag(QUEST_FLAGS_PARTY_ACCEPT)) { if (Group* pGroup = _player->GetGroup()) { for(GroupReference *itr = pGroup->GetFirstMember(); itr != NULL; itr = itr->next()) { Player* pPlayer = itr->getSource(); if (!pPlayer || pPlayer == _player) // not self continue; if (pPlayer->CanTakeQuest(qInfo, true)) { pPlayer->SetDivider(_player->GetGUID()); //need confirmation that any gossip window will close pPlayer->PlayerTalkClass->CloseGossip(); _player->SendQuestConfirmAccept(qInfo, pPlayer); } } } } if ( _player->CanCompleteQuest( quest ) ) _player->CompleteQuest( quest ); _player->GetAchievementMgr().StartTimedAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_COMPLETE_QUEST, quest); switch(pObject->GetTypeId()) { case TYPEID_UNIT: sScriptMgr.OnQuestAccept(_player, (Creature*)pObject, qInfo); break; case TYPEID_ITEM: case TYPEID_CONTAINER: { sScriptMgr.OnQuestAccept(_player, (Item*)pObject, qInfo); // destroy not required for quest finish quest starting item bool destroyItem = true; for(int i = 0; i < QUEST_ITEM_OBJECTIVES_COUNT; ++i) { if ((qInfo->ReqItemId[i] == ((Item*)pObject)->GetEntry()) && (((Item*)pObject)->GetProto()->MaxCount > 0)) { destroyItem = false; break; } } if(destroyItem) _player->DestroyItem(((Item*)pObject)->GetBagSlot(), ((Item*)pObject)->GetSlot(), true); break; } case TYPEID_GAMEOBJECT: sScriptMgr.OnQuestAccept(_player, (GameObject*)pObject, qInfo); break; } _player->PlayerTalkClass->CloseGossip(); if( qInfo->GetSrcSpell() > 0 ) _player->CastSpell( _player, qInfo->GetSrcSpell(), true); return; } } _player->PlayerTalkClass->CloseGossip(); }