[Rules] Add Group/Raid Experience Rules (#2850)

# Notes
- Add `Character:EnableGroupMemberEXPModifier`, enables or disables member-based experience modifiers in groups, default `true`.
- Add `Character:EnableRaidEXPModifier`, enables or disables member-based experience modifiers in raids, default `true`.
- Add `Character:EnableRaidMemberEXPModifier`, enables or disables member-based experience modifiers in raids, default `true`.
This commit is contained in:
Alex King 2023-02-13 01:25:59 -05:00 committed by GitHub
parent 85f7b10f90
commit 97edb09fba
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 34 additions and 17 deletions

View File

@ -197,10 +197,13 @@ RULE_BOOL(Character, PetZoneWithOwner, true, "Should Pets Zone with Owner")
RULE_BOOL(Character, FullManaOnDeath, true, "On death set mana to full")
RULE_BOOL(Character, FullEndurOnDeath, true, "On death set endurance to full")
RULE_INT(Character, ExperiencePercentCapPerKill, -1, "Caps the percentage of experience that can be gained per kill. -1 disables the cap; 0 blocks all (non-aa) xp.")
RULE_BOOL(Character, EnableGroupEXPModifier, true, "Enable or disable the group experience modifier based on number of players in group, default is true")
RULE_BOOL(Character, EnableGroupEXPModifier, true, "Enable or disable the group experience modifier in group, default is true")
RULE_BOOL(Character, EnableGroupMemberEXPModifier, true, "Enable or disable the group member experience modifier based on number of players in group, default is true")
RULE_REAL(Character, GroupMemberEXPModifier, 0.2, "Sets the group experience modifier per members between 2 and 5, default is 0.2")
RULE_REAL(Character, FullGroupEXPModifier, 2.16, "Sets the group experience modifier for a full group, default is 2.16")
RULE_BOOL(Character, IgnoreLevelBasedHasteCaps, false, "Ignores hard coded level based haste caps.")
RULE_BOOL(Character, EnableRaidEXPModifier, true, "Enable or disable the raid experience modifier, default is true")
RULE_BOOL(Character, EnableRaidMemberEXPModifier, true, "Enable or disable the raid experience modifier based on members in raid, default is true")
RULE_CATEGORY_END()
RULE_CATEGORY(Mercs)

View File

@ -1115,11 +1115,11 @@ void Group::SplitExp(const uint64 exp, Mob* other) {
return;
}
auto group_experience = exp;
auto group_experience = exp;
const auto highest_level = GetHighestLevel();
auto group_modifier = 1.0f;
if (RuleB(Character, EnableGroupEXPModifier)) {
if (RuleB(Character, EnableGroupMemberEXPModifier)) {
if (EQ::ValueWithin(member_count, 2, 5)) {
group_modifier = 1 + RuleR(Character, GroupMemberEXPModifier) * (member_count - 1); // 2 = 1.2x, 3 = 1.4x, 4 = 1.6x, 5 = 1.8x
} else if (member_count == 6) {
@ -1128,11 +1128,18 @@ void Group::SplitExp(const uint64 exp, Mob* other) {
}
if (EQ::ValueWithin(member_count, 2, 6)) {
group_experience += static_cast<uint64>(
static_cast<float>(exp) *
group_modifier *
RuleR(Character, GroupExpMultiplier)
);
if (RuleB(Character, EnableGroupEXPModifier)) {
group_experience += static_cast<uint64>(
static_cast<float>(exp) *
group_modifier *
RuleR(Character, GroupExpMultiplier)
);
} else {
group_experience += static_cast<uint64>(
static_cast<float>(exp) *
group_modifier
);
}
}
const uint8 consider_level = Mob::GetLevelCon(highest_level, other->GetLevel());
@ -1142,8 +1149,8 @@ void Group::SplitExp(const uint64 exp, Mob* other) {
for (const auto& m : members) {
if (m && m->IsClient()) {
const int32 diff = m->GetLevel() - highest_level;
int32 max_diff = -(m->GetLevel() * 15 / 10 - m->GetLevel());
const int32 diff = m->GetLevel() - highest_level;
int32 max_diff = -(m->GetLevel() * 15 / 10 - m->GetLevel());
if (max_diff > -5) {
max_diff = -5;
@ -1172,23 +1179,30 @@ void Raid::SplitExp(const uint64 exp, Mob* other) {
return;
}
auto raid_experience = exp;
auto raid_experience = exp;
const auto highest_level = GetHighestLevel();
raid_experience = static_cast<uint64>(
static_cast<float>(raid_experience) *
(1.0f - RuleR(Character, RaidExpMultiplier))
);
if (RuleB(Character, EnableRaidEXPModifier)) {
raid_experience = static_cast<uint64>(
static_cast<float>(raid_experience) *
(1.0f - RuleR(Character, RaidExpMultiplier))
);
}
const auto consider_level = Mob::GetLevelCon(highest_level, other->GetLevel());
if (consider_level == CON_GRAY) {
return;
}
uint32 member_modifier = 1;
if (RuleB(Character, EnableRaidMemberEXPModifier)) {
member_modifier = member_count;
}
for (const auto& m : members) {
if (m.member) {
const int32 diff = m.member->GetLevel() - highest_level;
int32 max_diff = -(m.member->GetLevel() * 15 / 10 - m.member->GetLevel());
int32 max_diff = -(m.member->GetLevel() * 15 / 10 - m.member->GetLevel());
if (max_diff > -5) {
max_diff = -5;
@ -1196,7 +1210,7 @@ void Raid::SplitExp(const uint64 exp, Mob* other) {
if (diff >= max_diff) {
const uint64 tmp = (m.member->GetLevel() + 3) * (m.member->GetLevel() + 3) * 75 * 35 / 10;
const uint64 tmp2 = (raid_experience / member_count) + 1;
const uint64 tmp2 = (raid_experience / member_modifier) + 1;
m.member->AddEXP(tmp < tmp2 ? tmp : tmp2, consider_level);
}
}