mirror of
https://github.com/ZDoom/qzdoom-gpl.git
synced 2024-11-15 08:41:59 +00:00
Remove disconnecting players safely
Players who were disconnecting would be removed outside of the playsims control, causing problems with sector lists.
This commit is contained in:
parent
0f9a8176f5
commit
ae71f94ed2
4 changed files with 83 additions and 59 deletions
|
@ -39,7 +39,6 @@
|
||||||
#include "cmdlib.h"
|
#include "cmdlib.h"
|
||||||
#include "s_sound.h"
|
#include "s_sound.h"
|
||||||
#include "m_cheat.h"
|
#include "m_cheat.h"
|
||||||
#include "p_effect.h"
|
|
||||||
#include "p_local.h"
|
#include "p_local.h"
|
||||||
#include "c_dispatch.h"
|
#include "c_dispatch.h"
|
||||||
#include "sbar.h"
|
#include "sbar.h"
|
||||||
|
@ -670,6 +669,9 @@ void PlayerIsGone (int netnode, int netconsole)
|
||||||
{
|
{
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
|
if (!nodeingame[netnode])
|
||||||
|
return;
|
||||||
|
|
||||||
for (i = netnode + 1; i < doomcom.numnodes; ++i)
|
for (i = netnode + 1; i < doomcom.numnodes; ++i)
|
||||||
{
|
{
|
||||||
if (nodeingame[i])
|
if (nodeingame[i])
|
||||||
|
@ -680,55 +682,17 @@ void PlayerIsGone (int netnode, int netconsole)
|
||||||
doomcom.numnodes = netnode;
|
doomcom.numnodes = netnode;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (playeringame[netconsole])
|
||||||
|
{
|
||||||
|
players[netconsole].playerstate = PST_GONE;
|
||||||
|
}
|
||||||
nodeingame[netnode] = false;
|
nodeingame[netnode] = false;
|
||||||
playeringame[netconsole] = false;
|
|
||||||
nodejustleft[netnode] = false;
|
nodejustleft[netnode] = false;
|
||||||
|
|
||||||
if (deathmatch)
|
|
||||||
{
|
|
||||||
Printf ("%s left the game with %d frags\n",
|
|
||||||
players[netconsole].userinfo.GetName(),
|
|
||||||
players[netconsole].fragcount);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
Printf ("%s left the game\n", players[netconsole].userinfo.GetName());
|
|
||||||
}
|
|
||||||
|
|
||||||
// [RH] Revert each player to their own view if spying through the player who left
|
|
||||||
for (int ii = 0; ii < MAXPLAYERS; ++ii)
|
|
||||||
{
|
|
||||||
if (playeringame[ii] && players[ii].camera == players[netconsole].mo)
|
|
||||||
{
|
|
||||||
players[ii].camera = players[ii].mo;
|
|
||||||
if (ii == consoleplayer && StatusBar != NULL)
|
|
||||||
{
|
|
||||||
StatusBar->AttachToPlayer (&players[ii]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// [RH] Make the player disappear
|
|
||||||
FBehavior::StaticStopMyScripts (players[netconsole].mo);
|
|
||||||
if (players[netconsole].mo != NULL)
|
|
||||||
{
|
|
||||||
P_DisconnectEffect (players[netconsole].mo);
|
|
||||||
players[netconsole].mo->player = NULL;
|
|
||||||
players[netconsole].mo->Destroy ();
|
|
||||||
if (!(players[netconsole].mo->ObjectFlags & OF_EuthanizeMe))
|
|
||||||
{ // We just destroyed a morphed player, so now the original player
|
|
||||||
// has taken their place. Destroy that one too.
|
|
||||||
players[netconsole].mo->Destroy();
|
|
||||||
}
|
|
||||||
players[netconsole].mo = NULL;
|
|
||||||
players[netconsole].camera = NULL;
|
|
||||||
}
|
|
||||||
// [RH] Let the scripts know the player left
|
|
||||||
FBehavior::StaticStartTypedScripts (SCRIPT_Disconnect, NULL, true, netconsole);
|
|
||||||
if (netconsole == Net_Arbitrator)
|
if (netconsole == Net_Arbitrator)
|
||||||
{
|
{
|
||||||
bglobal.RemoveAllBots (true);
|
bglobal.RemoveAllBots(true);
|
||||||
Printf ("Removed all bots\n");
|
Printf("Removed all bots\n");
|
||||||
|
|
||||||
// Pick a new network arbitrator
|
// Pick a new network arbitrator
|
||||||
for (int i = 0; i < MAXPLAYERS; i++)
|
for (int i = 0; i < MAXPLAYERS; i++)
|
||||||
|
@ -737,20 +701,21 @@ void PlayerIsGone (int netnode, int netconsole)
|
||||||
{
|
{
|
||||||
Net_Arbitrator = i;
|
Net_Arbitrator = i;
|
||||||
players[i].settings_controller = true;
|
players[i].settings_controller = true;
|
||||||
Printf ("%s is the new arbitrator\n", players[i].userinfo.GetName());
|
Printf("%s is the new arbitrator\n", players[i].userinfo.GetName());
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (debugfile && NetMode == NET_PacketServer)
|
}
|
||||||
|
|
||||||
|
if (debugfile && NetMode == NET_PacketServer)
|
||||||
|
{
|
||||||
|
if (Net_Arbitrator == consoleplayer)
|
||||||
{
|
{
|
||||||
if (Net_Arbitrator == consoleplayer)
|
fprintf(debugfile, "I am the new master!\n");
|
||||||
{
|
}
|
||||||
fprintf (debugfile, "I am the new master!\n");
|
else
|
||||||
}
|
{
|
||||||
else
|
fprintf(debugfile, "Node %d is the new master!\n", nodeforplayer[Net_Arbitrator]);
|
||||||
{
|
|
||||||
fprintf (debugfile, "Node %d is the new master!\n", nodeforplayer[Net_Arbitrator]);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -176,7 +176,8 @@ typedef enum
|
||||||
PST_LIVE, // Playing or camping.
|
PST_LIVE, // Playing or camping.
|
||||||
PST_DEAD, // Dead on the ground, view follows killer.
|
PST_DEAD, // Dead on the ground, view follows killer.
|
||||||
PST_REBORN, // Ready to restart/respawn???
|
PST_REBORN, // Ready to restart/respawn???
|
||||||
PST_ENTER // [BC] Entered the game
|
PST_ENTER, // [BC] Entered the game
|
||||||
|
PST_GONE // Player has left the game
|
||||||
} playerstate_t;
|
} playerstate_t;
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -76,6 +76,7 @@
|
||||||
#include "d_net.h"
|
#include "d_net.h"
|
||||||
#include "d_event.h"
|
#include "d_event.h"
|
||||||
#include "p_acs.h"
|
#include "p_acs.h"
|
||||||
|
#include "p_effect.h"
|
||||||
#include "m_joy.h"
|
#include "m_joy.h"
|
||||||
#include "farchive.h"
|
#include "farchive.h"
|
||||||
#include "r_renderer.h"
|
#include "r_renderer.h"
|
||||||
|
@ -1013,10 +1014,16 @@ void G_Ticker ()
|
||||||
// do player reborns if needed
|
// do player reborns if needed
|
||||||
for (i = 0; i < MAXPLAYERS; i++)
|
for (i = 0; i < MAXPLAYERS; i++)
|
||||||
{
|
{
|
||||||
if (playeringame[i] &&
|
if (playeringame[i])
|
||||||
(players[i].playerstate == PST_REBORN || players[i].playerstate == PST_ENTER))
|
|
||||||
{
|
{
|
||||||
G_DoReborn (i, false);
|
if ((players[i].playerstate == PST_GONE))
|
||||||
|
{
|
||||||
|
G_DoPlayerPop(i);
|
||||||
|
}
|
||||||
|
if ((players[i].playerstate == PST_REBORN || players[i].playerstate == PST_ENTER))
|
||||||
|
{
|
||||||
|
G_DoReborn(i, false);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1658,6 +1665,56 @@ void G_DoReborn (int playernum, bool freshbot)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
// G_DoReborn
|
||||||
|
//
|
||||||
|
void G_DoPlayerPop(int playernum)
|
||||||
|
{
|
||||||
|
playeringame[playernum] = false;
|
||||||
|
|
||||||
|
if (deathmatch)
|
||||||
|
{
|
||||||
|
Printf("%s left the game with %d frags\n",
|
||||||
|
players[playernum].userinfo.GetName(),
|
||||||
|
players[playernum].fragcount);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Printf("%s left the game\n", players[playernum].userinfo.GetName());
|
||||||
|
}
|
||||||
|
|
||||||
|
// [RH] Revert each player to their own view if spying through the player who left
|
||||||
|
for (int ii = 0; ii < MAXPLAYERS; ++ii)
|
||||||
|
{
|
||||||
|
if (playeringame[ii] && players[ii].camera == players[playernum].mo)
|
||||||
|
{
|
||||||
|
players[ii].camera = players[ii].mo;
|
||||||
|
if (ii == consoleplayer && StatusBar != NULL)
|
||||||
|
{
|
||||||
|
StatusBar->AttachToPlayer(&players[ii]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// [RH] Make the player disappear
|
||||||
|
FBehavior::StaticStopMyScripts(players[playernum].mo);
|
||||||
|
if (players[playernum].mo != NULL)
|
||||||
|
{
|
||||||
|
P_DisconnectEffect(players[playernum].mo);
|
||||||
|
players[playernum].mo->player = NULL;
|
||||||
|
players[playernum].mo->Destroy();
|
||||||
|
if (!(players[playernum].mo->ObjectFlags & OF_EuthanizeMe))
|
||||||
|
{ // We just destroyed a morphed player, so now the original player
|
||||||
|
// has taken their place. Destroy that one too.
|
||||||
|
players[playernum].mo->Destroy();
|
||||||
|
}
|
||||||
|
players[playernum].mo = NULL;
|
||||||
|
players[playernum].camera = NULL;
|
||||||
|
}
|
||||||
|
// [RH] Let the scripts know the player left
|
||||||
|
FBehavior::StaticStartTypedScripts(SCRIPT_Disconnect, NULL, true, playernum);
|
||||||
|
}
|
||||||
|
|
||||||
void G_ScreenShot (char *filename)
|
void G_ScreenShot (char *filename)
|
||||||
{
|
{
|
||||||
shotfile = filename;
|
shotfile = filename;
|
||||||
|
|
|
@ -81,6 +81,7 @@ enum EFinishLevelType
|
||||||
void G_PlayerFinishLevel (int player, EFinishLevelType mode, int flags);
|
void G_PlayerFinishLevel (int player, EFinishLevelType mode, int flags);
|
||||||
|
|
||||||
void G_DoReborn (int playernum, bool freshbot);
|
void G_DoReborn (int playernum, bool freshbot);
|
||||||
|
void G_DoPlayerPop(int playernum);
|
||||||
|
|
||||||
// Adds pitch to consoleplayer's viewpitch and clamps it
|
// Adds pitch to consoleplayer's viewpitch and clamps it
|
||||||
void G_AddViewPitch (int look);
|
void G_AddViewPitch (int look);
|
||||||
|
|
Loading…
Reference in a new issue