From 34505bcacfb06be0b5b430b835099522db22d9cf Mon Sep 17 00:00:00 2001 From: Marco Hladik Date: Sat, 28 Aug 2021 21:25:38 +0200 Subject: [PATCH] GS-EntBase: Fix crash with vehicles by networking them separately from CBaseEntity, which will assign the needed client-side input method for prediction --- src/client/entry.qc | 3 + src/gs-entbase/shared/basevehicle.h | 3 + src/gs-entbase/shared/basevehicle.qc | 118 ++++++++++++++++++++++++++- src/shared/entities.h | 3 +- 4 files changed, 124 insertions(+), 3 deletions(-) diff --git a/src/client/entry.qc b/src/client/entry.qc index 30dc182e..5b3384b9 100644 --- a/src/client/entry.qc +++ b/src/client/entry.qc @@ -941,6 +941,9 @@ CSQC_Ent_Update(float new) } me.ReceiveEntity(readfloat()); break; + case ENT_VEHICLE: + basevehicle_readentity(new); + break; case ENT_PLAYER: player pl = (player)self; diff --git a/src/gs-entbase/shared/basevehicle.h b/src/gs-entbase/shared/basevehicle.h index 30a96a96..4deeb779 100644 --- a/src/gs-entbase/shared/basevehicle.h +++ b/src/gs-entbase/shared/basevehicle.h @@ -19,6 +19,9 @@ class CBaseVehicle:CBaseTrigger #ifdef CLIENT virtual void(void) PredictPreFrame; virtual void(void) PredictPostFrame; + virtual void(float, float) ReadEntity; +#else + virtual float(entity, float) SendEntity; #endif virtual void(void) PlayerUpdateFlags; diff --git a/src/gs-entbase/shared/basevehicle.qc b/src/gs-entbase/shared/basevehicle.qc index 5ed94e95..446eb454 100644 --- a/src/gs-entbase/shared/basevehicle.qc +++ b/src/gs-entbase/shared/basevehicle.qc @@ -20,6 +20,7 @@ enumflags VHF_NOATTACK }; +#ifdef CLIENT void CBaseVehicle::PredictPreFrame(void) { @@ -36,6 +37,106 @@ CBaseVehicle::PredictPostFrame(void) ROLL_BACK(velocity); } +void +CBaseVehicle::ReadEntity(float fChanged, float new) +{ + m_eDriver = findfloat(world, ::entnum, readentitynum()); + + if (fChanged & BASEFL_CHANGED_ORIGIN) { + origin[0] = readcoord(); + origin[1] = readcoord(); + origin[2] = readcoord(); + } + + if (fChanged & BASEFL_CHANGED_ANGLES) { + angles[0] = readshort() / (32767 / 360); + angles[1] = readshort() / (32767 / 360); + angles[2] = readshort() / (32767 / 360); + } + + if (fChanged & BASEFL_CHANGED_MODELINDEX) { + setmodelindex(this, readshort()); + } + + if (fChanged & BASEFL_CHANGED_SOLID) { + solid = readbyte(); + } + + if (fChanged & BASEFL_CHANGED_MOVETYPE) { + movetype = readbyte(); + } + + if (fChanged & BASEFL_CHANGED_SIZE) { + mins[0] = readcoord(); + mins[1] = readcoord(); + mins[2] = readcoord(); + maxs[0] = readcoord(); + maxs[1] = readcoord(); + maxs[2] = readcoord(); + } + + if (fChanged & BASEFL_CHANGED_VELOCITY) { + velocity[0] = readfloat(); + velocity[1] = readfloat(); + velocity[2] = readfloat(); + } + + if (new) + drawmask = MASK_ENGINE; +} +#else +float +CBaseVehicle::SendEntity(entity ePEnt, float fChanged) +{ + WriteByte(MSG_ENTITY, ENT_VEHICLE); + WriteFloat(MSG_ENTITY, fChanged); + + WriteEntity(MSG_ENTITY, m_eDriver); + + /* really trying to get our moneys worth with 23 bits of mantissa */ + if (fChanged & BASEFL_CHANGED_ORIGIN) { + WriteCoord(MSG_ENTITY, origin[0]); + WriteCoord(MSG_ENTITY, origin[1]); + WriteCoord(MSG_ENTITY, origin[2]); + } + + if (fChanged & BASEFL_CHANGED_ANGLES) { + WriteShort(MSG_ENTITY, angles[0] * 32767 / 360); + WriteShort(MSG_ENTITY, angles[1] * 32767 / 360); + WriteShort(MSG_ENTITY, angles[2] * 32767 / 360); + } + + if (fChanged & BASEFL_CHANGED_MODELINDEX) { + WriteShort(MSG_ENTITY, modelindex); + } + + if (fChanged & BASEFL_CHANGED_SOLID) { + WriteByte(MSG_ENTITY, solid); + } + + if (fChanged & BASEFL_CHANGED_MOVETYPE) { + WriteByte(MSG_ENTITY, movetype); + } + + if (fChanged & BASEFL_CHANGED_SIZE) { + WriteCoord(MSG_ENTITY, mins[0]); + WriteCoord(MSG_ENTITY, mins[1]); + WriteCoord(MSG_ENTITY, mins[2]); + WriteCoord(MSG_ENTITY, maxs[0]); + WriteCoord(MSG_ENTITY, maxs[1]); + WriteCoord(MSG_ENTITY, maxs[2]); + } + + if (fChanged & BASEFL_CHANGED_VELOCITY) { + WriteFloat(MSG_ENTITY, velocity[0]); + WriteFloat(MSG_ENTITY, velocity[1]); + WriteFloat(MSG_ENTITY, velocity[2]); + } + + return (1); +} +#endif + void CBaseVehicle::PlayerInput(void) { @@ -83,14 +184,14 @@ CBaseVehicle::PlayerEnter(base_player pl) pl.movetype = MOVETYPE_NOCLIP; m_eDriver = (entity)pl; pl.vehicle = this; - pl.flags |= FL_INVEHICLE; + //pl.flags |= FL_INVEHICLE; } void CBaseVehicle::PlayerLeave(base_player pl) { pl.movetype = MOVETYPE_WALK; - pl.flags &= ~FL_INVEHICLE; + //pl.flags &= ~FL_INVEHICLE; if (m_iVehicleFlags & VHF_FROZEN) pl.flags &= ~FL_FROZEN; @@ -107,3 +208,16 @@ CBaseVehicle::CBaseVehicle(void) { CBaseEntity::CBaseEntity(); } +#ifdef CLIENT +void +basevehicle_readentity(float isnew) +{ + CBaseVehicle veh = (CBaseVehicle)self; + float flags = readfloat(); + + if (isnew) + spawnfunc_CBaseVehicle(); + + veh.ReadEntity(flags, isnew); +} +#endif diff --git a/src/shared/entities.h b/src/shared/entities.h index 8df584ad..7a43ec1d 100644 --- a/src/shared/entities.h +++ b/src/shared/entities.h @@ -31,7 +31,8 @@ enum ENT_DECAL, ENT_OLDCAMERA, ENT_MONITOR, - ENT_SEPARATOR + ENT_VEHICLE, + ENT_SEPARATOR, }; /* entity update flags */