Forbid character-based unlocks if you switched your skin in a context where it didn't auto-spectate you (more robust stop for #1231)

This commit is contained in:
toaster 2024-04-01 18:03:00 +01:00
parent 4f37a3f183
commit b818a7d776
3 changed files with 35 additions and 21 deletions

View file

@ -1203,33 +1203,40 @@ static void Got_NameAndColor(const UINT8 **cp, INT32 playernum)
// The following is a miniature subset of Got_Teamchange.
if ((gamestate == GS_LEVEL) // In a level?
&& (cv_restrictskinchange.value) // Skin changes are restricted?
&& (G_GametypeHasSpectators() && players[playernum].spectator == false) // not a spectator but could be?
&& (players[playernum].jointime > 1) // permit on join
&& (leveltime > introtime) // permit during intro turnaround
&& (players[playernum].skin != oldskin)) // a skin change actually happened?
{
for (i = 0; i < MAXPLAYERS; ++i)
{
if (i == playernum)
continue;
if (!playeringame[i])
continue;
if (players[i].spectator)
continue;
break;
}
players[playernum].roundconditions.switched_skin = true;
if (i != MAXPLAYERS // Someone on your server who isn't you?
&& LUA_HookTeamSwitch(&players[playernum], 0, false, false, false)) // fiiiine, lua can except it
if (
cv_restrictskinchange.value // Skin changes are restricted?
&& G_GametypeHasSpectators() // not a spectator...
&& players[playernum].spectator == false // ...but could be?
)
{
P_DamageMobj(players[playernum].mo, NULL, NULL, 1, DMG_SPECTATOR);
if (players[i].spectator)
for (i = 0; i < MAXPLAYERS; ++i)
{
HU_AddChatText(va("\x82*%s became a spectator.", player_names[playernum]), false);
if (i == playernum)
continue;
if (!playeringame[i])
continue;
if (players[i].spectator)
continue;
break;
}
FinalisePlaystateChange(playernum);
if (i != MAXPLAYERS // Someone on your server who isn't you?
&& LUA_HookTeamSwitch(&players[playernum], 0, false, false, false)) // fiiiine, lua can except it
{
P_DamageMobj(players[playernum].mo, NULL, NULL, 1, DMG_SPECTATOR);
if (players[i].spectator)
{
HU_AddChatText(va("\x82*%s became a spectator.", player_names[playernum]), false);
FinalisePlaystateChange(playernum);
}
}
}
}

View file

@ -464,6 +464,9 @@ struct roundconditions_t
// 32 triggers, one bit each, for map execution
UINT32 unlocktriggers;
// Forbidding skin-based unlocks if you changed your skin
boolean switched_skin;
};
// player_t struct for all skybox variables

View file

@ -1649,9 +1649,13 @@ boolean M_CheckCondition(condition_t *cn, player_t *player)
case UCRP_ISMAP:
return (gamemap == cn->requirement+1);
case UCRP_ISCHARACTER:
return (player->skin == cn->requirement);
return (
player->roundconditions.switched_skin == false
&& player->skin == cn->requirement
);
case UCRP_ISENGINECLASS:
return (player->skin < numskins
return (player->roundconditions.switched_skin == false
&& player->skin < numskins
&& R_GetEngineClass(
skins[player->skin].kartspeed,
skins[player->skin].kartweight,