Skip to content

Commit

Permalink
Core/Players: Introduce configurable allied race starting level and f…
Browse files Browse the repository at this point in the history
…ix default level selection for pandaren death knights
  • Loading branch information
Shauren committed Dec 22, 2020
1 parent 01af07c commit bff8f2f
Show file tree
Hide file tree
Showing 9 changed files with 82 additions and 44 deletions.
2 changes: 2 additions & 0 deletions src/server/game/DataStores/DB2Structure.h
Original file line number Diff line number Diff line change
Expand Up @@ -721,6 +721,8 @@ struct ChrRacesEntry
int8 FemaleTextureFallbackRaceID;
int8 FemaleTextureFallbackSex;
int8 UnalteredVisualCustomizationRaceID;

EnumFlag<ChrRacesFlag> GetFlags() const { return static_cast<ChrRacesFlag>(Flags); }
};

#define MAX_MASTERY_SPELLS 2
Expand Down
13 changes: 10 additions & 3 deletions src/server/game/DataStores/DBCEnums.h
Original file line number Diff line number Diff line change
Expand Up @@ -201,6 +201,13 @@ enum BattlemasterListFlags
BATTLEMASTER_LIST_FLAG_FACTIONAL = 0x40
};

enum class ChrRacesFlag : int32
{
AlliedRace = 0x80000
};

DEFINE_ENUM_FLAG(ChrRacesFlag);

enum ChrSpecializationFlag
{
CHR_SPECIALIZATION_FLAG_CASTER = 0x01,
Expand Down Expand Up @@ -851,14 +858,14 @@ enum class ChrCustomizationOptionFlag : int32
Disabled = 0x4,
};

DEFINE_ENUM_FLAG(ChrCustomizationOptionFlag)
DEFINE_ENUM_FLAG(ChrCustomizationOptionFlag);

enum class ChrCustomizationReqFlag : int32
{
HasRequirements = 0x1
};

DEFINE_ENUM_FLAG(ChrCustomizationReqFlag)
DEFINE_ENUM_FLAG(ChrCustomizationReqFlag);

enum Curves
{
Expand Down Expand Up @@ -1431,7 +1438,7 @@ enum class UiMapFlag : int32
ForceOnNavbar = 0x00008000
};

DEFINE_ENUM_FLAG(UiMapFlag)
DEFINE_ENUM_FLAG(UiMapFlag);

enum UiMapSystem : int8
{
Expand Down
63 changes: 35 additions & 28 deletions src/server/game/Entities/Player/Player.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -486,34 +486,7 @@ bool Player::Create(ObjectGuid::LowType guidlow, WorldPackets::Character::Charac
SetInventorySlotCount(INVENTORY_DEFAULT_SIZE);

// set starting level
uint32 start_level = sWorld->getIntConfig(CONFIG_START_PLAYER_LEVEL);
if (getClass() == CLASS_DEATH_KNIGHT)
start_level = sWorld->getIntConfig(CONFIG_START_DEATH_KNIGHT_PLAYER_LEVEL);
else if (getClass() == CLASS_DEMON_HUNTER)
start_level = sWorld->getIntConfig(CONFIG_START_DEMON_HUNTER_PLAYER_LEVEL);

if (createInfo->TemplateSet)
{
if (m_session->HasPermission(rbac::RBAC_PERM_USE_CHARACTER_TEMPLATES))
{
if (CharacterTemplate const* charTemplate = sCharacterTemplateDataStore->GetCharacterTemplate(*createInfo->TemplateSet))
{
if (charTemplate->Level > start_level)
start_level = charTemplate->Level;
}
}
else
TC_LOG_WARN("cheat", "Account: %u (IP: %s) tried to use a character template without given permission. Possible cheating attempt.", m_session->GetAccountId(), m_session->GetRemoteAddress().c_str());
}

if (m_session->HasPermission(rbac::RBAC_PERM_USE_START_GM_LEVEL))
{
uint32 gm_level = sWorld->getIntConfig(CONFIG_START_GM_LEVEL);
if (gm_level > start_level)
start_level = gm_level;
}

SetLevel(start_level);
SetLevel(GetStartLevel(createInfo->Race, createInfo->Class, createInfo->TemplateSet));

InitRunes();

Expand Down Expand Up @@ -23791,6 +23764,40 @@ WorldLocation Player::GetStartPosition() const
return WorldLocation(mapId, info->positionX, info->positionY, info->positionZ, 0);
}

uint8 Player::GetStartLevel(uint8 race, uint8 playerClass, Optional<int32> characterTemplateId) const
{
uint8 startLevel = sWorld->getIntConfig(CONFIG_START_PLAYER_LEVEL);
if (sChrRacesStore.AssertEntry(race)->GetFlags().HasFlag(ChrRacesFlag::AlliedRace))
startLevel = sWorld->getIntConfig(CONFIG_START_ALLIED_RACE_LEVEL);

if (playerClass == CLASS_DEATH_KNIGHT)
{
if (race == RACE_PANDAREN_ALLIANCE || race == RACE_PANDAREN_HORDE)
startLevel = std::max<uint8>(sWorld->getIntConfig(CONFIG_START_ALLIED_RACE_LEVEL), startLevel);
else
startLevel = std::max<uint8>(sWorld->getIntConfig(CONFIG_START_DEATH_KNIGHT_PLAYER_LEVEL), startLevel);
}
else if (playerClass == CLASS_DEMON_HUNTER)
startLevel = std::max<uint8>(sWorld->getIntConfig(CONFIG_START_DEMON_HUNTER_PLAYER_LEVEL), startLevel);

if (characterTemplateId)
{
if (m_session->HasPermission(rbac::RBAC_PERM_USE_CHARACTER_TEMPLATES))
{
if (CharacterTemplate const* charTemplate = sCharacterTemplateDataStore->GetCharacterTemplate(*characterTemplateId))
startLevel = std::max(charTemplate->Level, startLevel);
}
else
TC_LOG_WARN("cheat", "Account: %u (IP: %s) tried to use a character template without given permission. Possible cheating attempt.",
m_session->GetAccountId(), m_session->GetRemoteAddress().c_str());
}

if (m_session->HasPermission(rbac::RBAC_PERM_USE_START_GM_LEVEL))
startLevel = std::max<uint8>(sWorld->getIntConfig(CONFIG_START_GM_LEVEL), startLevel);

return startLevel;
}

bool Player::HaveAtClient(Object const* u) const
{
return u == this || m_clientGUIDs.find(u->GetGUID()) != m_clientGUIDs.end();
Expand Down
1 change: 1 addition & 0 deletions src/server/game/Entities/Player/Player.h
Original file line number Diff line number Diff line change
Expand Up @@ -2218,6 +2218,7 @@ class TC_GAME_API Player : public Unit, public GridObject<Player>
float m_homebindZ;

WorldLocation GetStartPosition() const;
uint8 GetStartLevel(uint8 race, uint8 playerClass, Optional<int32> characterTemplateId) const;

// currently visible objects at player client
GuidUnorderedSet m_clientGUIDs;
Expand Down
2 changes: 1 addition & 1 deletion src/server/game/Quests/QuestDef.h
Original file line number Diff line number Diff line change
Expand Up @@ -144,7 +144,7 @@ enum class QuestGiverStatus : uint32
ScriptedDefault = 0x80000000
};

DEFINE_ENUM_FLAG(QuestGiverStatus)
DEFINE_ENUM_FLAG(QuestGiverStatus);

enum QuestFlags : uint32
{
Expand Down
28 changes: 21 additions & 7 deletions src/server/game/World/World.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -931,12 +931,12 @@ void World::LoadConfigSettings(bool reload)
m_int_configs[CONFIG_START_PLAYER_LEVEL] = m_int_configs[CONFIG_MAX_PLAYER_LEVEL];
}

m_int_configs[CONFIG_START_DEATH_KNIGHT_PLAYER_LEVEL] = sConfigMgr->GetIntDefault("StartDeathKnightPlayerLevel", 55);
m_int_configs[CONFIG_START_DEATH_KNIGHT_PLAYER_LEVEL] = sConfigMgr->GetIntDefault("StartDeathKnightPlayerLevel", 8);
if (m_int_configs[CONFIG_START_DEATH_KNIGHT_PLAYER_LEVEL] < 1)
{
TC_LOG_ERROR("server.loading", "StartDeathKnightPlayerLevel (%i) must be in range 1..MaxPlayerLevel(%u). Set to 55.",
TC_LOG_ERROR("server.loading", "StartDeathKnightPlayerLevel (%i) must be in range 1..MaxPlayerLevel(%u). Set to 1.",
m_int_configs[CONFIG_START_DEATH_KNIGHT_PLAYER_LEVEL], m_int_configs[CONFIG_MAX_PLAYER_LEVEL]);
m_int_configs[CONFIG_START_DEATH_KNIGHT_PLAYER_LEVEL] = 55;
m_int_configs[CONFIG_START_DEATH_KNIGHT_PLAYER_LEVEL] = 1;
}
else if (m_int_configs[CONFIG_START_DEATH_KNIGHT_PLAYER_LEVEL] > m_int_configs[CONFIG_MAX_PLAYER_LEVEL])
{
Expand All @@ -945,12 +945,12 @@ void World::LoadConfigSettings(bool reload)
m_int_configs[CONFIG_START_DEATH_KNIGHT_PLAYER_LEVEL] = m_int_configs[CONFIG_MAX_PLAYER_LEVEL];
}

m_int_configs[CONFIG_START_DEMON_HUNTER_PLAYER_LEVEL] = sConfigMgr->GetIntDefault("StartDemonHunterPlayerLevel", 98);
if (m_int_configs[CONFIG_START_DEMON_HUNTER_PLAYER_LEVEL] < 98)
m_int_configs[CONFIG_START_DEMON_HUNTER_PLAYER_LEVEL] = sConfigMgr->GetIntDefault("StartDemonHunterPlayerLevel", 8);
if (m_int_configs[CONFIG_START_DEMON_HUNTER_PLAYER_LEVEL] < 1)
{
TC_LOG_ERROR("server.loading", "StartDemonHunterPlayerLevel (%i) must be in range 98..MaxPlayerLevel(%u). Set to 98.",
TC_LOG_ERROR("server.loading", "StartDemonHunterPlayerLevel (%i) must be in range 1..MaxPlayerLevel(%u). Set to 1.",
m_int_configs[CONFIG_START_DEMON_HUNTER_PLAYER_LEVEL], m_int_configs[CONFIG_MAX_PLAYER_LEVEL]);
m_int_configs[CONFIG_START_DEMON_HUNTER_PLAYER_LEVEL] = 98;
m_int_configs[CONFIG_START_DEMON_HUNTER_PLAYER_LEVEL] = 1;
}
else if (m_int_configs[CONFIG_START_DEMON_HUNTER_PLAYER_LEVEL] > m_int_configs[CONFIG_MAX_PLAYER_LEVEL])
{
Expand All @@ -959,6 +959,20 @@ void World::LoadConfigSettings(bool reload)
m_int_configs[CONFIG_START_DEMON_HUNTER_PLAYER_LEVEL] = m_int_configs[CONFIG_MAX_PLAYER_LEVEL];
}

m_int_configs[CONFIG_START_ALLIED_RACE_LEVEL] = sConfigMgr->GetIntDefault("StartAlliedRacePlayerLevel", 10);
if (m_int_configs[CONFIG_START_ALLIED_RACE_LEVEL] < 1)
{
TC_LOG_ERROR("server.loading", "StartDemonHunterPlayerLevel (%i) must be in range 1..MaxPlayerLevel(%u). Set to 1.",
m_int_configs[CONFIG_START_ALLIED_RACE_LEVEL], m_int_configs[CONFIG_MAX_PLAYER_LEVEL]);
m_int_configs[CONFIG_START_ALLIED_RACE_LEVEL] = 1;
}
else if (m_int_configs[CONFIG_START_ALLIED_RACE_LEVEL] > m_int_configs[CONFIG_MAX_PLAYER_LEVEL])
{
TC_LOG_ERROR("server.loading", "StartDemonHunterPlayerLevel (%i) must be in range 1..MaxPlayerLevel(%u). Set to %u.",
m_int_configs[CONFIG_START_ALLIED_RACE_LEVEL], m_int_configs[CONFIG_MAX_PLAYER_LEVEL], m_int_configs[CONFIG_MAX_PLAYER_LEVEL]);
m_int_configs[CONFIG_START_ALLIED_RACE_LEVEL] = m_int_configs[CONFIG_MAX_PLAYER_LEVEL];
}

m_int_configs[CONFIG_START_PLAYER_MONEY] = sConfigMgr->GetIntDefault("StartPlayerMoney", 0);
if (int32(m_int_configs[CONFIG_START_PLAYER_MONEY]) < 0)
{
Expand Down
1 change: 1 addition & 0 deletions src/server/game/World/World.h
Original file line number Diff line number Diff line change
Expand Up @@ -251,6 +251,7 @@ enum WorldIntConfigs
CONFIG_START_PLAYER_LEVEL,
CONFIG_START_DEATH_KNIGHT_PLAYER_LEVEL,
CONFIG_START_DEMON_HUNTER_PLAYER_LEVEL,
CONFIG_START_ALLIED_RACE_LEVEL,
CONFIG_START_PLAYER_MONEY,
CONFIG_CURRENCY_START_APEXIS_CRYSTALS,
CONFIG_CURRENCY_MAX_APEXIS_CRYSTALS,
Expand Down
4 changes: 1 addition & 3 deletions src/server/scripts/Commands/cs_reset.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -132,9 +132,7 @@ class reset_commandscript : public CommandScript
uint8 oldLevel = target->getLevel();

// set starting level
uint32 startLevel = target->getClass() != CLASS_DEATH_KNIGHT
? sWorld->getIntConfig(CONFIG_START_PLAYER_LEVEL)
: sWorld->getIntConfig(CONFIG_START_DEATH_KNIGHT_PLAYER_LEVEL);
uint8 startLevel = target->GetStartLevel(target->getRace(), target->getClass(), {});

target->_ApplyAllLevelScaleItemMods(false);
target->SetLevel(startLevel);
Expand Down
12 changes: 10 additions & 2 deletions src/server/worldserver/worldserver.conf.dist
Original file line number Diff line number Diff line change
Expand Up @@ -892,9 +892,9 @@ StartPlayerLevel = 1
# StartDeathKnightPlayerLevel
# Description: Starting level for death knights after creation.
# Range: 1-MaxPlayerLevel
# Default: 10
# Default: 8

StartDeathKnightPlayerLevel = 10
StartDeathKnightPlayerLevel = 8

#
# StartDemonHunterPlayerLevel
Expand All @@ -904,6 +904,14 @@ StartDeathKnightPlayerLevel = 10

StartDemonHunterPlayerLevel = 8

#
# StartAlliedRacePlayerLevel
# Description: Staring level for allied races after creation.
# Range: 1-MaxPlayerLevel
# Default: 10

StartAlliedRacePlayerLevel = 10

#
# StartPlayerMoney
# Description: Amount of money (in Copper) that a character has after creation.
Expand Down

0 comments on commit bff8f2f

Please sign in to comment.