aboutsummaryrefslogtreecommitdiff
path: root/src/server/game/Maps/MapInstanced.cpp
diff options
context:
space:
mode:
authortreeston <treeston.mmoc@gmail.com>2015-12-27 18:03:03 +0100
committertreeston <treeston.mmoc@gmail.com>2015-12-31 01:02:07 +0100
commit43fa7d48a5650c71f74098f3398cf5aca89c3837 (patch)
treea6d808e4b447f9df2b1f1cfe0a19483d64fe87d5 /src/server/game/Maps/MapInstanced.cpp
parent812809a977e2ba2a53e55c3dfc74bbed9dd59b7a (diff)
Game/Maps: Clean up instance handling.
- Rename Map::CanEnter to Map::CannotEnter. Return value changed from boolean (true means player can enter) to enum Map::EnterState (CAN_ENTER=0 means player can enter, any other value is a reason for deny). - Move hack-y player error messages from within Map::CanEnter to the function calling CanEnter as appropriate (primarily WorldSession::HandleAreaTriggerOpcode). - Modify WorldSession::HandleAreaTriggerOpcode to properly revive the player upon touching the portal leading to the instance they died in even if they are currently unable to zone in. Fixes and closes #15758. - Modify Player::LoadFromDB to properly spawn players in the instance they logged off in if possible. Fixes and closes #15561. - Modify permanent save behavior to be blizzlike: Players can always enter an instance they are saved to (assuming there are no map constraints against it), but get a homebind timer if the instance is already in use.
Diffstat (limited to 'src/server/game/Maps/MapInstanced.cpp')
-rw-r--r--src/server/game/Maps/MapInstanced.cpp31
1 files changed, 20 insertions, 11 deletions
diff --git a/src/server/game/Maps/MapInstanced.cpp b/src/server/game/Maps/MapInstanced.cpp
index d1b8bd66209..7e07d00fe6a 100644
--- a/src/server/game/Maps/MapInstanced.cpp
+++ b/src/server/game/Maps/MapInstanced.cpp
@@ -110,12 +110,12 @@ void MapInstanced::UnloadAll()
- create the instance if it's not created already
- the player is not actually added to the instance (only in InstanceMap::Add)
*/
-Map* MapInstanced::CreateInstanceForPlayer(const uint32 mapId, Player* player)
+Map* MapInstanced::CreateInstanceForPlayer(const uint32 mapId, Player* player, uint32 loginInstanceId)
{
if (GetId() != mapId || !player)
- return NULL;
+ return nullptr;
- Map* map = NULL;
+ Map* map = nullptr;
uint32 newInstanceId = 0; // instanceId of the resulting map
if (IsBattlegroundOrArena())
@@ -124,7 +124,7 @@ Map* MapInstanced::CreateInstanceForPlayer(const uint32 mapId, Player* player)
// the instance id is set in battlegroundid
newInstanceId = player->GetBattlegroundId();
if (!newInstanceId)
- return NULL;
+ return nullptr;
map = sMapMgr->FindMap(mapId, newInstanceId);
if (!map)
@@ -134,20 +134,29 @@ Map* MapInstanced::CreateInstanceForPlayer(const uint32 mapId, Player* player)
else
{
player->TeleportToBGEntryPoint();
- return NULL;
+ return nullptr;
}
}
}
else
{
InstancePlayerBind* pBind = player->GetBoundInstance(GetId(), player->GetDifficulty(IsRaid()));
- InstanceSave* pSave = pBind ? pBind->save : NULL;
+ InstanceSave* pSave = pBind ? pBind->save : nullptr;
- // the player's permanent player bind is taken into consideration first
- // then the player's group bind and finally the solo bind.
+ // priority:
+ // 1. player's permanent bind
+ // 2. player's current instance id if this is at login
+ // 3. group's current bind
+ // 4. player's current bind
if (!pBind || !pBind->perm)
{
- InstanceGroupBind* groupBind = NULL;
+ if (loginInstanceId) // if the player has a saved instance id on login, we either use this instance or relocate him out (return null)
+ {
+ map = FindInstanceMap(loginInstanceId);
+ return (map && map->GetId() == GetId()) ? map : nullptr; // is this check necessary? or does MapInstanced only find instances of itself?
+ }
+
+ InstanceGroupBind* groupBind = nullptr;
Group* group = player->GetGroup();
// use the player's difficulty setting (it may not be the same as the group's)
if (group)
@@ -278,8 +287,8 @@ bool MapInstanced::DestroyInstance(InstancedMaps::iterator &itr)
return true;
}
-bool MapInstanced::CanEnter(Player* /*player*/)
+Map::EnterState MapInstanced::CannotEnter(Player* /*player*/)
{
//ABORT();
- return true;
+ return CAN_ENTER;
}