diff --git a/src/d_clisrv.c b/src/d_clisrv.c index 5b43c2213..c73ee04ec 100644 --- a/src/d_clisrv.c +++ b/src/d_clisrv.c @@ -1555,6 +1555,8 @@ static boolean SV_SendServerConfig(INT32 node) netbuffer->u.servercfg.playerskins[i] = (UINT8)players[i].skin; netbuffer->u.servercfg.playercolor[i] = (UINT8)players[i].skincolor; + + netbuffer->u.servercfg.playerisbot[i] = players[i].bot; } memcpy(netbuffer->u.servercfg.server_context, server_context, 8); @@ -4289,6 +4291,7 @@ static void HandlePacketFromAwayNode(SINT8 node) playeringame[j] = true; SetPlayerSkinByNum(j, (INT32)netbuffer->u.servercfg.playerskins[j]); players[j].skincolor = netbuffer->u.servercfg.playercolor[j]; + players[j].bot = netbuffer->u.servercfg.playerisbot[j]; } scp = netbuffer->u.servercfg.varlengthinputs; diff --git a/src/d_clisrv.h b/src/d_clisrv.h index 49945de7c..d39babd82 100644 --- a/src/d_clisrv.h +++ b/src/d_clisrv.h @@ -323,6 +323,8 @@ typedef struct UINT8 playerskins[MAXPLAYERS]; UINT8 playercolor[MAXPLAYERS]; + UINT8 playerisbot[MAXPLAYERS]; + UINT8 gametype; UINT8 modifiedgame; SINT8 adminplayers[MAXPLAYERS]; // Needs to be signed diff --git a/src/k_bot.c b/src/k_bot.c index b95346d04..1e0edf71c 100644 --- a/src/k_bot.c +++ b/src/k_bot.c @@ -472,7 +472,7 @@ void K_BuildBotTiccmd(player_t *player, ticcmd_t *cmd) } cmd->driftturn = turnamt; - cmd->angleturn += turnamt; + cmd->angleturn = (player->mo->angle >> 16) + turnamt; } (void)ontrack; diff --git a/src/k_waypoint.c b/src/k_waypoint.c index 91cb9a1b1..611dec079 100644 --- a/src/k_waypoint.c +++ b/src/k_waypoint.c @@ -348,6 +348,16 @@ size_t K_GetWaypointHeapIndex(waypoint_t *waypoint) return waypointindex; } +/*-------------------------------------------------- + size_t K_GetNumWaypoints(void) + + See header file for description. +--------------------------------------------------*/ +size_t K_GetNumWaypoints(void) +{ + return numwaypoints; +} + /*-------------------------------------------------- waypoint_t *K_GetWaypointFromIndex(size_t waypointindex) @@ -1508,7 +1518,6 @@ static waypoint_t *K_MakeWaypoint(mobj_t *const mobj) I_Assert(waypointcap != NULL); // No waypoint mobjs in map load I_Assert(numwaypoints < numwaypointmobjs); // waypoint array reached max capacity - // numwaypoints is incremented later in K_SetupWaypoint madewaypoint = &waypointheap[numwaypoints]; numwaypoints++; diff --git a/src/k_waypoint.h b/src/k_waypoint.h index fb8d37f20..f1a678603 100644 --- a/src/k_waypoint.h +++ b/src/k_waypoint.h @@ -287,6 +287,16 @@ waypoint_t *K_SearchWaypointHeapForMobj(mobj_t * const mobj); --------------------------------------------------*/ size_t K_GetWaypointHeapIndex(waypoint_t *waypoint); +/*-------------------------------------------------- + size_t K_GetNumWaypoints(void) + + Returns the number of waypoints that are in the heap. + Intended for Net Archiving/Unarchiving + + Return:- + The number of waypoints in the heap +--------------------------------------------------*/ +size_t K_GetNumWaypoints(void); /*-------------------------------------------------- waypoint_t *K_GetWaypointFromIndex(size_t waypointindex) diff --git a/src/p_saveg.c b/src/p_saveg.c index 8546d3029..0220a09e8 100644 --- a/src/p_saveg.c +++ b/src/p_saveg.c @@ -49,6 +49,7 @@ UINT8 *save_p; #define ARCHIVEBLOCK_POBJS 0x7F928546 #define ARCHIVEBLOCK_THINKERS 0x7F37037C #define ARCHIVEBLOCK_SPECIALS 0x7F228378 +#define ARCHIVEBLOCK_WAYPOINTS 0x7F46498F // Note: This cannot be bigger // than an UINT16 @@ -1892,6 +1893,49 @@ static void P_NetArchiveThinkers(void) WRITEUINT8(save_p, tc_end); } +static void P_NetArchiveWaypoints(void) +{ + waypoint_t *waypoint; + size_t i; + size_t numWaypoints = K_GetNumWaypoints(); + + WRITEUINT32(save_p, ARCHIVEBLOCK_WAYPOINTS); + WRITEUINT32(save_p, numWaypoints); + + for (i = 0U; i < numWaypoints; i++) { + waypoint = K_GetWaypointFromIndex(i); + + // The only thing we save for each waypoint is the mobj. + // Waypoints should NEVER be completely created or destroyed mid-race as a result of this + WRITEUINT32(save_p, waypoint->mobj->mobjnum); + } +} + +static void P_NetUnArchiveWaypoints(void) +{ + if (READUINT32(save_p) != ARCHIVEBLOCK_WAYPOINTS) + I_Error("Bad $$$.sav at archive block Waypoints!"); + else { + UINT32 numArchiveWaypoints = READUINT32(save_p); + size_t numSpawnedWaypoints = K_GetNumWaypoints(); + + if (numArchiveWaypoints != numSpawnedWaypoints) { + I_Error("Bad $$$.sav: More saved waypoints than created!"); + } else { + waypoint_t *waypoint; + UINT32 i; + UINT32 temp; + for (i = 0U; i < numArchiveWaypoints; i++) { + waypoint = K_GetWaypointFromIndex(i); + temp = READUINT32(save_p); + if (!P_SetTarget(&waypoint->mobj, P_FindNewPosition(temp))) { + CONS_Debug(DBG_GAMELOGIC, "waypoint mobj not found for %d\n", i); + } + } + } + } +} + // Now save the pointers, tracer and target, but at load time we must // relink to this; the savegame contains the old position in the pointer // field copyed in the info field temporarily, but finally we just search @@ -3510,6 +3554,7 @@ void P_SaveNetGame(void) #endif P_NetArchiveThinkers(); P_NetArchiveSpecials(); + P_NetArchiveWaypoints(); } #ifdef HAVE_BLUA LUA_Archive(); @@ -3554,6 +3599,7 @@ boolean P_LoadNetGame(void) #endif P_NetUnArchiveThinkers(); P_NetUnArchiveSpecials(); + P_NetUnArchiveWaypoints(); P_RelinkPointers(); P_FinishMobjs(); }