From 03e3ff808e98b21567dccec3d0735afa0b7a51b7 Mon Sep 17 00:00:00 2001 From: terencehill Date: Mon, 15 Nov 2021 14:48:22 +0100 Subject: [PATCH] LMS: show number of leaders in the HUD --- qcsrc/common/gamemodes/gamemode/lms/cl_lms.qc | 23 +++++++ qcsrc/common/gamemodes/gamemode/lms/cl_lms.qh | 3 + qcsrc/common/gamemodes/gamemode/lms/lms.qh | 6 ++ qcsrc/common/gamemodes/gamemode/lms/sv_lms.qc | 66 ++++++++++++------- 4 files changed, 75 insertions(+), 23 deletions(-) diff --git a/qcsrc/common/gamemodes/gamemode/lms/cl_lms.qc b/qcsrc/common/gamemodes/gamemode/lms/cl_lms.qc index 7be2d31bc..b0a792c33 100644 --- a/qcsrc/common/gamemodes/gamemode/lms/cl_lms.qc +++ b/qcsrc/common/gamemodes/gamemode/lms/cl_lms.qc @@ -30,3 +30,26 @@ MUTATOR_HOOKFUNCTION(cl_lms, DrawInfoMessages) } return false; } + +void HUD_Mod_LMS_Draw(vector myPos, vector mySize) +{ + int stat = STAT(REDALIVE); // number of leaders + if(!stat) + { + mod_active = 0; + return; + } + + string pic = "player_neutral"; + vector color = '1 1 1'; + + drawpic_aspect_skin(myPos, pic, vec2(0.5 * mySize.x, mySize.y), '1 1 1', panel_fg_alpha, DRAWFLAG_NORMAL); + drawstring_aspect(myPos + eX * 0.5 * mySize.x, ftos(stat), vec2(0.5 * mySize.x, mySize.y), color, panel_fg_alpha, DRAWFLAG_NORMAL); +} + +void HUD_Mod_LMS(vector myPos, vector mySize) +{ + mod_active = 1; + + HUD_Mod_LMS_Draw(myPos, mySize); +} diff --git a/qcsrc/common/gamemodes/gamemode/lms/cl_lms.qh b/qcsrc/common/gamemodes/gamemode/lms/cl_lms.qh index 6f70f09be..2a1d52751 100644 --- a/qcsrc/common/gamemodes/gamemode/lms/cl_lms.qh +++ b/qcsrc/common/gamemodes/gamemode/lms/cl_lms.qh @@ -1 +1,4 @@ #pragma once + +void HUD_Mod_LMS(vector myPos, vector mySize); +void HUD_Mod_LMS_Draw(vector myPos, vector mySize); diff --git a/qcsrc/common/gamemodes/gamemode/lms/lms.qh b/qcsrc/common/gamemodes/gamemode/lms/lms.qh index 8a208c583..b90f6c6eb 100644 --- a/qcsrc/common/gamemodes/gamemode/lms/lms.qh +++ b/qcsrc/common/gamemodes/gamemode/lms/lms.qh @@ -2,6 +2,9 @@ #include +#ifdef CSQC +void HUD_Mod_LMS(vector myPos, vector mySize); +#endif CLASS(LastManStanding, Gametype) INIT(LastManStanding) { @@ -17,5 +20,8 @@ CLASS(LastManStanding, Gametype) returns(menu, _("Lives:"), 3, 50, 1, "g_lms_lives_override", string_null, string_null); } ATTRIB(LastManStanding, m_legacydefaults, string, "9 20 0"); +#ifdef CSQC + ATTRIB(LastManStanding, m_modicons, void(vector myPos, vector mySize), HUD_Mod_LMS); +#endif ENDCLASS(LastManStanding) REGISTER_GAMETYPE(LMS, NEW(LastManStanding)); diff --git a/qcsrc/common/gamemodes/gamemode/lms/sv_lms.qc b/qcsrc/common/gamemodes/gamemode/lms/sv_lms.qc index a4ad5cd52..629a2940f 100644 --- a/qcsrc/common/gamemodes/gamemode/lms/sv_lms.qc +++ b/qcsrc/common/gamemodes/gamemode/lms/sv_lms.qc @@ -23,7 +23,7 @@ float autocvar_g_lms_dynamic_vampire_factor_increase; float autocvar_g_lms_dynamic_vampire_factor_max; int autocvar_g_lms_dynamic_vampire_min_lives_diff; -.float lms_wp_time; +.float lms_leader; // main functions int LMS_NewPlayerLives() @@ -131,20 +131,19 @@ int WinningCondition_LMS() // runs on waypoints which are attached to leaders, updates once per frame bool lms_waypointsprite_visible_for_player(entity this, entity player, entity view) { - if(view.lms_wp_time) + if(view.lms_leader) if(IS_SPEC(player)) return false; // we don't want spectators of leaders to see the attached waypoint on the top of their screen float leader_time = autocvar_g_lms_leader_wp_time; float leader_repeat_time = leader_time + autocvar_g_lms_leader_wp_time_repeat; - float wp_time = this.owner.lms_wp_time; - if (wp_time && (time - wp_time) % leader_repeat_time > leader_time) + if (time % leader_repeat_time > leader_time) return false; return true; } -void lms_UpdateWaypoints() +void lms_UpdateLeaders() { int max_lives = 0; int pl_cnt = 0; @@ -171,30 +170,19 @@ void lms_UpdateWaypoints() int lives = GameRules_scoring_add(it, LMS_LIVES, 0); if (lives == max_lives) { - if (!it.waypointsprite_attachedforcarrier) - { - WaypointSprite_AttachCarrier(WP_LmsLeader, it, RADARICON_FLAGCARRIER); - it.waypointsprite_attachedforcarrier.waypointsprite_visible_for_player = lms_waypointsprite_visible_for_player; - WaypointSprite_UpdateRule(it.waypointsprite_attachedforcarrier, 0, SPRITERULE_DEFAULT); - vector pl_color = colormapPaletteColor(it.clientcolors & 0x0F, false); - WaypointSprite_UpdateTeamRadar(it.waypointsprite_attachedforcarrier, RADARICON_FLAGCARRIER, pl_color); - WaypointSprite_Ping(it.waypointsprite_attachedforcarrier); - } - if (!it.lms_wp_time) - it.lms_wp_time = time; + if (!it.lms_leader) + it.lms_leader = true; } else { - if (it.waypointsprite_attachedforcarrier) - WaypointSprite_Kill(it.waypointsprite_attachedforcarrier); - it.lms_wp_time = 0; + it.lms_leader = false; } }); else FOREACH_CLIENT(IS_PLAYER(it) && it.frags != FRAGS_PLAYER_OUT_OF_GAME, { if (it.waypointsprite_attachedforcarrier) WaypointSprite_Kill(it.waypointsprite_attachedforcarrier); - it.lms_wp_time = 0; + it.lms_leader = false; }); } @@ -227,7 +215,7 @@ MUTATOR_HOOKFUNCTION(lms, reset_map_players) TRANSMUTE(Player, it); PutClientInServer(it); - it.lms_wp_time = 0; + it.lms_leader = false; if (it.waypointsprite_attachedforcarrier) WaypointSprite_Kill(it.waypointsprite_attachedforcarrier); }); @@ -365,7 +353,7 @@ void lms_RemovePlayer(entity player) TRANSMUTE(Observer, player); } if (autocvar_g_lms_leader_wp_lives > 0) - lms_UpdateWaypoints(); + lms_UpdateLeaders(); } if (CS(player).killcount != FRAGS_SPECTATOR && player.lms_spectate_warning < 3) @@ -419,14 +407,46 @@ MUTATOR_HOOKFUNCTION(lms, ClientConnect) player.frags = FRAGS_SPECTATOR; } +int lms_leaders = 0; MUTATOR_HOOKFUNCTION(lms, PlayerPreThink) { entity player = M_ARGV(0, entity); + // recycled REDALIVE to avoid adding a dedicated stat + STAT(REDALIVE, player) = lms_leaders; + if(player.deadflag == DEAD_DYING) player.deadflag = DEAD_RESPAWNING; } +MUTATOR_HOOKFUNCTION(lms, SV_StartFrame) +{ + lms_leaders = 0; + FOREACH_CLIENT(true, { + if (IS_PLAYER(it) && it.frags != FRAGS_PLAYER_OUT_OF_GAME) + { + if (it.lms_leader) + { + if (!it.waypointsprite_attachedforcarrier) + { + WaypointSprite_AttachCarrier(WP_LmsLeader, it, RADARICON_FLAGCARRIER); + it.waypointsprite_attachedforcarrier.waypointsprite_visible_for_player = lms_waypointsprite_visible_for_player; + WaypointSprite_UpdateRule(it.waypointsprite_attachedforcarrier, 0, SPRITERULE_DEFAULT); + vector pl_color = colormapPaletteColor(it.clientcolors & 0x0F, false); + WaypointSprite_UpdateTeamRadar(it.waypointsprite_attachedforcarrier, RADARICON_FLAGCARRIER, pl_color); + WaypointSprite_Ping(it.waypointsprite_attachedforcarrier); + } + lms_leaders++; + } + } + else + { + if (it.waypointsprite_attachedforcarrier) + WaypointSprite_Kill(it.waypointsprite_attachedforcarrier); + } + }); +} + MUTATOR_HOOKFUNCTION(lms, PlayerRegen) { if(autocvar_g_lms_regenerate) @@ -481,7 +501,7 @@ MUTATOR_HOOKFUNCTION(lms, Damage_Calculate) MUTATOR_HOOKFUNCTION(lms, PlayerDied) { if (!warmup_stage && autocvar_g_lms_leader_wp_lives > 0) - lms_UpdateWaypoints(); + lms_UpdateLeaders(); } MUTATOR_HOOKFUNCTION(lms, CalculateRespawnTime) -- 2.39.2