X-Git-Url: https://de.git.xonotic.org/?a=blobdiff_plain;f=qcsrc%2Fcommon%2Fgamemodes%2Fgamemode%2Fclanarena%2Fsv_clanarena.qc;h=2bbed4a9abb78f5cb8fd73ecbdf5d9a9a68474f7;hb=79012b90e96396059bcc310a8a95ae38918993a4;hp=4c889cb24be655fe22afa1af098046b1a0219082;hpb=ba7c5c7aa1351282377f6c4afc4653a130409255;p=xonotic%2Fxonotic-data.pk3dir.git diff --git a/qcsrc/common/gamemodes/gamemode/clanarena/sv_clanarena.qc b/qcsrc/common/gamemodes/gamemode/clanarena/sv_clanarena.qc index 4c889cb24b..ba2402f276 100644 --- a/qcsrc/common/gamemodes/gamemode/clanarena/sv_clanarena.qc +++ b/qcsrc/common/gamemodes/gamemode/clanarena/sv_clanarena.qc @@ -62,7 +62,6 @@ int CA_GetWinnerTeam() void nades_Clear(entity player); -#define CA_ALIVE_TEAMS_OK() (Team_GetNumberOfAliveTeams() == NumTeams(ca_teams)) float CA_CheckWinner() { if(round_handler_GetEndTime() > 0 && round_handler_GetEndTime() - time <= 0) @@ -115,7 +114,7 @@ bool CA_CheckTeams() static int prev_missing_teams_mask; allowed_to_spawn = true; CA_count_alive_players(); - if(CA_ALIVE_TEAMS_OK()) + if (Team_GetNumberOfAliveTeams() == NumTeams(ca_teams)) { if(prev_missing_teams_mask > 0) Kill_Notification(NOTIF_ALL, NULL, MSG_CENTER, CPID_MISSING_TEAMS); @@ -148,7 +147,7 @@ bool CA_CheckTeams() bool ca_isEliminated(entity e) { - if(e.caplayer == 1 && (IS_DEAD(e) || e.frags == FRAGS_LMS_LOSER)) + if(e.caplayer == 1 && (IS_DEAD(e) || e.frags == FRAGS_PLAYER_OUT_OF_GAME)) return true; if(e.caplayer == 0.5) return true; @@ -164,7 +163,7 @@ entity CA_SpectateNext(entity player, entity start) { if (SAME_TEAM(player, e)) return e; } - // restart from begining + // restart from the beginning for (entity e = NULL; (e = find(e, classname, STR_PLAYER)); ) { if (SAME_TEAM(player, e)) return e; @@ -225,7 +224,6 @@ MUTATOR_HOOKFUNCTION(ca, reset_map_players) PutClientInServer(it); } }); - bot_relinkplayerlist(); return true; } @@ -253,12 +251,13 @@ entity ca_LastPlayerForTeam(entity this) { entity last_pl = NULL; FOREACH_CLIENT(IS_PLAYER(it) && it != this, { - if (!IS_DEAD(it)) - if (SAME_TEAM(this, it)) - if (!last_pl) - last_pl = it; - else - return NULL; + if (!IS_DEAD(it) && SAME_TEAM(this, it)) + { + if (!last_pl) + last_pl = it; + else + return NULL; + } }); return last_pl; } @@ -286,11 +285,7 @@ MUTATOR_HOOKFUNCTION(ca, PlayerDies) } frag_target.respawn_flags |= RESPAWN_FORCE; if (!warmup_stage) - { eliminatedPlayers.SendFlags |= 1; - if (IS_BOT_CLIENT(frag_target)) - bot_clear(frag_target); - } return true; } @@ -298,7 +293,7 @@ MUTATOR_HOOKFUNCTION(ca, ClientDisconnect) { entity player = M_ARGV(0, entity); - if (player.caplayer == 1) + if (IS_PLAYER(player) && !IS_DEAD(player)) ca_LastPlayerForTeam_Notify(player); return true; } @@ -307,12 +302,15 @@ MUTATOR_HOOKFUNCTION(ca, MakePlayerObserver) { entity player = M_ARGV(0, entity); - if (!IS_DEAD(player)) + if (IS_PLAYER(player) && !IS_DEAD(player)) ca_LastPlayerForTeam_Notify(player); if (player.killindicator_teamchange == -2) // player wants to spectate + { + entcs_update_players(player); player.caplayer = 0; + } if (player.caplayer) - player.frags = FRAGS_LMS_LOSER; + player.frags = FRAGS_PLAYER_OUT_OF_GAME; if (!warmup_stage) eliminatedPlayers.SendFlags |= 1; if (!player.caplayer) @@ -333,15 +331,15 @@ MUTATOR_HOOKFUNCTION(ca, GiveFragsForKill, CBC_ORDER_FIRST) MUTATOR_HOOKFUNCTION(ca, SetStartItems) { - start_items &= ~IT_UNLIMITED_AMMO; - start_health = warmup_start_health = cvar("g_lms_start_health"); - start_armorvalue = warmup_start_armorvalue = cvar("g_lms_start_armor"); - start_ammo_shells = warmup_start_ammo_shells = cvar("g_lms_start_ammo_shells"); - start_ammo_nails = warmup_start_ammo_nails = cvar("g_lms_start_ammo_nails"); - start_ammo_rockets = warmup_start_ammo_rockets = cvar("g_lms_start_ammo_rockets"); - start_ammo_cells = warmup_start_ammo_cells = cvar("g_lms_start_ammo_cells"); - start_ammo_plasma = warmup_start_ammo_plasma = cvar("g_lms_start_ammo_plasma"); - start_ammo_fuel = warmup_start_ammo_fuel = cvar("g_lms_start_ammo_fuel"); + start_items &= ~(IT_UNLIMITED_AMMO | IT_UNLIMITED_SUPERWEAPONS); + start_health = warmup_start_health = cvar("g_ca_start_health"); + start_armorvalue = warmup_start_armorvalue = cvar("g_ca_start_armor"); + start_ammo_shells = warmup_start_ammo_shells = cvar("g_ca_start_ammo_shells"); + start_ammo_nails = warmup_start_ammo_nails = cvar("g_ca_start_ammo_nails"); + start_ammo_rockets = warmup_start_ammo_rockets = cvar("g_ca_start_ammo_rockets"); + start_ammo_cells = warmup_start_ammo_cells = cvar("g_ca_start_ammo_cells"); + start_ammo_plasma = warmup_start_ammo_plasma = cvar("g_ca_start_ammo_plasma"); + start_ammo_fuel = warmup_start_ammo_fuel = cvar("g_ca_start_ammo_fuel"); } MUTATOR_HOOKFUNCTION(ca, Damage_Calculate) @@ -368,7 +366,7 @@ MUTATOR_HOOKFUNCTION(ca, FilterItem) entity item = M_ARGV(0, entity); if (autocvar_g_powerups <= 0) - if (item.flags & FL_POWERUP) + if (item.itemdef.instanceOfPowerup) return true; if (autocvar_g_pickup_items <= 0) @@ -377,16 +375,40 @@ MUTATOR_HOOKFUNCTION(ca, FilterItem) MUTATOR_HOOKFUNCTION(ca, PlayerDamage_SplitHealthArmor) { + if (time < game_starttime || (round_handler_IsActive() && !round_handler_IsRoundStarted())) + return; + entity frag_attacker = M_ARGV(1, entity); entity frag_target = M_ARGV(2, entity); + float frag_deathtype = M_ARGV(6, float); float frag_damage = M_ARGV(7, float); - float damage_take = M_ARGV(4, float); - float damage_save = M_ARGV(5, float); + float damage_take = bound(0, M_ARGV(4, float), GetResource(frag_target, RES_HEALTH)); + float damage_save = bound(0, M_ARGV(5, float), GetResource(frag_target, RES_ARMOR)); float excess = max(0, frag_damage - damage_take - damage_save); - if (frag_target != frag_attacker && IS_PLAYER(frag_attacker)) + //non-friendly fire + if (frag_target != frag_attacker && IS_PLAYER(frag_attacker) && DIFF_TEAM(frag_target, frag_attacker)) GameRules_scoring_add_team(frag_attacker, SCORE, (frag_damage - excess) * autocvar_g_ca_damage2score_multiplier); + + //friendly fire + if (SAME_TEAM(frag_target, frag_attacker)) + GameRules_scoring_add_team(frag_attacker, SCORE, (-1 * (frag_damage - excess)) * autocvar_g_ca_damage2score_multiplier); + + //handle (environmental hazard) suiciding, check first if player has a registered attacker who most likely pushed them there to avoid punishing pushed players as pushers are already rewarded + //deathtypes: + //kill = suicide, drown = drown in water/liquid, hurttrigger = out of the map void or hurt triggers inside maps like electric sparks + //camp = campcheck, lava = lava, slime = slime + //team change / rebalance suicides are currently not included + if (!IS_PLAYER(frag_attacker) && ( + frag_deathtype == DEATH_KILL.m_id || + frag_deathtype == DEATH_DROWN.m_id || + frag_deathtype == DEATH_HURTTRIGGER.m_id || + frag_deathtype == DEATH_CAMP.m_id || + frag_deathtype == DEATH_LAVA.m_id || + frag_deathtype == DEATH_SLIME.m_id || + frag_deathtype == DEATH_SWAMP.m_id)) + GameRules_scoring_add_team(frag_target, SCORE, (-1 * (frag_damage - excess)) * autocvar_g_ca_damage2score_multiplier); } MUTATOR_HOOKFUNCTION(ca, CalculateRespawnTime) @@ -421,7 +443,8 @@ MUTATOR_HOOKFUNCTION(ca, SpectateNext) { entity client = M_ARGV(0, entity); - if (!autocvar_g_ca_spectate_enemies && client.caplayer) + if (!autocvar_g_ca_spectate_enemies && client.caplayer + && Team_GetNumberOfAlivePlayers(Entity_GetTeam(client))) { entity targ = M_ARGV(1, entity); M_ARGV(1, entity) = CA_SpectateNext(client, targ); @@ -435,7 +458,8 @@ MUTATOR_HOOKFUNCTION(ca, SpectatePrev) entity targ = M_ARGV(1, entity); entity first = M_ARGV(2, entity); - if (!autocvar_g_ca_spectate_enemies && client.caplayer) + if (!autocvar_g_ca_spectate_enemies && client.caplayer + && Team_GetNumberOfAlivePlayers(Entity_GetTeam(client))) { do { targ = targ.chain; } while(targ && DIFF_TEAM(targ, client)); @@ -448,6 +472,8 @@ MUTATOR_HOOKFUNCTION(ca, SpectatePrev) return MUT_SPECPREV_RETURN; } } + else + return MUT_SPECPREV_CONTINUE; M_ARGV(1, entity) = targ; @@ -479,11 +505,6 @@ MUTATOR_HOOKFUNCTION(ca, ClientCommand_Spectate) return MUT_SPECCMD_CONTINUE; } -MUTATOR_HOOKFUNCTION(ca, WantWeapon) -{ - M_ARGV(2, bool) = true; // all weapons -} - MUTATOR_HOOKFUNCTION(ca, HideTeamNagger) { return true; // doesn't work well with the whole spectator as player thing @@ -498,6 +519,14 @@ MUTATOR_HOOKFUNCTION(ca, GetPlayerStatus) MUTATOR_HOOKFUNCTION(ca, SetWeaponArena) { - // most weapons arena - if (M_ARGV(0, string) == "0" || M_ARGV(0, string) == "") M_ARGV(0, string) = "most"; + if (M_ARGV(0, string) == "0" || M_ARGV(0, string) == "") + M_ARGV(0, string) = autocvar_g_ca_weaponarena; +} + +MUTATOR_HOOKFUNCTION(ca, SV_ParseServerCommand) +{ + string cmd_name = M_ARGV(0, string); + if (cmd_name == "shuffleteams") + shuffleteams_on_reset_map = !allowed_to_spawn; + return false; }