Core/OutdoorPvP: Refactor OutdoorPvP creation to be linked to host map creation instead of having globally accessible objects

Port From (https://github.com/TrinityCore/TrinityCore/commit/775be0682a794d0a1f62d656f8c6c6dffca8de79)
This commit is contained in:
hondacrx
2022-07-19 12:14:32 -04:00
parent 054dd15aa0
commit b3a404e2e8
8 changed files with 64 additions and 87 deletions
+1 -1
View File
@@ -1438,7 +1438,7 @@ namespace Game.Entities
if (bf != null) if (bf != null)
return bf; return bf;
else else
return Global.OutdoorPvPMgr.GetZoneScript(GetZoneId()); return Global.OutdoorPvPMgr.GetOutdoorPvPToZoneId(map, GetZoneId());
} }
} }
+1 -1
View File
@@ -765,7 +765,7 @@ namespace Game.Entities
} }
public OutdoorPvP GetOutdoorPvP() public OutdoorPvP GetOutdoorPvP()
{ {
return Global.OutdoorPvPMgr.GetOutdoorPvPToZoneId(GetZoneId()); return Global.OutdoorPvPMgr.GetOutdoorPvPToZoneId(GetMap(), GetZoneId());
} }
} }
} }
+4
View File
@@ -89,6 +89,8 @@ namespace Game.Maps
_worldStateValues = Global.WorldStateMgr.GetInitialWorldStatesForMap(this); _worldStateValues = Global.WorldStateMgr.GetInitialWorldStatesForMap(this);
Global.OutdoorPvPMgr.CreateOutdoorPvPForMap(this);
Global.ScriptMgr.OnCreateMap(this); Global.ScriptMgr.OnCreateMap(this);
} }
@@ -111,6 +113,8 @@ namespace Game.Maps
if (!m_scriptSchedule.Empty()) if (!m_scriptSchedule.Empty())
Global.MapMgr.DecreaseScheduledScriptCount((uint)m_scriptSchedule.Count); Global.MapMgr.DecreaseScheduledScriptCount((uint)m_scriptSchedule.Count);
Global.OutdoorPvPMgr.DestroyOutdoorPvPForMap(this);
if (m_parentMap == this) if (m_parentMap == this)
m_childTerrainMaps = null; m_childTerrainMaps = null;
+2 -13
View File
@@ -35,10 +35,10 @@ namespace Game.PvP
// base class for specific outdoor pvp handlers // base class for specific outdoor pvp handlers
public class OutdoorPvP : ZoneScript public class OutdoorPvP : ZoneScript
{ {
public OutdoorPvP() public OutdoorPvP(Map map)
{ {
m_TypeId = 0; m_TypeId = 0;
m_sendUpdate = true; m_map = map;
m_players[0] = new List<ObjectGuid>(); m_players[0] = new List<ObjectGuid>();
m_players[1] = new List<ObjectGuid>(); m_players[1] = new List<ObjectGuid>();
} }
@@ -285,21 +285,10 @@ namespace Game.PvP
public Map GetMap() { return m_map; } public Map GetMap() { return m_map; }
// Hack to store map because this code is just shit
public void SetMapFromZone(uint zone)
{
AreaTableRecord areaTable = CliDB.AreaTableStorage.LookupByKey(zone);
Cypher.Assert(areaTable != null);
Map map = Global.MapMgr.CreateBaseMap(areaTable.ContinentID);
Cypher.Assert(!map.Instanceable());
m_map = map;
}
// the map of the objectives belonging to this outdoorpvp // the map of the objectives belonging to this outdoorpvp
public Dictionary<ulong, OPvPCapturePoint> m_capturePoints = new(); public Dictionary<ulong, OPvPCapturePoint> m_capturePoints = new();
List<ObjectGuid>[] m_players = new List<ObjectGuid>[2]; List<ObjectGuid>[] m_players = new List<ObjectGuid>[2];
public OutdoorPvPTypes m_TypeId; public OutdoorPvPTypes m_TypeId;
bool m_sendUpdate;
Map m_map; Map m_map;
} }
+50 -65
View File
@@ -45,34 +45,40 @@ namespace Game.PvP
do do
{ {
uint typeId = result.Read<byte>(0); OutdoorPvPTypes typeId = (OutdoorPvPTypes)result.Read<byte>(0);
if (Global.DisableMgr.IsDisabledFor(DisableType.OutdoorPVP, typeId, null)) if (Global.DisableMgr.IsDisabledFor(DisableType.OutdoorPVP, (uint)typeId, null))
continue; continue;
if (typeId >= (int)OutdoorPvPTypes.Max) if (typeId >= OutdoorPvPTypes.Max)
{ {
Log.outError(LogFilter.Sql, "Invalid OutdoorPvPTypes value {0} in outdoorpvp_template; skipped.", typeId); Log.outError(LogFilter.Sql, "Invalid OutdoorPvPTypes value {0} in outdoorpvp_template; skipped.", typeId);
continue; continue;
} }
OutdoorPvPTypes realTypeId = (OutdoorPvPTypes)typeId; m_OutdoorPvPDatas[typeId] = Global.ObjectMgr.GetScriptId(result.Read<string>(1));
OutdoorPvPScriptIds[realTypeId] = Global.ObjectMgr.GetScriptId(result.Read<string>(1));
++count; ++count;
} }
while (result.NextRow()); while (result.NextRow());
OutdoorPvP pvp; Log.outInfo(LogFilter.ServerLoading, $"Loaded {count} outdoor PvP definitions in {Time.GetMSTimeDiffToNow(oldMSTime)} ms");
}
public void CreateOutdoorPvPForMap(Map map)
{
for (OutdoorPvPTypes outdoorPvpType = OutdoorPvPTypes.HellfirePeninsula; outdoorPvpType < OutdoorPvPTypes.Max; ++outdoorPvpType) for (OutdoorPvPTypes outdoorPvpType = OutdoorPvPTypes.HellfirePeninsula; outdoorPvpType < OutdoorPvPTypes.Max; ++outdoorPvpType)
{ {
if (!OutdoorPvPScriptIds.ContainsKey(outdoorPvpType)) if (map.GetId() != m_OutdoorMapIds[(int)outdoorPvpType])
continue;
if (!m_OutdoorPvPDatas.ContainsKey(outdoorPvpType))
{ {
Log.outError(LogFilter.Sql, "Could not initialize OutdoorPvP object for type ID {0}; no entry in database.", outdoorPvpType); Log.outError(LogFilter.Sql, "Could not initialize OutdoorPvP object for type ID {0}; no entry in database.", outdoorPvpType);
continue; continue;
} }
pvp = Global.ScriptMgr.CreateOutdoorPvP(OutdoorPvPScriptIds[outdoorPvpType]); OutdoorPvP pvp = Global.ScriptMgr.CreateOutdoorPvP(m_OutdoorPvPDatas[outdoorPvpType], map);
if (pvp == null) if (pvp == null)
{ {
Log.outError(LogFilter.Outdoorpvp, "Could not initialize OutdoorPvP object for type ID {0}; got NULL pointer from script.", outdoorPvpType); Log.outError(LogFilter.Outdoorpvp, "Could not initialize OutdoorPvP object for type ID {0}; got NULL pointer from script.", outdoorPvpType);
@@ -85,20 +91,23 @@ namespace Game.PvP
continue; continue;
} }
m_OutdoorPvPSet.Add(pvp); m_OutdoorPvPByMap.Add(map, pvp);
} }
}
Log.outInfo(LogFilter.ServerLoading, "Loaded {0} outdoor PvP definitions in {1} ms", count, Time.GetMSTimeDiffToNow(oldMSTime)); public void DestroyOutdoorPvPForMap(Map map)
{
m_OutdoorPvPByMap.Remove(map);
} }
public void AddZone(uint zoneid, OutdoorPvP handle) public void AddZone(uint zoneid, OutdoorPvP handle)
{ {
m_OutdoorPvPMap[zoneid] = handle; m_OutdoorPvPMap[(handle.GetMap(), zoneid)] = handle;
} }
public void HandlePlayerEnterZone(Player player, uint zoneid) public void HandlePlayerEnterZone(Player player, uint zoneid)
{ {
var outdoor = GetOutdoorPvPToZoneId(zoneid); var outdoor = GetOutdoorPvPToZoneId(player.GetMap(), zoneid);
if (outdoor == null) if (outdoor == null)
return; return;
@@ -111,7 +120,7 @@ namespace Game.PvP
public void HandlePlayerLeaveZone(Player player, uint zoneid) public void HandlePlayerLeaveZone(Player player, uint zoneid)
{ {
var outdoor = GetOutdoorPvPToZoneId(zoneid); var outdoor = GetOutdoorPvPToZoneId(player.GetMap(), zoneid);
if (outdoor == null) if (outdoor == null)
return; return;
@@ -123,15 +132,9 @@ namespace Game.PvP
Log.outDebug(LogFilter.Outdoorpvp, "Player {0} left outdoorpvp id {1}", player.GetGUID().ToString(), outdoor.GetTypeId()); Log.outDebug(LogFilter.Outdoorpvp, "Player {0} left outdoorpvp id {1}", player.GetGUID().ToString(), outdoor.GetTypeId());
} }
public OutdoorPvP GetOutdoorPvPToZoneId(uint zoneid) public OutdoorPvP GetOutdoorPvPToZoneId(Map map, uint zoneid)
{ {
var outdoor = m_OutdoorPvPMap.LookupByKey(zoneid); return m_OutdoorPvPMap.LookupByKey((map, zoneid));
if (outdoor == null)
{
// no handle for this zone, return
return null;
}
return outdoor;
} }
public void Update(uint diff) public void Update(uint diff)
@@ -139,7 +142,7 @@ namespace Game.PvP
m_UpdateTimer += diff; m_UpdateTimer += diff;
if (m_UpdateTimer > 1000) if (m_UpdateTimer > 1000)
{ {
foreach (var outdoor in m_OutdoorPvPSet) foreach (var (_, outdoor) in m_OutdoorPvPByMap)
outdoor.Update(m_UpdateTimer); outdoor.Update(m_UpdateTimer);
m_UpdateTimer = 0; m_UpdateTimer = 0;
} }
@@ -147,69 +150,50 @@ namespace Game.PvP
public bool HandleCustomSpell(Player player, uint spellId, GameObject go) public bool HandleCustomSpell(Player player, uint spellId, GameObject go)
{ {
foreach (var outdoor in m_OutdoorPvPSet) OutdoorPvP pvp = player.GetOutdoorPvP();
{ if (pvp != null && pvp.HasPlayer(player))
if (outdoor.HandleCustomSpell(player, spellId, go)) return pvp.HandleCustomSpell(player, spellId, go);
return true;
}
return false; return false;
} }
public ZoneScript GetZoneScript(uint zoneId)
{
var outdoor = GetOutdoorPvPToZoneId(zoneId);
if (outdoor == null)
return null;
return outdoor;
}
public bool HandleOpenGo(Player player, GameObject go) public bool HandleOpenGo(Player player, GameObject go)
{ {
foreach (var outdoor in m_OutdoorPvPSet) OutdoorPvP pvp = player.GetOutdoorPvP();
{ if (pvp != null && pvp.HasPlayer(player))
if (outdoor.HandleOpenGo(player, go)) return pvp.HandleOpenGo(player, go);
return true;
}
return false; return false;
} }
public void HandleGossipOption(Player player, Creature creature, uint gossipid) public void HandleGossipOption(Player player, Creature creature, uint gossipid)
{ {
foreach (var outdoor in m_OutdoorPvPSet) OutdoorPvP pvp = player.GetOutdoorPvP();
{ if (pvp != null && pvp.HasPlayer(player))
if (outdoor.HandleGossipOption(player, creature, gossipid)) pvp.HandleGossipOption(player, creature, gossipid);
return;
}
} }
public bool CanTalkTo(Player player, Creature creature, GossipMenuItems gso) public bool CanTalkTo(Player player, Creature creature, GossipMenuItems gso)
{ {
foreach (var outdoor in m_OutdoorPvPSet) OutdoorPvP pvp = player.GetOutdoorPvP();
{ if (pvp != null && pvp.HasPlayer(player))
if (outdoor.CanTalkTo(player, creature, gso)) return pvp.CanTalkTo(player, creature, gso);
return true;
}
return false; return false;
} }
public void HandleDropFlag(Player player, uint spellId) public void HandleDropFlag(Player player, uint spellId)
{ {
foreach (var outdoor in m_OutdoorPvPSet) OutdoorPvP pvp = player.GetOutdoorPvP();
{ if (pvp != null && pvp.HasPlayer(player))
if (outdoor.HandleDropFlag(player, spellId)) pvp.HandleDropFlag(player, spellId);
return;
}
} }
public void HandlePlayerResurrects(Player player, uint zoneid) public void HandlePlayerResurrects(Player player, uint zoneid)
{ {
var outdoor = GetOutdoorPvPToZoneId(zoneid); OutdoorPvP pvp = player.GetOutdoorPvP();
if (outdoor == null) if (pvp != null && pvp.HasPlayer(player))
return; pvp.HandlePlayerResurrects(player, zoneid);
if (outdoor.HasPlayer(player))
outdoor.HandlePlayerResurrects(player, zoneid);
} }
public string GetDefenseMessage(uint zoneId, uint id, Locale locale) public string GetDefenseMessage(uint zoneId, uint id, Locale locale)
@@ -224,14 +208,15 @@ namespace Game.PvP
// contains all initiated outdoor pvp events // contains all initiated outdoor pvp events
// used when initing / cleaning up // used when initing / cleaning up
List<OutdoorPvP> m_OutdoorPvPSet = new(); MultiMap<Map, OutdoorPvP> m_OutdoorPvPByMap = new();
// maps the zone ids to an outdoor pvp event // maps the zone ids to an outdoor pvp event
// used in player event handling // used in player event handling
Dictionary<uint, OutdoorPvP> m_OutdoorPvPMap = new(); Dictionary<(Map map, uint zoneId), OutdoorPvP> m_OutdoorPvPMap = new();
// Holds the outdoor PvP templates // Holds the outdoor PvP templates
Dictionary<OutdoorPvPTypes, uint> OutdoorPvPScriptIds = new(); uint[] m_OutdoorMapIds = { 0, 530, 530, 530, 530, 1 };
Dictionary<OutdoorPvPTypes, uint> m_OutdoorPvPDatas = new();
// update interval // update interval
uint m_UpdateTimer; uint m_UpdateTimer;
@@ -25,7 +25,7 @@ namespace Game.PvP
{ {
class HellfirePeninsulaPvP : OutdoorPvP class HellfirePeninsulaPvP : OutdoorPvP
{ {
public HellfirePeninsulaPvP() public HellfirePeninsulaPvP(Map map) : base(map)
{ {
m_TypeId = OutdoorPvPTypes.HellfirePeninsula; m_TypeId = OutdoorPvPTypes.HellfirePeninsula;
m_AllianceTowersControlled = 0; m_AllianceTowersControlled = 0;
@@ -36,7 +36,6 @@ namespace Game.PvP
{ {
m_AllianceTowersControlled = 0; m_AllianceTowersControlled = 0;
m_HordeTowersControlled = 0; m_HordeTowersControlled = 0;
SetMapFromZone(HPConst.BuffZones[0]);
// add the zones affected by the pvp buff // add the zones affected by the pvp buff
for (int i = 0; i < HPConst.BuffZones.Length; ++i) for (int i = 0; i < HPConst.BuffZones.Length; ++i)
@@ -305,9 +304,9 @@ namespace Game.PvP
{ {
public OutdoorPvP_hellfire_peninsula() : base("outdoorpvp_hp") { } public OutdoorPvP_hellfire_peninsula() : base("outdoorpvp_hp") { }
public override OutdoorPvP GetOutdoorPvP() public override OutdoorPvP GetOutdoorPvP(Map map)
{ {
return new HellfirePeninsulaPvP(); return new HellfirePeninsulaPvP(map);
} }
} }
+1 -1
View File
@@ -469,7 +469,7 @@ namespace Game.Scripting
public override bool IsDatabaseBound() { return true; } public override bool IsDatabaseBound() { return true; }
// Should return a fully valid OutdoorPvP object for the type ID. // Should return a fully valid OutdoorPvP object for the type ID.
public virtual OutdoorPvP GetOutdoorPvP() { return null; } public virtual OutdoorPvP GetOutdoorPvP(Map map) { return null; }
} }
public class WeatherScript : ScriptObject public class WeatherScript : ScriptObject
+2 -2
View File
@@ -729,9 +729,9 @@ namespace Game.Scripting
} }
// OutdoorPvPScript // OutdoorPvPScript
public OutdoorPvP CreateOutdoorPvP(uint scriptId) public OutdoorPvP CreateOutdoorPvP(uint scriptId, Map map)
{ {
return RunScriptRet<OutdoorPvPScript, OutdoorPvP>(p => p.GetOutdoorPvP(), scriptId, null); return RunScriptRet<OutdoorPvPScript, OutdoorPvP>(p => p.GetOutdoorPvP(map), scriptId, null);
} }
// WeatherScript // WeatherScript