aboutsummaryrefslogtreecommitdiff
path: root/src/server/game
diff options
context:
space:
mode:
Diffstat (limited to 'src/server/game')
-rw-r--r--src/server/game/AI/SmartScripts/SmartScriptMgr.cpp2
-rw-r--r--src/server/game/Achievements/AchievementMgr.cpp14
-rw-r--r--src/server/game/Battlegrounds/Zones/BattlegroundSA.cpp6
-rw-r--r--src/server/game/Chat/Chat.cpp4
-rw-r--r--src/server/game/Conditions/ConditionMgr.cpp2
-rw-r--r--src/server/game/DataStores/DBCStores.cpp63
-rw-r--r--src/server/game/DataStores/DBCStores.h7
-rw-r--r--src/server/game/DataStores/DBCStructure.h2
-rw-r--r--src/server/game/DataStores/DBCfmt.h2
-rw-r--r--src/server/game/Entities/Creature/Creature.cpp14
-rw-r--r--src/server/game/Entities/GameObject/GameObject.cpp3
-rw-r--r--src/server/game/Entities/Player/Player.cpp53
-rw-r--r--src/server/game/Entities/Unit/Unit.cpp22
-rw-r--r--src/server/game/Globals/ObjectMgr.cpp10
-rw-r--r--src/server/game/Grids/GridDefines.h2
-rw-r--r--src/server/game/Grids/Notifiers/GridNotifiers.cpp2
-rw-r--r--src/server/game/Handlers/ChannelHandler.cpp2
-rw-r--r--src/server/game/Handlers/MiscHandler.cpp4
-rw-r--r--src/server/game/Handlers/MovementHandler.cpp3
-rw-r--r--src/server/game/Loot/LootMgr.cpp4
-rw-r--r--src/server/game/Maps/Map.cpp141
-rw-r--r--src/server/game/Maps/Map.h37
-rw-r--r--src/server/game/Maps/MapManager.h14
-rw-r--r--src/server/game/OutdoorPvP/OutdoorPvP.cpp2
-rw-r--r--src/server/game/Spells/Auras/SpellAuraEffects.cpp24
-rw-r--r--src/server/game/Spells/Spell.cpp2
-rw-r--r--src/server/game/Spells/SpellEffects.cpp4
-rw-r--r--src/server/game/Spells/SpellMgr.cpp4
-rw-r--r--src/server/game/Texts/CreatureTextMgr.cpp43
29 files changed, 199 insertions, 293 deletions
diff --git a/src/server/game/AI/SmartScripts/SmartScriptMgr.cpp b/src/server/game/AI/SmartScripts/SmartScriptMgr.cpp
index 977847e60c9..ef3357fa6ed 100644
--- a/src/server/game/AI/SmartScripts/SmartScriptMgr.cpp
+++ b/src/server/game/AI/SmartScripts/SmartScriptMgr.cpp
@@ -468,7 +468,7 @@ bool SmartAIMgr::IsEventValid(SmartScriptHolder& e)
TC_LOG_ERROR("sql.sql", "SmartAIMgr: Entry %d SourceType %u Event %u Action %u uses non-existent Map entry %u, skipped.", e.entryOrGuid, e.GetScriptType(), e.event_id, e.GetActionType(), e.event.respawn.map);
return false;
}
- if (e.event.respawn.type == SMART_SCRIPT_RESPAWN_CONDITION_AREA && !GetAreaEntryByAreaID(e.event.respawn.area))
+ if (e.event.respawn.type == SMART_SCRIPT_RESPAWN_CONDITION_AREA && !sAreaTableStore.LookupEntry(e.event.respawn.area))
{
TC_LOG_ERROR("sql.sql", "SmartAIMgr: Entry %d SourceType %u Event %u Action %u uses non-existent Area entry %u, skipped.", e.entryOrGuid, e.GetScriptType(), e.event_id, e.GetActionType(), e.event.respawn.area);
return false;
diff --git a/src/server/game/Achievements/AchievementMgr.cpp b/src/server/game/Achievements/AchievementMgr.cpp
index 90e61826e35..ac8e0298a44 100644
--- a/src/server/game/Achievements/AchievementMgr.cpp
+++ b/src/server/game/Achievements/AchievementMgr.cpp
@@ -156,7 +156,7 @@ bool AchievementCriteriaData::IsValid(AchievementCriteriaEntry const* criteria)
return true;
}
case ACHIEVEMENT_CRITERIA_DATA_TYPE_S_AREA:
- if (!GetAreaEntryByAreaID(area.id))
+ if (!sAreaTableStore.LookupEntry(area.id))
{
TC_LOG_ERROR("sql.sql", "Table `achievement_criteria_data` (Entry: %u Type: %u) for data type ACHIEVEMENT_CRITERIA_DATA_TYPE_S_AREA (%u) has wrong area id in value1 (%u), ignored.",
criteria->ID, criteria->requiredType, dataType, area.id);
@@ -1905,17 +1905,15 @@ bool AchievementMgr::RequirementsSatisfied(AchievementCriteriaEntry const* achie
bool matchFound = false;
for (int j = 0; j < MAX_WORLD_MAP_OVERLAY_AREA_IDX; ++j)
{
- uint32 area_id = worldOverlayEntry->areatableID[j];
- if (!area_id) // array have 0 only in empty tail
+ AreaTableEntry const* area = sAreaTableStore.LookupEntry(worldOverlayEntry->areatableID[j]);
+ if (!area)
break;
- int32 exploreFlag = GetAreaFlagByAreaID(area_id);
- if (exploreFlag < 0)
+ uint32 playerIndexOffset = uint32(area->exploreFlag) / 32;
+ if (playerIndexOffset >= PLAYER_EXPLORED_ZONES_SIZE)
continue;
- uint32 playerIndexOffset = uint32(exploreFlag) / 32;
- uint32 mask = 1 << (uint32(exploreFlag) % 32);
-
+ uint32 mask = 1 << (uint32(area->exploreFlag) % 32);
if (GetPlayer()->GetUInt32Value(PLAYER_EXPLORED_ZONES_1 + playerIndexOffset) & mask)
{
matchFound = true;
diff --git a/src/server/game/Battlegrounds/Zones/BattlegroundSA.cpp b/src/server/game/Battlegrounds/Zones/BattlegroundSA.cpp
index 9ab96383ed1..1942ac9d648 100644
--- a/src/server/game/Battlegrounds/Zones/BattlegroundSA.cpp
+++ b/src/server/game/Battlegrounds/Zones/BattlegroundSA.cpp
@@ -389,6 +389,8 @@ void BattlegroundSA::PostUpdateImpl(uint32 diff)
{
if (TotalTime >= BG_SA_ROUNDLENGTH)
{
+ CastSpellOnTeam(SPELL_END_OF_ROUND, ALLIANCE);
+ CastSpellOnTeam(SPELL_END_OF_ROUND, HORDE);
RoundScores[0].winner = Attackers;
RoundScores[0].time = BG_SA_ROUNDLENGTH;
TotalTime = 0;
@@ -401,8 +403,6 @@ void BattlegroundSA::PostUpdateImpl(uint32 diff)
ToggleTimer();
ResetObjs();
GetBgMap()->UpdateAreaDependentAuras();
- CastSpellOnTeam(SPELL_END_OF_ROUND, ALLIANCE);
- CastSpellOnTeam(SPELL_END_OF_ROUND, HORDE);
return;
}
}
@@ -410,6 +410,8 @@ void BattlegroundSA::PostUpdateImpl(uint32 diff)
{
if (TotalTime >= EndRoundTimer)
{
+ CastSpellOnTeam(SPELL_END_OF_ROUND, ALLIANCE);
+ CastSpellOnTeam(SPELL_END_OF_ROUND, HORDE);
RoundScores[1].time = BG_SA_ROUNDLENGTH;
RoundScores[1].winner = (Attackers == TEAM_ALLIANCE) ? TEAM_HORDE : TEAM_ALLIANCE;
if (RoundScores[0].time == RoundScores[1].time)
diff --git a/src/server/game/Chat/Chat.cpp b/src/server/game/Chat/Chat.cpp
index 011b68a2bb3..8fe0810f3b9 100644
--- a/src/server/game/Chat/Chat.cpp
+++ b/src/server/game/Chat/Chat.cpp
@@ -296,11 +296,11 @@ bool ChatHandler::ExecuteCommandInTable(std::vector<ChatCommand> const& table, c
uint32 areaId = player->GetAreaId();
std::string areaName = "Unknown";
std::string zoneName = "Unknown";
- if (AreaTableEntry const* area = GetAreaEntryByAreaID(areaId))
+ if (AreaTableEntry const* area = sAreaTableStore.LookupEntry(areaId))
{
int locale = GetSessionDbcLocale();
areaName = area->area_name[locale];
- if (AreaTableEntry const* zone = GetAreaEntryByAreaID(area->zone))
+ if (AreaTableEntry const* zone = sAreaTableStore.LookupEntry(area->zone))
zoneName = zone->area_name[locale];
}
diff --git a/src/server/game/Conditions/ConditionMgr.cpp b/src/server/game/Conditions/ConditionMgr.cpp
index d5367e919a3..4215a3a5d02 100644
--- a/src/server/game/Conditions/ConditionMgr.cpp
+++ b/src/server/game/Conditions/ConditionMgr.cpp
@@ -1708,7 +1708,7 @@ bool ConditionMgr::isConditionTypeValid(Condition* cond) const
}
case CONDITION_ZONEID:
{
- AreaTableEntry const* areaEntry = GetAreaEntryByAreaID(cond->ConditionValue1);
+ AreaTableEntry const* areaEntry = sAreaTableStore.LookupEntry(cond->ConditionValue1);
if (!areaEntry)
{
TC_LOG_ERROR("sql.sql", "%s Area (%u) does not exist, skipped.", cond->ToString(true).c_str(), cond->ConditionValue1);
diff --git a/src/server/game/DataStores/DBCStores.cpp b/src/server/game/DataStores/DBCStores.cpp
index c73350872cc..6c51c71fe7b 100644
--- a/src/server/game/DataStores/DBCStores.cpp
+++ b/src/server/game/DataStores/DBCStores.cpp
@@ -51,11 +51,9 @@ struct WMOAreaTableTripple
typedef std::map<WMOAreaTableTripple, WMOAreaTableEntry const*> WMOAreaInfoByTripple;
typedef std::multimap<uint32, CharSectionsEntry const*> CharSectionsMap;
-DBCStorage <AreaTableEntry> sAreaStore(AreaTableEntryfmt);
+DBCStorage <AreaTableEntry> sAreaTableStore(AreaTableEntryfmt);
DBCStorage <AreaGroupEntry> sAreaGroupStore(AreaGroupEntryfmt);
DBCStorage <AreaPOIEntry> sAreaPOIStore(AreaPOIEntryfmt);
-static AreaFlagByAreaID sAreaFlagByAreaID;
-static AreaFlagByMapID sAreaFlagByMapID; // for instances without generated *.map files
static WMOAreaInfoByTripple sWMOAreaInfoByTripple;
@@ -286,21 +284,7 @@ void LoadDBCStores(const std::string& dataPath)
StoreProblemList bad_dbc_files;
uint32 availableDbcLocales = 0xFFFFFFFF;
- LoadDBC(availableDbcLocales, bad_dbc_files, sAreaStore, dbcPath, "AreaTable.dbc");
-
- // must be after sAreaStore loading
- for (uint32 i = 0; i < sAreaStore.GetNumRows(); ++i) // areaflag numbered from 0
- {
- if (AreaTableEntry const* area = sAreaStore.LookupEntry(i))
- {
- // fill AreaId->DBC records
- sAreaFlagByAreaID.insert(AreaFlagByAreaID::value_type(uint16(area->ID), area->exploreFlag));
-
- // fill MapId->DBC records (skip sub zones and continents)
- if (area->zone == 0 && area->mapid != 0 && area->mapid != 1 && area->mapid != 530 && area->mapid != 571)
- sAreaFlagByMapID.insert(AreaFlagByMapID::value_type(area->mapid, area->exploreFlag));
- }
- }
+ LoadDBC(availableDbcLocales, bad_dbc_files, sAreaTableStore, dbcPath, "AreaTable.dbc");
LoadDBC(availableDbcLocales, bad_dbc_files, sAchievementStore, dbcPath, "Achievement.dbc", &CustomAchievementfmt, &CustomAchievementIndex);
LoadDBC(availableDbcLocales, bad_dbc_files, sAchievementCriteriaStore, dbcPath, "Achievement_Criteria.dbc");
@@ -721,7 +705,7 @@ void LoadDBCStores(const std::string& dataPath)
}
// Check loaded DBC files proper version
- if (!sAreaStore.LookupEntry(3617) || // last area (areaflag) added in 3.3.5a
+ if (!sAreaTableStore.LookupEntry(4987) || // last area added in 3.3.5a
!sCharTitlesStore.LookupEntry(177) || // last char title added in 3.3.5a
!sGemPropertiesStore.LookupEntry(1629) || // last added spell in 3.3.5a
!sItemStore.LookupEntry(56806) || // last gem property added in 3.3.5a
@@ -773,41 +757,13 @@ uint32 GetTalentSpellCost(uint32 spellId)
return 0;
}
-int32 GetAreaFlagByAreaID(uint32 area_id)
-{
- AreaFlagByAreaID::iterator i = sAreaFlagByAreaID.find(area_id);
- if (i == sAreaFlagByAreaID.end())
- return -1;
-
- return i->second;
-}
WMOAreaTableEntry const* GetWMOAreaTableEntryByTripple(int32 rootid, int32 adtid, int32 groupid)
{
WMOAreaInfoByTripple::iterator i = sWMOAreaInfoByTripple.find(WMOAreaTableTripple(rootid, adtid, groupid));
- if (i == sWMOAreaInfoByTripple.end())
- return NULL;
- return i->second;
-}
-
-AreaTableEntry const* GetAreaEntryByAreaID(uint32 area_id)
-{
- int32 areaflag = GetAreaFlagByAreaID(area_id);
- if (areaflag < 0)
+ if (i == sWMOAreaInfoByTripple.end())
return NULL;
-
- return sAreaStore.LookupEntry(areaflag);
-}
-
-AreaTableEntry const* GetAreaEntryByAreaFlagAndMap(uint32 area_flag, uint32 map_id)
-{
- if (area_flag)
- return sAreaStore.LookupEntry(area_flag);
-
- if (MapEntry const* mapEntry = sMapStore.LookupEntry(map_id))
- return GetAreaEntryByAreaID(mapEntry->linked_zone);
-
- return NULL;
+ return i->second;
}
char const* GetRaceName(uint8 race, uint8 locale)
@@ -822,15 +778,6 @@ char const* GetClassName(uint8 class_, uint8 locale)
return classEntry ? classEntry->name[locale] : NULL;
}
-uint32 GetAreaFlagByMapId(uint32 mapid)
-{
- AreaFlagByMapID::iterator i = sAreaFlagByMapID.find(mapid);
- if (i == sAreaFlagByMapID.end())
- return 0;
- else
- return i->second;
-}
-
uint32 GetVirtualMapForMapAndZone(uint32 mapid, uint32 zoneId)
{
if (mapid != 530 && mapid != 571) // speed for most cases
diff --git a/src/server/game/DataStores/DBCStores.h b/src/server/game/DataStores/DBCStores.h
index 14f59b04e6d..56ee1f618dd 100644
--- a/src/server/game/DataStores/DBCStores.h
+++ b/src/server/game/DataStores/DBCStores.h
@@ -33,11 +33,6 @@ char* GetPetName(uint32 petfamily, uint32 dbclang);
uint32 GetTalentSpellCost(uint32 spellId);
TalentSpellPos const* GetTalentSpellPos(uint32 spellId);
-int32 GetAreaFlagByAreaID(uint32 area_id); // -1 if not found
-AreaTableEntry const* GetAreaEntryByAreaID(uint32 area_id);
-AreaTableEntry const* GetAreaEntryByAreaFlagAndMap(uint32 area_flag, uint32 map_id);
-uint32 GetAreaFlagByMapId(uint32 mapid);
-
char const* GetRaceName(uint8 race, uint8 locale);
char const* GetClassName(uint8 class_, uint8 locale);
@@ -86,7 +81,7 @@ EmotesTextSoundEntry const* FindTextSoundEmoteFor(uint32 emote, uint32 race, uin
extern DBCStorage <AchievementEntry> sAchievementStore;
extern DBCStorage <AchievementCriteriaEntry> sAchievementCriteriaStore;
-extern DBCStorage <AreaTableEntry> sAreaStore;// recommend access using functions
+extern DBCStorage <AreaTableEntry> sAreaTableStore;
extern DBCStorage <AreaGroupEntry> sAreaGroupStore;
extern DBCStorage <AreaPOIEntry> sAreaPOIStore;
extern DBCStorage <AreaTriggerEntry> sAreaTriggerStore;
diff --git a/src/server/game/DataStores/DBCStructure.h b/src/server/game/DataStores/DBCStructure.h
index 2f4820d0353..b5dc4489148 100644
--- a/src/server/game/DataStores/DBCStructure.h
+++ b/src/server/game/DataStores/DBCStructure.h
@@ -509,7 +509,7 @@ struct AreaTableEntry
uint32 ID; // 0
uint32 mapid; // 1
uint32 zone; // 2 if 0 then it's zone, else it's zone id of this area
- uint32 exploreFlag; // 3, main index
+ uint32 exploreFlag; // 3
uint32 flags; // 4, unknown value but 312 for all cities
// 5-9 unused
int32 area_level; // 10
diff --git a/src/server/game/DataStores/DBCfmt.h b/src/server/game/DataStores/DBCfmt.h
index 22a01dae9f0..c61ec997bc2 100644
--- a/src/server/game/DataStores/DBCfmt.h
+++ b/src/server/game/DataStores/DBCfmt.h
@@ -23,7 +23,7 @@ char const Achievementfmt[] = "niixssssssssssssssssxxxxxxxxxxxxxxxxxxiixixxxxxxx
const std::string CustomAchievementfmt = "pppaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaapapaaaaaaaaaaaaaaaaaapp";
const std::string CustomAchievementIndex = "ID";
char const AchievementCriteriafmt[] = "niiiiiiiixxxxxxxxxxxxxxxxxiiiix";
-char const AreaTableEntryfmt[] = "iiinixxxxxissssssssssssssssxiiiiixxx";
+char const AreaTableEntryfmt[] = "niiiixxxxxissssssssssssssssxiiiiixxx";
char const AreaGroupEntryfmt[] = "niiiiiii";
char const AreaPOIEntryfmt[] = "niiiiiiiiiiifffixixxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxix";
char const AreaTriggerEntryfmt[] = "niffffffff";
diff --git a/src/server/game/Entities/Creature/Creature.cpp b/src/server/game/Entities/Creature/Creature.cpp
index 1497eb4922c..5d62b740947 100644
--- a/src/server/game/Entities/Creature/Creature.cpp
+++ b/src/server/game/Entities/Creature/Creature.cpp
@@ -369,13 +369,13 @@ bool Creature::InitEntry(uint32 entry, CreatureData const* data /*= nullptr*/)
SetByteValue(UNIT_FIELD_BYTES_0, 2, minfo->gender);
// Load creature equipment
- if (!data || data->equipmentId == 0)
- LoadEquipment(); // use default equipment (if available)
- else if (data && data->equipmentId != 0) // override, 0 means no equipment
+ if (data && data->equipmentId != 0)
{
m_originalEquipmentId = data->equipmentId;
LoadEquipment(data->equipmentId);
}
+ else
+ LoadEquipment(0, true);
SetName(normalInfo->Name); // at normal entry always
@@ -1409,6 +1409,7 @@ void Creature::LoadEquipment(int8 id, bool force /*= true*/)
SetUInt32Value(UNIT_VIRTUAL_ITEM_SLOT_ID + i, 0);
m_equipmentId = 0;
}
+
return;
}
@@ -1417,7 +1418,7 @@ void Creature::LoadEquipment(int8 id, bool force /*= true*/)
return;
m_equipmentId = id;
- for (uint8 i = 0; i < 3; ++i)
+ for (uint8 i = 0; i < MAX_EQUIPMENT_ITEMS; ++i)
SetUInt32Value(UNIT_VIRTUAL_ITEM_SLOT_ID + i, einfo->ItemEntry[i]);
}
@@ -2148,6 +2149,11 @@ bool Creature::CanCreatureAttack(Unit const* victim, bool /*force*/) const
if (GetMap()->IsDungeon())
return true;
+ // if the mob is actively being damaged, do not reset due to distance unless it's a world boss
+ if (!isWorldBoss())
+ if (time(NULL) - GetLastDamagedTime() <= MAX_AGGRO_RESET_TIME)
+ return true;
+
//Use AttackDistance in distance check if threat radius is lower. This prevents creature bounce in and out of combat every update tick.
float dist = std::max(GetAttackDistance(victim), sWorld->getFloatConfig(CONFIG_THREAT_RADIUS)) + m_CombatDistance;
diff --git a/src/server/game/Entities/GameObject/GameObject.cpp b/src/server/game/Entities/GameObject/GameObject.cpp
index b030f42bef7..1acfeacbf83 100644
--- a/src/server/game/Entities/GameObject/GameObject.cpp
+++ b/src/server/game/Entities/GameObject/GameObject.cpp
@@ -1399,7 +1399,10 @@ void GameObject::Use(Unit* user)
player->SendCinematicStart(info->camera.cinematicId);
if (info->camera.eventID)
+ {
GetMap()->ScriptsStart(sEventScripts, info->camera.eventID, player, this);
+ EventInform(info->camera.eventID, user);
+ }
return;
}
diff --git a/src/server/game/Entities/Player/Player.cpp b/src/server/game/Entities/Player/Player.cpp
index 8ce78f88906..9ae9f21c967 100644
--- a/src/server/game/Entities/Player/Player.cpp
+++ b/src/server/game/Entities/Player/Player.cpp
@@ -4682,6 +4682,7 @@ void Player::ResurrectPlayer(float restore_percent, bool applySickness)
// remove death flag + set aura
SetByteValue(UNIT_FIELD_BYTES_1, 3, 0x00);
+ RemoveFlag(PLAYER_FLAGS, PLAYER_FLAGS_IS_OUT_OF_BOUNDS);
// This must be called always even on Players with race != RACE_NIGHTELF in case of faction change
RemoveAurasDueToSpell(20584); // RACE_NIGHTELF speed bonuses
@@ -5102,10 +5103,10 @@ void Player::RepopAtGraveyard()
// note: this can be called also when the player is alive
// for example from WorldSession::HandleMovementOpcodes
- AreaTableEntry const* zone = GetAreaEntryByAreaID(GetAreaId());
+ AreaTableEntry const* zone = sAreaTableStore.LookupEntry(GetAreaId());
// Such zones are considered unreachable as a ghost and the player must be automatically revived
- if ((!IsAlive() && zone && zone->flags & AREA_FLAG_NEED_FLY) || GetTransport() || GetPositionZ() < -500.0f)
+ if ((!IsAlive() && zone && zone->flags & AREA_FLAG_NEED_FLY) || GetTransport() || GetPositionZ() < GetMap()->GetMinHeight(GetPositionX(), GetPositionY()))
{
ResurrectPlayer(0.5f);
SpawnCorpseBones();
@@ -5142,8 +5143,10 @@ void Player::RepopAtGraveyard()
GetSession()->SendPacket(&data);
}
}
- else if (GetPositionZ() < -500.0f)
+ else if (GetPositionZ() < GetMap()->GetMinHeight(GetPositionX(), GetPositionY()))
TeleportTo(m_homebindMapId, m_homebindX, m_homebindY, m_homebindZ, GetOrientation());
+
+ RemoveFlag(PLAYER_FLAGS, PLAYER_FLAGS_IS_OUT_OF_BOUNDS);
}
bool Player::CanJoinConstantChannelInZone(ChatChannelsEntry const* channel, AreaTableEntry const* zone)
@@ -5188,7 +5191,7 @@ void Player::UpdateLocalChannels(uint32 newZone)
if (GetSession()->PlayerLoading() && !IsBeingTeleportedFar())
return; // The client handles it automatically after loading, but not after teleporting
- AreaTableEntry const* current_zone = GetAreaEntryByAreaID(newZone);
+ AreaTableEntry const* current_zone = sAreaTableStore.LookupEntry(newZone);
if (!current_zone)
return;
@@ -6429,22 +6432,32 @@ void Player::CheckAreaExploreAndOutdoor()
return;
bool isOutdoor;
- uint16 areaFlag = GetBaseMap()->GetAreaFlag(GetPositionX(), GetPositionY(), GetPositionZ(), &isOutdoor);
+ uint32 areaId = GetBaseMap()->GetAreaId(GetPositionX(), GetPositionY(), GetPositionZ(), &isOutdoor);
+ AreaTableEntry const* areaEntry = sAreaTableStore.LookupEntry(areaId);
if (sWorld->getBoolConfig(CONFIG_VMAP_INDOOR_CHECK) && !isOutdoor)
RemoveAurasWithAttribute(SPELL_ATTR0_OUTDOORS_ONLY);
- if (areaFlag == 0xffff)
+ if (!areaId)
return;
- int offset = areaFlag / 32;
+
+ if (!areaEntry)
+ {
+ TC_LOG_ERROR("entities.player", "Player '%s' (%s) discovered unknown area (x: %f y: %f z: %f map: %u)",
+ GetName().c_str(), GetGUID().ToString().c_str(), GetPositionX(), GetPositionY(), GetPositionZ(), GetMapId());
+ return;
+ }
+
+ uint32 offset = areaEntry->exploreFlag / 32;
if (offset >= PLAYER_EXPLORED_ZONES_SIZE)
{
- TC_LOG_ERROR("entities.player", "Wrong area flag %u in map data for (X: %f Y: %f) point to field PLAYER_EXPLORED_ZONES_1 + %u ( %u must be < %u ).", areaFlag, GetPositionX(), GetPositionY(), offset, offset, PLAYER_EXPLORED_ZONES_SIZE);
+ TC_LOG_ERROR("entities.player", "Player::CheckAreaExploreAndOutdoor: Wrong area flag %u in map data for (X: %f Y: %f) point to field PLAYER_EXPLORED_ZONES_1 + %u ( %u must be < %u ).",
+ areaEntry->exploreFlag, GetPositionX(), GetPositionY(), offset, offset, PLAYER_EXPLORED_ZONES_SIZE);
return;
}
- uint32 val = (uint32)(1 << (areaFlag % 32));
+ uint32 val = (uint32)(1 << (areaEntry->exploreFlag % 32));
uint32 currFields = GetUInt32Value(PLAYER_EXPLORED_ZONES_1 + offset);
if (!(currFields & val))
@@ -6453,19 +6466,11 @@ void Player::CheckAreaExploreAndOutdoor()
UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_EXPLORE_AREA);
- AreaTableEntry const* areaEntry = GetAreaEntryByAreaFlagAndMap(areaFlag, GetMapId());
- if (!areaEntry)
- {
- TC_LOG_ERROR("entities.player", "Player %u discovered unknown area (x: %f y: %f z: %f map: %u", GetGUID().GetCounter(), GetPositionX(), GetPositionY(), GetPositionZ(), GetMapId());
- return;
- }
-
if (areaEntry->area_level > 0)
{
- uint32 area = areaEntry->ID;
if (getLevel() >= sWorld->getIntConfig(CONFIG_MAX_PLAYER_LEVEL))
{
- SendExplorationExperience(area, 0);
+ SendExplorationExperience(areaId, 0);
}
else
{
@@ -6489,9 +6494,9 @@ void Player::CheckAreaExploreAndOutdoor()
}
GiveXP(XP, NULL);
- SendExplorationExperience(area, XP);
+ SendExplorationExperience(areaId, XP);
}
- TC_LOG_DEBUG("entities.player", "Player %u discovered a new area: %u", GetGUID().GetCounter(), area);
+ TC_LOG_DEBUG("entities.player", "Player '%s' (%s) discovered a new area: %u", GetName().c_str(),GetGUID().ToString().c_str(), areaId);
}
}
}
@@ -7061,7 +7066,7 @@ void Player::UpdateArea(uint32 newArea)
// so apply them accordingly
m_areaUpdateId = newArea;
- AreaTableEntry const* area = GetAreaEntryByAreaID(newArea);
+ AreaTableEntry const* area = sAreaTableStore.LookupEntry(newArea);
pvpInfo.IsInFFAPvPArea = area && (area->flags & AREA_FLAG_ARENA);
UpdatePvPState(true);
@@ -7109,7 +7114,7 @@ void Player::UpdateZone(uint32 newZone, uint32 newArea)
// zone changed, so area changed as well, update it
UpdateArea(newArea);
- AreaTableEntry const* zone = GetAreaEntryByAreaID(newZone);
+ AreaTableEntry const* zone = sAreaTableStore.LookupEntry(newZone);
if (!zone)
return;
@@ -26154,11 +26159,11 @@ std::string Player::GetMapAreaAndZoneString()
uint32 areaId = GetAreaId();
std::string areaName = "Unknown";
std::string zoneName = "Unknown";
- if (AreaTableEntry const* area = GetAreaEntryByAreaID(areaId))
+ if (AreaTableEntry const* area = sAreaTableStore.LookupEntry(areaId))
{
int locale = GetSession()->GetSessionDbcLocale();
areaName = area->area_name[locale];
- if (AreaTableEntry const* zone = GetAreaEntryByAreaID(area->zone))
+ if (AreaTableEntry const* zone = sAreaTableStore.LookupEntry(area->zone))
zoneName = zone->area_name[locale];
}
diff --git a/src/server/game/Entities/Unit/Unit.cpp b/src/server/game/Entities/Unit/Unit.cpp
index 3aed5fde7b3..c224ef78ec8 100644
--- a/src/server/game/Entities/Unit/Unit.cpp
+++ b/src/server/game/Entities/Unit/Unit.cpp
@@ -8328,8 +8328,6 @@ bool Unit::HandleProcTriggerSpell(Unit* victim, uint32 damage, AuraEffect* trigg
case 52914:
case 52915:
case 52910:
- // Honor Among Thieves
- case 52916:
{
target = triggeredByAura->GetBase()->GetCaster();
if (!target)
@@ -12750,7 +12748,7 @@ Unit* Creature::SelectVictim()
}
}
else
- return NULL;
+ return nullptr;
if (target && _IsTargetAcceptable(target) && CanCreatureAttack(target))
{
@@ -12759,14 +12757,6 @@ Unit* Creature::SelectVictim()
return target;
}
- // Case where mob is being kited.
- // Mob may not be in range to attack or may have dropped target. In any case,
- // don't evade if damage received within the last 10 seconds
- // Does not apply to world bosses to prevent kiting to cities
- if (!isWorldBoss() && !GetInstanceId())
- if (time(NULL) - GetLastDamagedTime() <= MAX_AGGRO_RESET_TIME)
- return target;
-
// last case when creature must not go to evade mode:
// it in combat but attacker not make any damage and not enter to aggro radius to have record in threat list
// for example at owner command to pet attack some far away creature
@@ -12775,12 +12765,12 @@ Unit* Creature::SelectVictim()
{
if ((*itr) && !CanCreatureAttack(*itr) && (*itr)->GetTypeId() != TYPEID_PLAYER
&& !(*itr)->ToCreature()->HasUnitTypeMask(UNIT_MASK_CONTROLABLE_GUARDIAN))
- return NULL;
+ return nullptr;
}
/// @todo a vehicle may eat some mob, so mob should not evade
if (GetVehicle())
- return NULL;
+ return nullptr;
// search nearby enemy before enter evade mode
if (HasReactState(REACT_AGGRESSIVE))
@@ -12798,17 +12788,17 @@ Unit* Creature::SelectVictim()
{
if ((*itr)->GetBase()->IsPermanent())
{
- AI()->EnterEvadeMode();
+ AI()->EnterEvadeMode(CreatureAI::EVADE_REASON_OTHER);
break;
}
}
- return NULL;
+ return nullptr;
}
// enter in evade mode in other case
AI()->EnterEvadeMode(CreatureAI::EVADE_REASON_NO_HOSTILES);
- return NULL;
+ return nullptr;
}
//======================================================================
diff --git a/src/server/game/Globals/ObjectMgr.cpp b/src/server/game/Globals/ObjectMgr.cpp
index d2064092a65..f45634e9684 100644
--- a/src/server/game/Globals/ObjectMgr.cpp
+++ b/src/server/game/Globals/ObjectMgr.cpp
@@ -1756,7 +1756,7 @@ void ObjectMgr::LoadCreatures()
if (!ok)
continue;
- // -1 random, 0 no equipment,
+ // -1 random, 0 no equipment
if (data.equipmentId != 0)
{
if (!GetEquipmentInfo(data.id, data.equipmentId))
@@ -2773,7 +2773,7 @@ void ObjectMgr::LoadItemTemplates()
itemTemplate.ItemSet = 0;
}
- if (itemTemplate.Area && !GetAreaEntryByAreaID(itemTemplate.Area))
+ if (itemTemplate.Area && !sAreaTableStore.LookupEntry(itemTemplate.Area))
TC_LOG_ERROR("sql.sql", "Item (Entry: %u) has wrong Area (%u)", entry, itemTemplate.Area);
if (itemTemplate.Map && !sMapStore.LookupEntry(itemTemplate.Map))
@@ -4143,7 +4143,7 @@ void ObjectMgr::LoadQuests()
// client quest log visual (area case)
if (qinfo->ZoneOrSort > 0)
{
- if (!GetAreaEntryByAreaID(qinfo->ZoneOrSort))
+ if (!sAreaTableStore.LookupEntry(qinfo->ZoneOrSort))
{
TC_LOG_ERROR("sql.sql", "Quest %u has `ZoneOrSort` = %u (zone case) but zone with this id does not exist.",
qinfo->GetQuestId(), qinfo->ZoneOrSort);
@@ -5956,7 +5956,7 @@ void ObjectMgr::LoadGraveyardZones()
continue;
}
- AreaTableEntry const* areaEntry = GetAreaEntryByAreaID(zoneId);
+ AreaTableEntry const* areaEntry = sAreaTableStore.LookupEntry(zoneId);
if (!areaEntry)
{
TC_LOG_ERROR("sql.sql", "Table `game_graveyard_zone` has a record for not existing zone id (%u), skipped.", zoneId);
@@ -7796,7 +7796,7 @@ void ObjectMgr::LoadFishingBaseSkillLevel()
uint32 entry = fields[0].GetUInt32();
int32 skill = fields[1].GetInt16();
- AreaTableEntry const* fArea = GetAreaEntryByAreaID(entry);
+ AreaTableEntry const* fArea = sAreaTableStore.LookupEntry(entry);
if (!fArea)
{
TC_LOG_ERROR("sql.sql", "AreaId %u defined in `skill_fishing_base_level` does not exist", entry);
diff --git a/src/server/game/Grids/GridDefines.h b/src/server/game/Grids/GridDefines.h
index 162c39b951b..24c9100b222 100644
--- a/src/server/game/Grids/GridDefines.h
+++ b/src/server/game/Grids/GridDefines.h
@@ -226,7 +226,7 @@ namespace Trinity
inline bool IsValidMapCoord(float x, float y, float z)
{
- return IsValidMapCoord(x, y) && std::isfinite(z);
+ return IsValidMapCoord(x, y) && IsValidMapCoord(z);
}
inline bool IsValidMapCoord(float x, float y, float z, float o)
diff --git a/src/server/game/Grids/Notifiers/GridNotifiers.cpp b/src/server/game/Grids/Notifiers/GridNotifiers.cpp
index c48d1947eec..571d56b618e 100644
--- a/src/server/game/Grids/Notifiers/GridNotifiers.cpp
+++ b/src/server/game/Grids/Notifiers/GridNotifiers.cpp
@@ -131,7 +131,7 @@ inline void CreatureUnitRelocationWorker(Creature* c, Unit* u)
if (!u->IsAlive() || !c->IsAlive() || c == u || u->IsInFlight())
return;
- if (c->HasReactState(REACT_AGGRESSIVE) && !c->HasUnitState(UNIT_STATE_SIGHTLESS))
+ if ((c->HasReactState(REACT_AGGRESSIVE) || c->IsTrigger()) && !c->HasUnitState(UNIT_STATE_SIGHTLESS))
{
if (c->IsAIEnabled && c->CanSeeOrDetect(u, false, true))
c->AI()->MoveInLineOfSight_Safe(u);
diff --git a/src/server/game/Handlers/ChannelHandler.cpp b/src/server/game/Handlers/ChannelHandler.cpp
index 976860e8cc0..9285f4247b2 100644
--- a/src/server/game/Handlers/ChannelHandler.cpp
+++ b/src/server/game/Handlers/ChannelHandler.cpp
@@ -39,7 +39,7 @@ void WorldSession::HandleJoinChannel(WorldPacket& recvPacket)
if (!channel)
return;
- AreaTableEntry const* zone = GetAreaEntryByAreaID(GetPlayer()->GetZoneId());
+ AreaTableEntry const* zone = sAreaTableStore.LookupEntry(GetPlayer()->GetZoneId());
if (!zone || !GetPlayer()->CanJoinConstantChannelInZone(channel, zone))
return;
}
diff --git a/src/server/game/Handlers/MiscHandler.cpp b/src/server/game/Handlers/MiscHandler.cpp
index 6cd8bfc014e..5f5a66e7b20 100644
--- a/src/server/game/Handlers/MiscHandler.cpp
+++ b/src/server/game/Handlers/MiscHandler.cpp
@@ -319,7 +319,7 @@ void WorldSession::HandleWhoOpcode(WorldPacket& recvData)
continue;
std::string aname;
- if (AreaTableEntry const* areaEntry = GetAreaEntryByAreaID(pzoneid))
+ if (AreaTableEntry const* areaEntry = sAreaTableStore.LookupEntry(pzoneid))
aname = areaEntry->area_name[GetSessionDbcLocale()];
bool s_show = true;
@@ -1753,7 +1753,7 @@ void WorldSession::HandleHearthAndResurrect(WorldPacket& /*recvData*/)
return;
}
- AreaTableEntry const* atEntry = GetAreaEntryByAreaID(_player->GetAreaId());
+ AreaTableEntry const* atEntry = sAreaTableStore.LookupEntry(_player->GetAreaId());
if (!atEntry || !(atEntry->flags & AREA_FLAG_WINTERGRASP_2))
return;
diff --git a/src/server/game/Handlers/MovementHandler.cpp b/src/server/game/Handlers/MovementHandler.cpp
index eea5c62fbd1..02702fc5622 100644
--- a/src/server/game/Handlers/MovementHandler.cpp
+++ b/src/server/game/Handlers/MovementHandler.cpp
@@ -386,7 +386,7 @@ void WorldSession::HandleMovementOpcodes(WorldPacket& recvData)
plrMover->UpdateFallInformationIfNeed(movementInfo, opcode);
- if (movementInfo.pos.GetPositionZ() < -500.0f)
+ if (movementInfo.pos.GetPositionZ() < plrMover->GetMap()->GetMinHeight(movementInfo.pos.GetPositionX(), movementInfo.pos.GetPositionY()))
{
if (!(plrMover->GetBattleground() && plrMover->GetBattleground()->HandlePlayerUnderMap(_player)))
{
@@ -395,6 +395,7 @@ void WorldSession::HandleMovementOpcodes(WorldPacket& recvData)
/// @todo discard movement packets after the player is rooted
if (plrMover->IsAlive())
{
+ plrMover->SetFlag(PLAYER_FLAGS, PLAYER_FLAGS_IS_OUT_OF_BOUNDS);
plrMover->EnvironmentalDamage(DAMAGE_FALL_TO_VOID, GetPlayer()->GetMaxHealth());
// player can be alive if GM/etc
// change the death state to CORPSE to prevent the death timer from
diff --git a/src/server/game/Loot/LootMgr.cpp b/src/server/game/Loot/LootMgr.cpp
index 530bcd2902c..19dc210ea5b 100644
--- a/src/server/game/Loot/LootMgr.cpp
+++ b/src/server/game/Loot/LootMgr.cpp
@@ -1580,8 +1580,8 @@ void LoadLootTemplates_Fishing()
uint32 count = LootTemplates_Fishing.LoadAndCollectLootIds(lootIdSet);
// remove real entries and check existence loot
- for (uint32 i = 1; i < sAreaStore.GetNumRows(); ++i)
- if (AreaTableEntry const* areaEntry = sAreaStore.LookupEntry(i))
+ for (uint32 i = 1; i < sAreaTableStore.GetNumRows(); ++i)
+ if (AreaTableEntry const* areaEntry = sAreaTableStore.LookupEntry(i))
if (lootIdSet.find(areaEntry->ID) != lootIdSet.end())
lootIdSet.erase(areaEntry->ID);
diff --git a/src/server/game/Maps/Map.cpp b/src/server/game/Maps/Map.cpp
index a2cb84359f2..1560d4bdd08 100644
--- a/src/server/game/Maps/Map.cpp
+++ b/src/server/game/Maps/Map.cpp
@@ -37,7 +37,7 @@
#include "VMapFactory.h"
u_map_magic MapMagic = { {'M','A','P','S'} };
-u_map_magic MapVersionMagic = { {'v','1','.','3'} };
+u_map_magic MapVersionMagic = { {'v','1','.','7'} };
u_map_magic MapAreaMagic = { {'A','R','E','A'} };
u_map_magic MapHeightMagic = { {'M','H','G','T'} };
u_map_magic MapLiquidMagic = { {'M','L','I','Q'} };
@@ -1644,13 +1644,15 @@ GridMap::GridMap()
_flags = 0;
// Area data
_gridArea = 0;
- _areaMap = NULL;
+ _areaMap = nullptr;
// Height level data
_gridHeight = INVALID_HEIGHT;
_gridGetHeight = &GridMap::getHeightFromFlat;
_gridIntHeightMultiplier = 0;
- m_V9 = NULL;
- m_V8 = NULL;
+ m_V9 = nullptr;
+ m_V8 = nullptr;
+ _maxHeight = nullptr;
+ _minHeight = nullptr;
// Liquid data
_liquidType = 0;
_liquidOffX = 0;
@@ -1658,9 +1660,9 @@ GridMap::GridMap()
_liquidWidth = 0;
_liquidHeight = 0;
_liquidLevel = INVALID_HEIGHT;
- _liquidEntry = NULL;
- _liquidFlags = NULL;
- _liquidMap = NULL;
+ _liquidEntry = nullptr;
+ _liquidFlags = nullptr;
+ _liquidMap = nullptr;
}
GridMap::~GridMap()
@@ -1723,15 +1725,19 @@ void GridMap::unloadData()
delete[] _areaMap;
delete[] m_V9;
delete[] m_V8;
+ delete[] _maxHeight;
+ delete[] _minHeight;
delete[] _liquidEntry;
delete[] _liquidFlags;
delete[] _liquidMap;
- _areaMap = NULL;
- m_V9 = NULL;
- m_V8 = NULL;
- _liquidEntry = NULL;
- _liquidFlags = NULL;
- _liquidMap = NULL;
+ _areaMap = nullptr;
+ m_V9 = nullptr;
+ m_V8 = nullptr;
+ _maxHeight = nullptr;
+ _minHeight = nullptr;
+ _liquidEntry = nullptr;
+ _liquidFlags = nullptr;
+ _liquidMap = nullptr;
_gridGetHeight = &GridMap::getHeightFromFlat;
}
@@ -1746,7 +1752,7 @@ bool GridMap::loadAreaData(FILE* in, uint32 offset, uint32 /*size*/)
_gridArea = header.gridArea;
if (!(header.flags & MAP_AREA_NO_AREA))
{
- _areaMap = new uint16 [16*16];
+ _areaMap = new uint16[16 * 16];
if (fread(_areaMap, sizeof(uint16), 16*16, in) != 16*16)
return false;
}
@@ -1796,6 +1802,16 @@ bool GridMap::loadHeightData(FILE* in, uint32 offset, uint32 /*size*/)
}
else
_gridGetHeight = &GridMap::getHeightFromFlat;
+
+ if (header.flags & MAP_HEIGHT_HAS_FLIGHT_BOUNDS)
+ {
+ _maxHeight = new float[16 * 16];
+ _minHeight = new float[16 * 16];
+ if (fread(_maxHeight, sizeof(float), 16 * 16, in) != 16 * 16 ||
+ fread(_minHeight, sizeof(float), 16 * 16, in) != 16 * 16)
+ return false;
+ }
+
return true;
}
@@ -2066,6 +2082,18 @@ float GridMap::getHeightFromUint16(float x, float y) const
return (float)((a * x) + (b * y) + c)*_gridIntHeightMultiplier + _gridHeight;
}
+float GridMap::getMinHeight(float x, float y) const
+{
+ if (!_minHeight)
+ return -500.0f;
+
+ x = 16 * (CENTER_GRID_ID - x / SIZE_OF_GRIDS);
+ y = 16 * (CENTER_GRID_ID - y / SIZE_OF_GRIDS);
+ int lx = (int)x & 15;
+ int ly = (int)y & 15;
+ return _minHeight[lx * 16 + ly];
+}
+
float GridMap::getLiquidLevel(float x, float y) const
{
if (!_liquidMap)
@@ -2125,12 +2153,12 @@ inline ZLiquidStatus GridMap::getLiquidStatus(float x, float y, float z, uint8 R
uint32 liqTypeIdx = liquidEntry->Type;
if (entry < 21)
{
- if (AreaTableEntry const* area = GetAreaEntryByAreaFlagAndMap(getArea(x, y), MAPID_INVALID))
+ if (AreaTableEntry const* area = sAreaTableStore.LookupEntry(getArea(x, y)))
{
uint32 overrideLiquid = area->LiquidTypeOverride[liquidEntry->Type];
if (!overrideLiquid && area->zone)
{
- area = GetAreaEntryByAreaID(area->zone);
+ area = sAreaTableStore.LookupEntry(area->zone);
if (area)
overrideLiquid = area->LiquidTypeOverride[liquidEntry->Type];
}
@@ -2266,6 +2294,14 @@ float Map::GetHeight(float x, float y, float z, bool checkVMap /*= true*/, float
return mapHeight; // explicitly use map data
}
+float Map::GetMinHeight(float x, float y) const
+{
+ if (GridMap const* grid = const_cast<Map*>(this)->GetGrid(x, y))
+ return grid->getMinHeight(x, y);
+
+ return -500.0f;
+}
+
inline bool IsOutdoorWMO(uint32 mogpFlags, int32 /*adtId*/, int32 /*rootId*/, int32 /*groupId*/, WMOAreaTableEntry const* wmoEntry, AreaTableEntry const* atEntry)
{
bool outdoor = true;
@@ -2304,7 +2340,7 @@ bool Map::IsOutdoors(float x, float y, float z) const
if (wmoEntry)
{
TC_LOG_DEBUG("maps", "Got WMOAreaTableEntry! flag %u, areaid %u", wmoEntry->Flags, wmoEntry->areaId);
- atEntry = GetAreaEntryByAreaID(wmoEntry->areaId);
+ atEntry = sAreaTableStore.LookupEntry(wmoEntry->areaId);
}
return IsOutdoorWMO(mogpFlags, adtId, rootId, groupId, wmoEntry, atEntry);
}
@@ -2328,7 +2364,7 @@ bool Map::GetAreaInfo(float x, float y, float z, uint32 &flags, int32 &adtId, in
return false;
}
-uint16 Map::GetAreaFlag(float x, float y, float z, bool *isOutdoors) const
+uint32 Map::GetAreaId(float x, float y, float z, bool *isOutdoors) const
{
uint32 mogpFlags;
int32 adtId, rootId, groupId;
@@ -2341,20 +2377,20 @@ uint16 Map::GetAreaFlag(float x, float y, float z, bool *isOutdoors) const
haveAreaInfo = true;
wmoEntry = GetWMOAreaTableEntryByTripple(rootId, adtId, groupId);
if (wmoEntry)
- atEntry = GetAreaEntryByAreaID(wmoEntry->areaId);
+ atEntry = sAreaTableStore.LookupEntry(wmoEntry->areaId);
}
- uint16 areaflag;
+ uint32 areaId;
if (atEntry)
- areaflag = atEntry->exploreFlag;
+ areaId = atEntry->ID;
else
{
if (GridMap* gmap = const_cast<Map*>(this)->GetGrid(x, y))
- areaflag = gmap->getArea(x, y);
+ areaId = gmap->getArea(x, y);
// this used while not all *.map files generated (instances)
else
- areaflag = GetAreaFlagByMapId(i_mapEntry->MapID);
+ areaId = i_mapEntry->linked_zone;
}
if (isOutdoors)
@@ -2364,8 +2400,31 @@ uint16 Map::GetAreaFlag(float x, float y, float z, bool *isOutdoors) const
else
*isOutdoors = true;
}
- return areaflag;
- }
+ return areaId;
+}
+
+uint32 Map::GetAreaId(float x, float y, float z) const
+{
+ return GetAreaId(x, y, z, nullptr);
+}
+
+uint32 Map::GetZoneId(float x, float y, float z) const
+{
+ uint32 areaId = GetAreaId(x, y, z);
+ if (AreaTableEntry const* area = sAreaTableStore.LookupEntry(areaId))
+ if (area->zone)
+ return area->zone;
+
+ return areaId;
+}
+
+void Map::GetZoneAndAreaId(uint32& zoneid, uint32& areaid, float x, float y, float z) const
+{
+ areaid = zoneid = GetAreaId(x, y, z);
+ if (AreaTableEntry const* area = sAreaTableStore.LookupEntry(areaid))
+ if (area->zone)
+ zoneid = area->zone;
+}
uint8 Map::GetTerrainType(float x, float y) const
{
@@ -2401,12 +2460,12 @@ ZLiquidStatus Map::getLiquidStatus(float x, float y, float z, uint8 ReqLiquidTyp
if (liquid_type && liquid_type < 21)
{
- if (AreaTableEntry const* area = GetAreaEntryByAreaFlagAndMap(GetAreaFlag(x, y, z), GetId()))
+ if (AreaTableEntry const* area = sAreaTableStore.LookupEntry(GetAreaId(x, y, z)))
{
uint32 overrideLiquid = area->LiquidTypeOverride[liquidFlagType];
if (!overrideLiquid && area->zone)
{
- area = GetAreaEntryByAreaID(area->zone);
+ area = sAreaTableStore.LookupEntry(area->zone);
if (area)
overrideLiquid = area->LiquidTypeOverride[liquidFlagType];
}
@@ -2468,34 +2527,6 @@ float Map::GetWaterLevel(float x, float y) const
return 0;
}
-uint32 Map::GetAreaIdByAreaFlag(uint16 areaflag, uint32 map_id)
-{
- AreaTableEntry const* entry = GetAreaEntryByAreaFlagAndMap(areaflag, map_id);
-
- if (entry)
- return entry->ID;
- else
- return 0;
-}
-
-uint32 Map::GetZoneIdByAreaFlag(uint16 areaflag, uint32 map_id)
-{
- AreaTableEntry const* entry = GetAreaEntryByAreaFlagAndMap(areaflag, map_id);
-
- if (entry)
- return (entry->zone != 0) ? entry->zone : entry->ID;
- else
- return 0;
-}
-
-void Map::GetZoneAndAreaIdByAreaFlag(uint32& zoneid, uint32& areaid, uint16 areaflag, uint32 map_id)
-{
- AreaTableEntry const* entry = GetAreaEntryByAreaFlagAndMap(areaflag, map_id);
-
- areaid = entry ? entry->ID : 0;
- zoneid = entry ? ((entry->zone != 0) ? entry->zone : entry->ID) : 0;
-}
-
bool Map::isInLineOfSight(float x1, float y1, float z1, float x2, float y2, float z2, uint32 phasemask) const
{
return VMAP::VMapFactory::createOrGetVMapManager()->isInLineOfSight(GetId(), x1, y1, z1, x2, y2, z2)
diff --git a/src/server/game/Maps/Map.h b/src/server/game/Maps/Map.h
index 01db38d9c30..13d48db0f9d 100644
--- a/src/server/game/Maps/Map.h
+++ b/src/server/game/Maps/Map.h
@@ -98,9 +98,10 @@ struct map_areaHeader
uint16 gridArea;
};
-#define MAP_HEIGHT_NO_HEIGHT 0x0001
-#define MAP_HEIGHT_AS_INT16 0x0002
-#define MAP_HEIGHT_AS_INT8 0x0004
+#define MAP_HEIGHT_NO_HEIGHT 0x0001
+#define MAP_HEIGHT_AS_INT16 0x0002
+#define MAP_HEIGHT_AS_INT8 0x0004
+#define MAP_HEIGHT_HAS_FLIGHT_BOUNDS 0x0008
struct map_heightHeader
{
@@ -166,6 +167,8 @@ class GridMap
uint16* m_uint16_V8;
uint8* m_uint8_V8;
};
+ float* _maxHeight;
+ float* _minHeight;
// Height level data
float _gridHeight;
float _gridIntHeightMultiplier;
@@ -206,6 +209,7 @@ public:
uint16 getArea(float x, float y) const;
inline float getHeight(float x, float y) const {return (this->*_gridGetHeight)(x, y);}
+ float getMinHeight(float x, float y) const;
float getLiquidLevel(float x, float y) const;
uint8 getTerrainType(float x, float y) const;
ZLiquidStatus getLiquidStatus(float x, float y, float z, uint8 ReqLiquidType, LiquidData* data = 0);
@@ -326,11 +330,15 @@ class Map : public GridRefManager<NGridType>
// some calls like isInWater should not use vmaps due to processor power
// can return INVALID_HEIGHT if under z+2 z coord not found height
float GetHeight(float x, float y, float z, bool checkVMap = true, float maxSearchDist = DEFAULT_HEIGHT_SEARCH) const;
+ float GetMinHeight(float x, float y) const;
ZLiquidStatus getLiquidStatus(float x, float y, float z, uint8 ReqLiquidType, LiquidData* data = nullptr) const;
- uint16 GetAreaFlag(float x, float y, float z, bool *isOutdoors=nullptr) const;
- bool GetAreaInfo(float x, float y, float z, uint32 &mogpflags, int32 &adtId, int32 &rootId, int32 &groupId) const;
+ uint32 GetAreaId(float x, float y, float z, bool *isOutdoors) const;
+ bool GetAreaInfo(float x, float y, float z, uint32& mogpflags, int32& adtId, int32& rootId, int32& groupId) const;
+ uint32 GetAreaId(float x, float y, float z) const;
+ uint32 GetZoneId(float x, float y, float z) const;
+ void GetZoneAndAreaId(uint32& zoneid, uint32& areaid, float x, float y, float z) const;
bool IsOutdoors(float x, float y, float z) const;
@@ -339,25 +347,6 @@ class Map : public GridRefManager<NGridType>
bool IsInWater(float x, float y, float z, LiquidData* data = nullptr) const;
bool IsUnderWater(float x, float y, float z) const;
- static uint32 GetAreaIdByAreaFlag(uint16 areaflag, uint32 map_id);
- static uint32 GetZoneIdByAreaFlag(uint16 areaflag, uint32 map_id);
- static void GetZoneAndAreaIdByAreaFlag(uint32& zoneid, uint32& areaid, uint16 areaflag, uint32 map_id);
-
- uint32 GetAreaId(float x, float y, float z) const
- {
- return GetAreaIdByAreaFlag(GetAreaFlag(x, y, z), GetId());
- }
-
- uint32 GetZoneId(float x, float y, float z) const
- {
- return GetZoneIdByAreaFlag(GetAreaFlag(x, y, z), GetId());
- }
-
- void GetZoneAndAreaId(uint32& zoneid, uint32& areaid, float x, float y, float z) const
- {
- GetZoneAndAreaIdByAreaFlag(zoneid, areaid, GetAreaFlag(x, y, z), GetId());
- }
-
void MoveAllCreaturesInMoveList();
void MoveAllGameObjectsInMoveList();
void MoveAllDynamicObjectsInMoveList();
diff --git a/src/server/game/Maps/MapManager.h b/src/server/game/Maps/MapManager.h
index 51bb418bdf5..7f9621593d4 100644
--- a/src/server/game/Maps/MapManager.h
+++ b/src/server/game/Maps/MapManager.h
@@ -42,22 +42,20 @@ class MapManager
Map* CreateMap(uint32 mapId, Player* player, uint32 loginInstanceId=0);
Map* FindMap(uint32 mapId, uint32 instanceId) const;
- uint16 GetAreaFlag(uint32 mapid, float x, float y, float z) const
- {
- Map const* m = const_cast<MapManager*>(this)->CreateBaseMap(mapid);
- return m->GetAreaFlag(x, y, z);
- }
uint32 GetAreaId(uint32 mapid, float x, float y, float z) const
{
- return Map::GetAreaIdByAreaFlag(GetAreaFlag(mapid, x, y, z), mapid);
+ Map const* m = const_cast<MapManager*>(this)->CreateBaseMap(mapid);
+ return m->GetAreaId(x, y, z);
}
uint32 GetZoneId(uint32 mapid, float x, float y, float z) const
{
- return Map::GetZoneIdByAreaFlag(GetAreaFlag(mapid, x, y, z), mapid);
+ Map const* m = const_cast<MapManager*>(this)->CreateBaseMap(mapid);
+ return m->GetZoneId(x, y, z);
}
void GetZoneAndAreaId(uint32& zoneid, uint32& areaid, uint32 mapid, float x, float y, float z)
{
- Map::GetZoneAndAreaIdByAreaFlag(zoneid, areaid, GetAreaFlag(mapid, x, y, z), mapid);
+ Map const* m = const_cast<MapManager*>(this)->CreateBaseMap(mapid);
+ m->GetZoneAndAreaId(zoneid, areaid, x, y, z);
}
void Initialize(void);
diff --git a/src/server/game/OutdoorPvP/OutdoorPvP.cpp b/src/server/game/OutdoorPvP/OutdoorPvP.cpp
index 868cba9a5b9..d329ab27de9 100644
--- a/src/server/game/OutdoorPvP/OutdoorPvP.cpp
+++ b/src/server/game/OutdoorPvP/OutdoorPvP.cpp
@@ -687,7 +687,7 @@ void OutdoorPvP::BroadcastWorker(Worker& _worker, uint32 zoneId)
void OutdoorPvP::SetMapFromZone(uint32 zone)
{
- AreaTableEntry const* areaTable = GetAreaEntryByAreaID(zone);
+ AreaTableEntry const* areaTable = sAreaTableStore.LookupEntry(zone);
ASSERT(areaTable);
Map* map = sMapMgr->CreateBaseMap(areaTable->mapid);
ASSERT(!map->Instanceable());
diff --git a/src/server/game/Spells/Auras/SpellAuraEffects.cpp b/src/server/game/Spells/Auras/SpellAuraEffects.cpp
index 6a10d113553..207908c6d51 100644
--- a/src/server/game/Spells/Auras/SpellAuraEffects.cpp
+++ b/src/server/game/Spells/Auras/SpellAuraEffects.cpp
@@ -4683,11 +4683,6 @@ void AuraEffect::HandleAuraDummy(AuraApplication const* aurApp, uint8 mode, bool
if (target->GetTypeId() == TYPEID_PLAYER)
target->ToPlayer()->RemoveAmmo(); // not use ammo and not allow use
break;
- case 52916: // Honor Among Thieves
- if (target->GetTypeId() == TYPEID_PLAYER)
- if (Unit* spellTarget = ObjectAccessor::GetUnit(*target, target->ToPlayer()->GetComboTarget()))
- target->CastSpell(spellTarget, 51699, true);
- break;
case 71563:
if (Aura* newAura = target->AddAura(71564, target))
newAura->SetStackAmount(newAura->GetSpellInfo()->StackAmount);
@@ -5619,25 +5614,6 @@ void AuraEffect::HandlePeriodicTriggerSpellAuraTick(Unit* target, Unit* caster)
target->RemoveAurasDueToSpell(28820);
return;
}
- // Totemic Mastery (Skyshatter Regalia (Shaman Tier 6) - bonus)
- case 38443:
- {
- bool all = true;
- for (int i = SUMMON_SLOT_TOTEM; i < MAX_TOTEM_SLOT; ++i)
- {
- if (!target->m_SummonSlot[i])
- {
- all = false;
- break;
- }
- }
-
- if (all)
- target->CastSpell(target, 38437, true, NULL, this);
- else
- target->RemoveAurasDueToSpell(38437);
- return;
- }
}
break;
}
diff --git a/src/server/game/Spells/Spell.cpp b/src/server/game/Spells/Spell.cpp
index 63fe148dd93..7c1ccbdb463 100644
--- a/src/server/game/Spells/Spell.cpp
+++ b/src/server/game/Spells/Spell.cpp
@@ -5477,7 +5477,7 @@ SpellCastResult Spell::CheckCast(bool strict)
if (m_originalCaster && m_originalCaster->GetTypeId() == TYPEID_PLAYER && m_originalCaster->IsAlive())
{
Battlefield* Bf = sBattlefieldMgr->GetBattlefieldToZoneId(m_originalCaster->GetZoneId());
- if (AreaTableEntry const* area = GetAreaEntryByAreaID(m_originalCaster->GetAreaId()))
+ if (AreaTableEntry const* area = sAreaTableStore.LookupEntry(m_originalCaster->GetAreaId()))
if (area->flags & AREA_FLAG_NO_FLY_ZONE || (Bf && !Bf->CanFlyIn()))
return (_triggeredCastFlags & TRIGGERED_DONT_REPORT_CAST_ERROR) ? SPELL_FAILED_DONT_REPORT : SPELL_FAILED_NOT_HERE;
}
diff --git a/src/server/game/Spells/SpellEffects.cpp b/src/server/game/Spells/SpellEffects.cpp
index f961654f279..b2aa44e28df 100644
--- a/src/server/game/Spells/SpellEffects.cpp
+++ b/src/server/game/Spells/SpellEffects.cpp
@@ -4137,14 +4137,14 @@ void Spell::EffectDuel(SpellEffIndex effIndex)
return;
// Players can only fight a duel in zones with this flag
- AreaTableEntry const* casterAreaEntry = GetAreaEntryByAreaID(caster->GetAreaId());
+ AreaTableEntry const* casterAreaEntry = sAreaTableStore.LookupEntry(caster->GetAreaId());
if (casterAreaEntry && !(casterAreaEntry->flags & AREA_FLAG_ALLOW_DUELS))
{
SendCastResult(SPELL_FAILED_NO_DUELING); // Dueling isn't allowed here
return;
}
- AreaTableEntry const* targetAreaEntry = GetAreaEntryByAreaID(target->GetAreaId());
+ AreaTableEntry const* targetAreaEntry = sAreaTableStore.LookupEntry(target->GetAreaId());
if (targetAreaEntry && !(targetAreaEntry->flags & AREA_FLAG_ALLOW_DUELS))
{
SendCastResult(SPELL_FAILED_NO_DUELING); // Dueling isn't allowed here
diff --git a/src/server/game/Spells/SpellMgr.cpp b/src/server/game/Spells/SpellMgr.cpp
index ff8fc4539ff..40e8f2d4e24 100644
--- a/src/server/game/Spells/SpellMgr.cpp
+++ b/src/server/game/Spells/SpellMgr.cpp
@@ -1159,7 +1159,7 @@ bool SpellArea::IsFitToRequirements(Player const* player, uint32 newZone, uint32
if (!player)
return false;
- AreaTableEntry const* pArea = GetAreaEntryByAreaID(player->GetAreaId());
+ AreaTableEntry const* pArea = sAreaTableStore.LookupEntry(player->GetAreaId());
if (!(pArea && pArea->flags & AREA_FLAG_NO_FLY_ZONE))
return false;
if (!player->HasAuraType(SPELL_AURA_MOD_INCREASE_MOUNTED_FLIGHT_SPEED) && !player->HasAuraType(SPELL_AURA_FLY))
@@ -2618,7 +2618,7 @@ void SpellMgr::LoadSpellAreas()
}
}
- if (spellArea.areaId && !GetAreaEntryByAreaID(spellArea.areaId))
+ if (spellArea.areaId && !sAreaTableStore.LookupEntry(spellArea.areaId))
{
TC_LOG_ERROR("sql.sql", "Spell %u listed in `spell_area` have wrong area (%u) requirement", spell, spellArea.areaId);
continue;
diff --git a/src/server/game/Texts/CreatureTextMgr.cpp b/src/server/game/Texts/CreatureTextMgr.cpp
index 8d3ee939e2c..499f0c9cbf0 100644
--- a/src/server/game/Texts/CreatureTextMgr.cpp
+++ b/src/server/game/Texts/CreatureTextMgr.cpp
@@ -191,7 +191,6 @@ void CreatureTextMgr::LoadCreatureTextLocales()
} while (result->NextRow());
TC_LOG_INFO("server.loading", ">> Loaded %u creature localized texts in %u ms", textCount, GetMSTimeDiffToNow(oldMSTime));
-
}
uint32 CreatureTextMgr::SendChat(Creature* source, uint8 textGroup, WorldObject const* whisperTarget /*= nullptr*/, ChatMsg msgType /*= CHAT_MSG_ADDON*/, Language language /*= LANG_ADDON*/, CreatureTextRange range /*= TEXT_RANGE_NORMAL*/, uint32 sound /*= 0*/, Team team /*= TEAM_OTHER*/, bool gmOnly /*= false*/, Player* srcPlr /*= nullptr*/)
@@ -228,42 +227,10 @@ uint32 CreatureTextMgr::SendChat(Creature* source, uint8 textGroup, WorldObject
tempGroup = textGroupContainer;
}
- uint8 count = 0;
- float lastChance = -1;
- bool isEqualChanced = true;
-
- float totalChance = 0;
-
- for (CreatureTextGroup::const_iterator iter = tempGroup.begin(); iter != tempGroup.end(); ++iter)
+ auto iter = Trinity::Containers::SelectRandomWeightedContainerElement(tempGroup, [](CreatureTextEntry const& t) -> double
{
- if (lastChance >= 0 && lastChance != iter->probability)
- isEqualChanced = false;
-
- lastChance = iter->probability;
- totalChance += iter->probability;
- ++count;
- }
-
- int32 offset = -1;
- if (!isEqualChanced)
- {
- for (CreatureTextGroup::const_iterator iter = tempGroup.begin(); iter != tempGroup.end(); ++iter)
- {
- uint32 chance = uint32(iter->probability);
- uint32 r = urand(0, 100);
- ++offset;
- if (r <= chance)
- break;
- }
- }
-
- uint32 pos = 0;
- if (isEqualChanced || offset < 0)
- pos = urand(0, count - 1);
- else if (offset >= 0)
- pos = offset;
-
- CreatureTextGroup::const_iterator iter = tempGroup.begin() + pos;
+ return t.probability;
+ });
ChatMsg finalType = (msgType == CHAT_MSG_ADDON) ? iter->type : msgType;
Language finalLang = (language == LANG_ADDON) ? iter->lang : language;
@@ -293,9 +260,7 @@ uint32 CreatureTextMgr::SendChat(Creature* source, uint8 textGroup, WorldObject
SendChatPacket(finalSource, builder, finalType, whisperTarget, range, team, gmOnly);
}
- if (isEqualChanced || totalChance == 100.0f)
- SetRepeatId(source, textGroup, iter->id);
-
+ SetRepeatId(source, textGroup, iter->id);
return iter->duration;
}