add EXP multipliers
This commit is contained in:
@@ -21,6 +21,7 @@ Lobby::Lobby(uint32_t id)
|
||||
episode(Episode::NONE),
|
||||
mode(GameMode::NORMAL),
|
||||
difficulty(0),
|
||||
exp_multiplier(1),
|
||||
random_seed(random_object<uint32_t>()),
|
||||
event(0),
|
||||
block(0),
|
||||
|
||||
@@ -69,6 +69,7 @@ struct Lobby : public std::enable_shared_from_this<Lobby> {
|
||||
Episode episode;
|
||||
GameMode mode;
|
||||
uint8_t difficulty; // 0-3
|
||||
uint16_t exp_multiplier;
|
||||
std::u16string password;
|
||||
std::u16string name;
|
||||
// This seed is also sent to the client for rare enemy generation
|
||||
|
||||
@@ -3417,6 +3417,9 @@ static void on_6F(shared_ptr<ServerState> s, shared_ptr<Client> c,
|
||||
c->flags &= (~Client::Flag::LOADING);
|
||||
|
||||
send_resume_game(l, c);
|
||||
if (l->version == GameVersion::BB) {
|
||||
send_set_exp_multiplier(l);
|
||||
}
|
||||
send_server_time(c);
|
||||
// Only get player info again on BB, since on other versions the returned info
|
||||
// only includes items that would be saved if the client disconnects
|
||||
|
||||
@@ -1447,7 +1447,7 @@ static void on_enemy_killed_bb(shared_ptr<ServerState> s,
|
||||
|
||||
uint32_t experience = 0xFFFFFFFF;
|
||||
try {
|
||||
experience = s->battle_params->get(l->mode == GameMode::SOLO, l->episode, l->difficulty, e.type).experience;
|
||||
experience = s->battle_params->get(l->mode == GameMode::SOLO, l->episode, l->difficulty, e.type).experience * l->exp_multiplier;
|
||||
} catch (const exception& e) {
|
||||
if (c->options.debug) {
|
||||
send_text_message_printf(c, "$C5E-%hX __MISSING__\n%s", cmd.enemy_id.load(), e.what());
|
||||
@@ -1472,9 +1472,8 @@ static void on_enemy_killed_bb(shared_ptr<ServerState> s,
|
||||
|
||||
if (experience != 0xFFFFFFFF) {
|
||||
// Killer gets full experience, others get 77%
|
||||
uint32_t player_exp = (e.last_hit_by_client_id == other_c->lobby_client_id)
|
||||
? experience
|
||||
: ((experience * 77) / 100);
|
||||
bool is_killer = (e.last_hit_by_client_id == other_c->lobby_client_id);
|
||||
uint32_t player_exp = is_killer ? experience : ((experience * 77) / 100);
|
||||
|
||||
other_c->game_data.player()->disp.experience += player_exp;
|
||||
send_give_experience(l, other_c, player_exp);
|
||||
@@ -1498,6 +1497,8 @@ static void on_enemy_killed_bb(shared_ptr<ServerState> s,
|
||||
if (leveled_up) {
|
||||
send_level_up(l, other_c);
|
||||
}
|
||||
|
||||
// TODO: Update kill counts on unsealable items
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+11
-1
@@ -2082,13 +2082,23 @@ void send_give_experience(shared_ptr<Lobby> l, shared_ptr<Client> c,
|
||||
if (c->version() != GameVersion::BB) {
|
||||
throw logic_error("6xBF can only be sent to BB clients");
|
||||
}
|
||||
|
||||
uint16_t client_id = c->lobby_client_id;
|
||||
G_GiveExperience_BB_6xBF cmd = {
|
||||
{0xBF, sizeof(G_GiveExperience_BB_6xBF) / 4, client_id}, amount};
|
||||
send_command_t(l, 0x60, 0x00, cmd);
|
||||
}
|
||||
|
||||
void send_set_exp_multiplier(std::shared_ptr<Lobby> l) {
|
||||
if (l->version != GameVersion::BB) {
|
||||
throw logic_error("6xDD can only be sent to BB clients");
|
||||
}
|
||||
if (!l->is_game()) {
|
||||
throw logic_error("6xDD can only be sent in games (not in lobbies)");
|
||||
}
|
||||
G_SetEXPMultiplier_BB_6xDD cmd = {{0xBF, sizeof(G_SetEXPMultiplier_BB_6xDD) / 4, l->exp_multiplier}};
|
||||
send_command_t(l, 0x60, 0x00, cmd);
|
||||
}
|
||||
|
||||
void send_rare_enemy_index_list(shared_ptr<Client> c, const vector<size_t>& indexes) {
|
||||
S_RareMonsterList_BB_DE cmd;
|
||||
if (indexes.size() > cmd.enemy_ids.size()) {
|
||||
|
||||
@@ -322,6 +322,7 @@ void send_shop(std::shared_ptr<Client> c, uint8_t shop_type);
|
||||
void send_level_up(std::shared_ptr<Lobby> l, std::shared_ptr<Client> c);
|
||||
void send_give_experience(std::shared_ptr<Lobby> l, std::shared_ptr<Client> c,
|
||||
uint32_t amount);
|
||||
void send_set_exp_multiplier(std::shared_ptr<Lobby> l);
|
||||
void send_rare_enemy_index_list(std::shared_ptr<Client> c, const std::vector<size_t>& indexes);
|
||||
void send_ep3_card_list_update(
|
||||
std::shared_ptr<ServerState> s, std::shared_ptr<Client> c);
|
||||
|
||||
Reference in New Issue
Block a user