mirror of
https://github.com/EQEmu/Server.git
synced 2025-12-11 12:41:30 +00:00
121 lines
3.0 KiB
C++
121 lines
3.0 KiB
C++
#include "skill_caps.h"
|
|
#include "timer.h"
|
|
|
|
// cache the skill cap max level in the database
|
|
std::map<uint8_t, int32_t> skill_max_level = {};
|
|
|
|
uint8 skill_cap_max_level = (
|
|
RuleI(Character, SkillCapMaxLevel) > 0 ?
|
|
RuleI(Character, SkillCapMaxLevel) :
|
|
RuleI(Character, MaxLevel)
|
|
);
|
|
|
|
SkillCaps *SkillCaps::SetContentDatabase(Database *db)
|
|
{
|
|
m_content_database = db;
|
|
|
|
return this;
|
|
}
|
|
|
|
int32_t SkillCaps::GetSkillCapMaxLevel(uint8 class_id, EQ::skills::SkillType skill_id)
|
|
{
|
|
// pull the max value defined in the database if it exists
|
|
auto it = skill_max_level.find((class_id * 1000000) + skill_id);
|
|
if (it != skill_max_level.end()) {
|
|
return it->second;
|
|
}
|
|
|
|
return skill_cap_max_level;
|
|
}
|
|
|
|
SkillCapsRepository::SkillCaps SkillCaps::GetSkillCap(uint8 class_id, EQ::skills::SkillType skill_id, uint8 level)
|
|
{
|
|
if (!IsPlayerClass(class_id) || static_cast<uint32>(skill_id) > EQ::skills::HIGHEST_SKILL + 1) {
|
|
return SkillCapsRepository::NewEntity();
|
|
}
|
|
|
|
const uint8 max_level = GetSkillCapMaxLevel(class_id, skill_id);
|
|
if (level > max_level) {
|
|
level = max_level;
|
|
}
|
|
|
|
const uint64_t key = (class_id * 1000000) + (level * 1000) + static_cast<uint32>(skill_id);
|
|
auto pos = m_skill_caps.find(key);
|
|
if (pos != m_skill_caps.end()) {
|
|
return pos->second;
|
|
}
|
|
|
|
return SkillCapsRepository::NewEntity();
|
|
}
|
|
|
|
uint8 SkillCaps::GetSkillTrainLevel(uint8 class_id, EQ::skills::SkillType skill_id, uint8 level)
|
|
{
|
|
if (
|
|
!IsPlayerClass(class_id) ||
|
|
class_id > Class::PLAYER_CLASS_COUNT ||
|
|
static_cast<uint32>(skill_id) > (EQ::skills::HIGHEST_SKILL + 1)
|
|
) {
|
|
return 0;
|
|
}
|
|
|
|
const uint8 max_level = level > skill_cap_max_level ? level : skill_cap_max_level;
|
|
const uint64_t key = (class_id * 1000000) + (level * 1000) + static_cast<uint32>(skill_id);
|
|
for (uint8 current_level = 1; current_level <= max_level; current_level++) {
|
|
auto pos = m_skill_caps.find(key);
|
|
if (pos != m_skill_caps.end()) {
|
|
return current_level;
|
|
}
|
|
}
|
|
|
|
return 0;
|
|
}
|
|
|
|
void SkillCaps::LoadSkillCaps()
|
|
{
|
|
const auto &l = SkillCapsRepository::All(*m_content_database);
|
|
|
|
m_skill_caps.clear();
|
|
|
|
for (const auto &e: l) {
|
|
if (
|
|
e.level < 1 ||
|
|
!IsPlayerClass(e.class_id) ||
|
|
static_cast<EQ::skills::SkillType>(e.skill_id) >= EQ::skills::SkillCount
|
|
) {
|
|
continue;
|
|
}
|
|
|
|
const uint64_t key = (e.class_id * 1000000) + (e.level * 1000) + e.skill_id;
|
|
m_skill_caps[key] = e;
|
|
|
|
const int max_level_key = (e.class_id * 1000000) + e.skill_id;
|
|
auto it = skill_max_level.find(max_level_key);
|
|
if (it != skill_max_level.end()) {
|
|
// Key found, update the value if the new level is higher
|
|
if (e.level > it->second) {
|
|
it->second = e.level;
|
|
}
|
|
// we never want to exceed the defined rule skill cap max level
|
|
if (it->second > skill_cap_max_level) {
|
|
it->second = skill_cap_max_level;
|
|
}
|
|
}
|
|
else {
|
|
// Key not found, insert the new key-value pair
|
|
skill_max_level[max_level_key] = e.level;
|
|
}
|
|
}
|
|
|
|
LogInfo(
|
|
"Loaded [{}] Skill Cap Entr{}",
|
|
l.size(),
|
|
l.size() != 1 ? "ies" : "y"
|
|
);
|
|
}
|
|
|
|
void SkillCaps::ReloadSkillCaps()
|
|
{
|
|
ClearSkillCaps();
|
|
LoadSkillCaps();
|
|
}
|