[9425] More achievement types support.

Implemented new achievement criteria requirement:
* ACHIEVEMENT_CRITERIA_REQUIRE_S_EQUIPED_ITEM_LVL (item level and item quality equiped in specific slot)

Implemented suppoprt achievement types:
* ACHIEVEMENT_CRITERIA_TYPE_EQUIP_EPIC_ITEM (required DB data)
* ACHIEVEMENT_CRITERIA_TYPE_SPECIAL_PVP_KILL (required DB data)

Also achievment types used only for statistics:
* ACHIEVEMENT_CRITERIA_TYPE_CREATE_AUCTION
* ACHIEVEMENT_CRITERIA_TYPE_WON_AUCTIONS
* ACHIEVEMENT_CRITERIA_TYPE_MONEY_FROM_VENDORS
* ACHIEVEMENT_CRITERIA_TYPE_GOLD_EARNED_BY_AUCTIONS
* ACHIEVEMENT_CRITERIA_TYPE_LOOT_EPIC_ITEM
* ACHIEVEMENT_CRITERIA_TYPE_RECEIVE_EPIC_ITEM
This commit is contained in:
VladimirMangos 2010-02-21 03:12:29 +03:00
parent 8bb13412e5
commit df652c56c0
10 changed files with 123 additions and 17 deletions

View file

@ -89,7 +89,9 @@ bool AchievementCriteriaRequirement::IsValid(AchievementCriteriaEntry const* cri
case ACHIEVEMENT_CRITERIA_TYPE_COMPLETE_QUEST: // only hardcoded list
case ACHIEVEMENT_CRITERIA_TYPE_CAST_SPELL:
case ACHIEVEMENT_CRITERIA_TYPE_WIN_RATED_ARENA:
case ACHIEVEMENT_CRITERIA_TYPE_EQUIP_EPIC_ITEM:
case ACHIEVEMENT_CRITERIA_TYPE_DO_EMOTE:
case ACHIEVEMENT_CRITERIA_TYPE_SPECIAL_PVP_KILL:
case ACHIEVEMENT_CRITERIA_TYPE_WIN_DUEL:
case ACHIEVEMENT_CRITERIA_TYPE_LOOT_TYPE:
case ACHIEVEMENT_CRITERIA_TYPE_CAST_SPELL2:
@ -241,6 +243,14 @@ bool AchievementCriteriaRequirement::IsValid(AchievementCriteriaEntry const* cri
return false;
}
return true;
case ACHIEVEMENT_CRITERIA_REQUIRE_S_EQUIPED_ITEM:
if(equipped_item.item_quality >= MAX_ITEM_QUALITY)
{
sLog.outErrorDb( "Table `achievement_criteria_requirement` (Entry: %u Type: %u) for requirement ACHIEVEMENT_CRITERIA_REQUIRE_S_EQUIPED_ITEM (%u) have unknown quality state in value1 (%u), ignore.",
criteria->ID, criteria->requiredType,requirementType,equipped_item.item_quality);
return false;
}
return true;
default:
sLog.outErrorDb( "Table `achievement_criteria_requirement` (Entry: %u Type: %u) have data for not supported data type (%u), ignore.", criteria->ID, criteria->requiredType,requirementType);
return false;
@ -317,6 +327,7 @@ bool AchievementCriteriaRequirement::Meets(uint32 criteria_id, Player const* sou
return bg->IsTeamScoreInRange(source->GetTeam()==ALLIANCE ? HORDE : ALLIANCE,bg_loss_team_score.min_score,bg_loss_team_score.max_score);
}
case ACHIEVEMENT_CRITERIA_REQUIRE_INSTANCE_SCRIPT:
{
if (!source->IsInWorld())
return false;
Map* map = source->GetMap();
@ -334,6 +345,15 @@ bool AchievementCriteriaRequirement::Meets(uint32 criteria_id, Player const* sou
return false;
}
return data->CheckAchievementCriteriaMeet(criteria_id, source, target, miscvalue1);
}
case ACHIEVEMENT_CRITERIA_REQUIRE_S_EQUIPED_ITEM:
{
Item* item = source->GetItemByPos(INVENTORY_SLOT_BAG_0,miscvalue1);
if (!item)
return false;
ItemPrototype const* proto = item->GetProto();
return proto->ItemLevel >= equipped_item.item_level && proto->Quality >= equipped_item.item_quality;
}
}
return false;
}
@ -713,6 +733,8 @@ void AchievementMgr::UpdateAchievementCriteria(AchievementCriteriaTypes type, ui
case ACHIEVEMENT_CRITERIA_TYPE_COMPLETE_DAILY_QUEST:
case ACHIEVEMENT_CRITERIA_TYPE_NUMBER_OF_TALENT_RESETS:
case ACHIEVEMENT_CRITERIA_TYPE_LOSE_DUEL:
case ACHIEVEMENT_CRITERIA_TYPE_CREATE_AUCTION:
case ACHIEVEMENT_CRITERIA_TYPE_WON_AUCTIONS: /* FIXME: for online player only currently */
case ACHIEVEMENT_CRITERIA_TYPE_ROLL_NEED:
case ACHIEVEMENT_CRITERIA_TYPE_ROLL_GREED:
case ACHIEVEMENT_CRITERIA_TYPE_QUEST_ABANDONED:
@ -724,12 +746,14 @@ void AchievementMgr::UpdateAchievementCriteria(AchievementCriteriaTypes type, ui
SetCriteriaProgress(achievementCriteria, 1, PROGRESS_ACCUMULATE);
break;
// std case: increment at miscvalue1
case ACHIEVEMENT_CRITERIA_TYPE_MONEY_FROM_VENDORS:
case ACHIEVEMENT_CRITERIA_TYPE_GOLD_SPENT_FOR_TALENTS:
case ACHIEVEMENT_CRITERIA_TYPE_MONEY_FROM_QUEST_REWARD:
case ACHIEVEMENT_CRITERIA_TYPE_GOLD_SPENT_FOR_TRAVELLING:
case ACHIEVEMENT_CRITERIA_TYPE_GOLD_SPENT_AT_BARBER:
case ACHIEVEMENT_CRITERIA_TYPE_GOLD_SPENT_FOR_MAIL:
case ACHIEVEMENT_CRITERIA_TYPE_LOOT_MONEY:
case ACHIEVEMENT_CRITERIA_TYPE_GOLD_EARNED_BY_AUCTIONS:/* FIXME: for online player only currently */
case ACHIEVEMENT_CRITERIA_TYPE_TOTAL_DAMAGE_RECEIVED:
case ACHIEVEMENT_CRITERIA_TYPE_TOTAL_HEALING_RECEIVED:
// AchievementMgr::UpdateAchievementCriteria might also be called on login - skip in this case
@ -1194,6 +1218,21 @@ void AchievementMgr::UpdateAchievementCriteria(AchievementCriteriaTypes type, ui
SetCriteriaProgress(achievementCriteria, 1);
break;
}
case ACHIEVEMENT_CRITERIA_TYPE_EQUIP_EPIC_ITEM:
{
// miscvalue1 = equip_slot+1 (for avoid use 0)
if(!miscvalue1)
continue;
uint32 item_slot = miscvalue1-1;
if(item_slot != achievementCriteria->equip_epic_item.itemSlot)
continue;
// those requirements couldn't be found in the dbc
AchievementCriteriaRequirementSet const* data = sAchievementMgr.GetCriteriaRequirementSet(achievementCriteria);
if(!data || !data->Meets(GetPlayer(),unit,item_slot))
continue;
SetCriteriaProgress(achievementCriteria, 1, PROGRESS_SET);
break;
}
case ACHIEVEMENT_CRITERIA_TYPE_ROLL_NEED_ON_LOOT:
case ACHIEVEMENT_CRITERIA_TYPE_ROLL_GREED_ON_LOOT:
{
@ -1269,6 +1308,23 @@ void AchievementMgr::UpdateAchievementCriteria(AchievementCriteriaTypes type, ui
SetCriteriaProgress(achievementCriteria, 1, PROGRESS_ACCUMULATE);
break;
case ACHIEVEMENT_CRITERIA_TYPE_SPECIAL_PVP_KILL:
{
// AchievementMgr::UpdateAchievementCriteria might also be called on login - skip in this case
if (!miscvalue1)
continue;
// those requirements couldn't be found in the dbc
AchievementCriteriaRequirementSet const* data = sAchievementMgr.GetCriteriaRequirementSet(achievementCriteria);
if (!data)
continue;
if (!data->Meets(GetPlayer(),unit))
continue;
SetCriteriaProgress(achievementCriteria, 1, PROGRESS_ACCUMULATE);
break;
}
case ACHIEVEMENT_CRITERIA_TYPE_FISH_IN_GAMEOBJECT:
if (!miscvalue1)
continue;
@ -1324,6 +1380,18 @@ void AchievementMgr::UpdateAchievementCriteria(AchievementCriteriaTypes type, ui
case ACHIEVEMENT_CRITERIA_TYPE_KNOWN_FACTIONS:
SetCriteriaProgress(achievementCriteria, GetPlayer()->GetReputationMgr().GetVisibleFactionCount());
break;
case ACHIEVEMENT_CRITERIA_TYPE_LOOT_EPIC_ITEM:
case ACHIEVEMENT_CRITERIA_TYPE_RECEIVE_EPIC_ITEM:
{
// AchievementMgr::UpdateAchievementCriteria might also be called on login - skip in this case
if (!miscvalue1)
continue;
ItemPrototype const* proto = ObjectMgr::GetItemPrototype(miscvalue1);
if (!proto || proto->Quality < ITEM_QUALITY_EPIC)
continue;
SetCriteriaProgress(achievementCriteria, 1, PROGRESS_ACCUMULATE);
break;
}
case ACHIEVEMENT_CRITERIA_TYPE_LEARN_SKILL_LINE:
{
if (miscvalue1 && miscvalue1 != achievementCriteria->learn_skill_line.skillLine)
@ -1379,18 +1447,11 @@ void AchievementMgr::UpdateAchievementCriteria(AchievementCriteriaTypes type, ui
case ACHIEVEMENT_CRITERIA_TYPE_HIGHEST_TEAM_RATING:
case ACHIEVEMENT_CRITERIA_TYPE_REACH_TEAM_RATING:
case ACHIEVEMENT_CRITERIA_TYPE_OWN_RANK:
case ACHIEVEMENT_CRITERIA_TYPE_EQUIP_EPIC_ITEM:
case ACHIEVEMENT_CRITERIA_TYPE_GET_KILLING_BLOWS:
case ACHIEVEMENT_CRITERIA_TYPE_MONEY_FROM_VENDORS:
case ACHIEVEMENT_CRITERIA_TYPE_SPECIAL_PVP_KILL:
case ACHIEVEMENT_CRITERIA_TYPE_EARNED_PVP_TITLE:
case ACHIEVEMENT_CRITERIA_TYPE_KILL_CREATURE_TYPE:
case ACHIEVEMENT_CRITERIA_TYPE_GOLD_EARNED_BY_AUCTIONS:
case ACHIEVEMENT_CRITERIA_TYPE_CREATE_AUCTION:
case ACHIEVEMENT_CRITERIA_TYPE_WON_AUCTIONS:
case ACHIEVEMENT_CRITERIA_TYPE_LOOT_EPIC_ITEM:
case ACHIEVEMENT_CRITERIA_TYPE_RECEIVE_EPIC_ITEM:
case ACHIEVEMENT_CRITERIA_TYPE_TOTAL:
case ACHIEVEMENT_CRITERIA_TYPE_EARN_ACHIEVEMENT_POINTS:
case ACHIEVEMENT_CRITERIA_TYPE_USE_LFD_TO_GROUP_WITH_PLAYERS:
break; // Not implemented yet :(
}
if(IsCompletedCriteria(achievementCriteria,achievement))
@ -1501,6 +1562,8 @@ bool AchievementMgr::IsCompletedCriteria(AchievementCriteriaEntry const* achieve
return progress->counter >= achievementCriteria->gain_exalted_reputation.numberOfExaltedFactions;
case ACHIEVEMENT_CRITERIA_TYPE_VISIT_BARBER_SHOP:
return progress->counter >= achievementCriteria->visit_barber.numberOfVisits;
case ACHIEVEMENT_CRITERIA_TYPE_EQUIP_EPIC_ITEM:
return progress->counter >= achievementCriteria->equip_epic_item.count;
case ACHIEVEMENT_CRITERIA_TYPE_ROLL_NEED_ON_LOOT:
case ACHIEVEMENT_CRITERIA_TYPE_ROLL_GREED_ON_LOOT:
return progress->counter >= achievementCriteria->roll_greed_on_loot.count;
@ -1518,6 +1581,8 @@ bool AchievementMgr::IsCompletedCriteria(AchievementCriteriaEntry const* achieve
return progress->counter >= achievementCriteria->loot_money.goldInCopper;
case ACHIEVEMENT_CRITERIA_TYPE_USE_GAMEOBJECT:
return progress->counter >= achievementCriteria->use_gameobject.useCount;
case ACHIEVEMENT_CRITERIA_TYPE_SPECIAL_PVP_KILL:
return progress->counter >= achievementCriteria->special_pvp_kill.killCount;
case ACHIEVEMENT_CRITERIA_TYPE_FISH_IN_GAMEOBJECT:
return progress->counter >= achievementCriteria->fish_in_gameobject.lootCount;
case ACHIEVEMENT_CRITERIA_TYPE_LEARN_SKILLLINE_SPELLS:
@ -1539,17 +1604,23 @@ bool AchievementMgr::IsCompletedCriteria(AchievementCriteriaEntry const* achieve
case ACHIEVEMENT_CRITERIA_TYPE_KILLED_BY_CREATURE:
case ACHIEVEMENT_CRITERIA_TYPE_KILLED_BY_PLAYER:
case ACHIEVEMENT_CRITERIA_TYPE_DEATHS_FROM:
case ACHIEVEMENT_CRITERIA_TYPE_MONEY_FROM_VENDORS:
case ACHIEVEMENT_CRITERIA_TYPE_GOLD_SPENT_FOR_TALENTS:
case ACHIEVEMENT_CRITERIA_TYPE_NUMBER_OF_TALENT_RESETS:
case ACHIEVEMENT_CRITERIA_TYPE_GOLD_SPENT_AT_BARBER:
case ACHIEVEMENT_CRITERIA_TYPE_GOLD_SPENT_FOR_MAIL:
case ACHIEVEMENT_CRITERIA_TYPE_LOSE_DUEL:
case ACHIEVEMENT_CRITERIA_TYPE_GOLD_EARNED_BY_AUCTIONS:
case ACHIEVEMENT_CRITERIA_TYPE_CREATE_AUCTION:
case ACHIEVEMENT_CRITERIA_TYPE_HIGHEST_AUCTION_BID:
case ACHIEVEMENT_CRITERIA_TYPE_WON_AUCTIONS:
case ACHIEVEMENT_CRITERIA_TYPE_HIGHEST_AUCTION_SOLD:
case ACHIEVEMENT_CRITERIA_TYPE_HIGHEST_GOLD_VALUE_OWNED:
case ACHIEVEMENT_CRITERIA_TYPE_GAIN_REVERED_REPUTATION:
case ACHIEVEMENT_CRITERIA_TYPE_GAIN_HONORED_REPUTATION:
case ACHIEVEMENT_CRITERIA_TYPE_KNOWN_FACTIONS:
case ACHIEVEMENT_CRITERIA_TYPE_LOOT_EPIC_ITEM:
case ACHIEVEMENT_CRITERIA_TYPE_RECEIVE_EPIC_ITEM:
case ACHIEVEMENT_CRITERIA_TYPE_ROLL_NEED:
case ACHIEVEMENT_CRITERIA_TYPE_ROLL_GREED:
case ACHIEVEMENT_CRITERIA_TYPE_HIGHEST_HEALTH:
@ -1983,10 +2054,14 @@ void AchievementGlobalMgr::LoadAchievementCriteriaRequirements()
if(criteria->win_rated_arena.flag!=ACHIEVEMENT_CRITERIA_CONDITION_NO_LOOSE)
continue;
break;
case ACHIEVEMENT_CRITERIA_TYPE_EQUIP_EPIC_ITEM: // any cases
break;
case ACHIEVEMENT_CRITERIA_TYPE_DO_EMOTE: // need skip generic cases
if(criteria->do_emote.count==0)
continue;
break;
case ACHIEVEMENT_CRITERIA_TYPE_SPECIAL_PVP_KILL:// any cases
break;
case ACHIEVEMENT_CRITERIA_TYPE_WIN_DUEL: // skip statistics
if(criteria->win_duel.duelCount==0)
continue;