"DP_SND_STEREOWAV "
"DP_SOLIDCORPSE "
"DP_SPRITE32 "
+"DP_SV_BOTCLIENT "
"DP_SV_CLIENTCOLORS "
"DP_SV_CLIENTNAME "
"DP_SV_DRAWONLYTOCLIENT "
host_client = oldhostclient;
}
+//entity() spawnclient (DP_SV_BOTCLIENT)
+void PF_spawnclient (void)
+{
+ int i;
+ edict_t *ed;
+ pr_xfunction->builtinsprofile += 2;
+ ed = sv.edicts;
+ for (i = 0;i < svs.maxclients;i++)
+ {
+ if (!svs.clients[i].active)
+ {
+ pr_xfunction->builtinsprofile += 100;
+ SV_ConnectClient (i, NULL);
+ ed = EDICT_NUM(i + 1);
+ break;
+ }
+ }
+ RETURN_EDICT(ed);
+}
+
+//float(entity clent) clienttype (DP_SV_BOTCLIENT)
+void PF_clienttype (void)
+{
+ int clientnum;
+ clientnum = G_EDICTNUM(OFS_PARM0) - 1;
+ if (clientnum < 0 || clientnum >= svs.maxclients)
+ G_FLOAT(OFS_RETURN) = 3;
+ else if (!svs.clients[clientnum].active)
+ G_FLOAT(OFS_RETURN) = 0;
+ else if (svs.clients[clientnum].netconnection)
+ G_FLOAT(OFS_RETURN) = 1;
+ else
+ G_FLOAT(OFS_RETURN) = 2;
+}
builtin_t pr_builtin[] =
{
PF_gettagindex, // #451 float(entity ent, string tagname) gettagindex (DP_QC_GETTAGINFO)
PF_gettaginfo, // #452 vector(entity ent, float tagindex) gettaginfo (DP_QC_GETTAGINFO)
PF_dropclient, // #453 void(entity clent) dropclient (DP_SV_DROPCLIENT)
-NULL, // #454
-NULL, // #455
+PF_spawnclient, // #454 entity() spawnclient (DP_SV_BOTCLIENT)
+PF_clienttype, // #455 float(entity clent) clienttype (DP_SV_BOTCLIENT)
NULL, // #456
NULL, // #457
NULL, // #458
// edicts get reallocated on level changes, so we need to update it here
client->edict = EDICT_NUM((client - svs.clients) + 1);
+ // if client is a botclient coming from a level change, we need to set up
+ // client info that normally requires networking
+ if (!client->netconnection)
+ {
+ int i;
+
+ // set up the edict
+ ED_ClearEdict(client->edict);
+
+ // copy spawn parms out of the client_t
+ for (i=0 ; i< NUM_SPAWN_PARMS ; i++)
+ (&pr_global_struct->parm1)[i] = host_client->spawn_parms[i];
+
+ // call the spawn function
+ pr_global_struct->time = sv.time;
+ pr_global_struct->self = EDICT_TO_PROG(sv_player);
+ PR_ExecuteProgram (pr_global_struct->ClientConnect, "QC function ClientConnect is missing");
+ PR_ExecuteProgram (pr_global_struct->PutClientInServer, "QC function PutClientInServer is missing");
+ host_client->spawned = true;
+ return;
+ }
// LordHavoc: clear entityframe tracking
client->spawn_parms[i] = (&pr_global_struct->parm1)[i];
}
- SV_SendServerinfo (client);
+ // don't call SendServerinfo for a fresh botclient because its fields have
+ // not been set up by the qc yet
+ if (client->netconnection)
+ SV_SendServerinfo (client);
}
SV_CreateBaseline ();
// send serverinfo to all connected clients
+ // (note this also handles botclients coming back from a level change)
for (i = 0, host_client = svs.clients;i < svs.maxclients;i++, host_client++)
if (host_client->active)
SV_SendServerinfo(host_client);