Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix: party shared experience #3133

Open
wants to merge 5 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
27 changes: 8 additions & 19 deletions data/events/scripts/party.lua
Original file line number Diff line number Diff line change
Expand Up @@ -66,25 +66,14 @@ function Party:onDisband()
end

function Party:onShareExperience(exp)
local sharedExperienceMultiplier = 1.20 --20%
local vocationsIds = {}
local uniqueVocationsCount = self:getUniqueVocationsCount()
local partySize = self:getMemberCount() + 1

local vocationId = self:getLeader():getVocation():getBase():getId()
if vocationId ~= VOCATION_NONE then
table.insert(vocationsIds, vocationId)
end

for _, member in ipairs(self:getMembers()) do
vocationId = member:getVocation():getBase():getId()
if not table.contains(vocationsIds, vocationId) and vocationId ~= VOCATION_NONE then
table.insert(vocationsIds, vocationId)
end
end

local size = #vocationsIds
if size > 1 then
sharedExperienceMultiplier = 1.0 + ((size * (5 * (size - 1) + 10)) / 100)
end
-- Formula to calculate the % based on the vocations amount
local sharedExperienceMultiplier = ((0.1 * (uniqueVocationsCount ^ 2)) - (0.2 * uniqueVocationsCount) + 1.3)
-- Since the formula its non linear, we need to subtract 0.1 if all vocations are present,
-- because on all vocations the multiplier is 2.1 and it should be 2.0
sharedExperienceMultiplier = partySize < 4 and sharedExperienceMultiplier or sharedExperienceMultiplier - 0.1

return math.ceil((exp * sharedExperienceMultiplier) / (#self:getMembers() + 1))
return math.ceil((exp * sharedExperienceMultiplier) / partySize)
end
26 changes: 24 additions & 2 deletions src/creatures/players/grouping/party.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
#include "config/configmanager.hpp"
#include "creatures/creature.hpp"
#include "creatures/players/player.hpp"
#include "creatures/players/vocations/vocation.hpp"
#include "game/game.hpp"
#include "game/movement/position.hpp"
#include "lua/callbacks/event_callback.hpp"
Expand Down Expand Up @@ -61,6 +62,25 @@ size_t Party::getInvitationCount() const {
return inviteList.size();
}

uint8_t Party::getUniqueVocationsCount() const {
std::unordered_set<uint8_t> uniqueVocations;

for (const auto &player : getPlayers()) {
if (uniqueVocations.size() >= 4) {
break;
}

const auto &vocation = player->getVocation();
if (!vocation) {
continue;
}

uniqueVocations.insert(vocation->getBaseId());
}

return uniqueVocations.size();
}

void Party::disband() {
if (!g_events().eventPartyOnDisband(getParty())) {
return;
Expand Down Expand Up @@ -504,9 +524,11 @@ void Party::shareExperience(uint64_t experience, const std::shared_ptr<Creature>
g_callbacks().executeCallback(EventCallback_t::partyOnShareExperience, &EventCallback::partyOnShareExperience, getParty(), std::ref(shareExperience));

for (const auto &member : getMembers()) {
member->onGainSharedExperience(shareExperience, target);
const auto memberStaminaBoost = static_cast<float>(member->getStaminaXpBoost()) / 100;
member->onGainSharedExperience(shareExperience * memberStaminaBoost, target);
}
leader->onGainSharedExperience(shareExperience, target);
const auto leaderStaminaBoost = static_cast<float>(leader->getStaminaXpBoost()) / 100;
leader->onGainSharedExperience(shareExperience * leaderStaminaBoost, target);
}

bool Party::canUseSharedExperience(const std::shared_ptr<Player> &player) {
Expand Down
1 change: 1 addition & 0 deletions src/creatures/players/grouping/party.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,7 @@ class Party final : public SharedObject {
std::vector<std::shared_ptr<Player>> getInvitees();
size_t getMemberCount() const;
size_t getInvitationCount() const;
uint8_t getUniqueVocationsCount() const;

void disband();
bool invitePlayer(const std::shared_ptr<Player> &player);
Expand Down
12 changes: 12 additions & 0 deletions src/lua/functions/creatures/player/party_functions.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ void PartyFunctions::init(lua_State* L) {
Lua::registerMethod(L, "Party", "getMemberCount", PartyFunctions::luaPartyGetMemberCount);
Lua::registerMethod(L, "Party", "getInvitees", PartyFunctions::luaPartyGetInvitees);
Lua::registerMethod(L, "Party", "getInviteeCount", PartyFunctions::luaPartyGetInviteeCount);
Lua::registerMethod(L, "Party", "getUniqueVocationsCount", PartyFunctions::luaPartyGetUniqueVocationsCount);
Lua::registerMethod(L, "Party", "addInvite", PartyFunctions::luaPartyAddInvite);
Lua::registerMethod(L, "Party", "removeInvite", PartyFunctions::luaPartyRemoveInvite);
Lua::registerMethod(L, "Party", "addMember", PartyFunctions::luaPartyAddMember);
Expand Down Expand Up @@ -162,6 +163,17 @@ int PartyFunctions::luaPartyGetInviteeCount(lua_State* L) {
return 1;
}

int PartyFunctions::luaPartyGetUniqueVocationsCount(lua_State* L) {
// party:getUniqueVocationsCount()
const auto &party = Lua::getUserdataShared<Party>(L, 1);
if (party) {
lua_pushnumber(L, party->getUniqueVocationsCount());
} else {
lua_pushnil(L);
}
return 1;
}

int PartyFunctions::luaPartyAddInvite(lua_State* L) {
// party:addInvite(player)
const auto &player = Lua::getPlayer(L, 2);
Expand Down
1 change: 1 addition & 0 deletions src/lua/functions/creatures/player/party_functions.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ class PartyFunctions {
static int luaPartyGetMemberCount(lua_State* L);
static int luaPartyGetInvitees(lua_State* L);
static int luaPartyGetInviteeCount(lua_State* L);
static int luaPartyGetUniqueVocationsCount(lua_State* L);
static int luaPartyAddInvite(lua_State* L);
static int luaPartyRemoveInvite(lua_State* L);
static int luaPartyAddMember(lua_State* L);
Expand Down
Loading