void SV_Physics_Toss (prvm_edict_t *ent);
+int SV_GetPitchSign(prvm_edict_t *ent)
+{
+ dp_model_t *model;
+ int modelindex;
+ if (
+ ((modelindex = (int)ent->fields.server->modelindex) >= 1 && modelindex < MAX_MODELS && (model = sv.models[modelindex]))
+ ?
+ model->type == mod_alias
+ :
+ (
+ (((unsigned char)PRVM_EDICTFIELDVALUE(ent, prog->fieldoffsets.pflags)->_float) & PFLAGS_FULLDYNAMIC)
+ ||
+ ((gamemode == GAME_TENEBRAE) && ((unsigned int)ent->fields.server->effects & (16 | 32)))
+ )
+ )
+ return -1;
+ return 1;
+}
+
/*
===============================================================================
// if the modelindex is 0, it shouldn't be SOLID_BSP!
if (modelindex > 0 && modelindex < MAX_MODELS)
model = sv.models[(int)touch->fields.server->modelindex];
- //pitchsign = 1;
- if (
- ((modelindex = (int)touch->fields.server->modelindex) >= 1 && modelindex < MAX_MODELS && (model = sv.models[(int)touch->fields.server->modelindex]))
- ?
- model->type == mod_alias
- :
- (
- (((unsigned char)PRVM_EDICTFIELDVALUE(touch, prog->fieldoffsets.pflags)->_float) & PFLAGS_FULLDYNAMIC)
- ||
- ((gamemode == GAME_TENEBRAE) && ((unsigned int)touch->fields.server->effects & (16 | 32)))
- )
- )
- pitchsign = -1;
+ pitchsign = SV_GetPitchSign(touch);
}
if (model)
Matrix4x4_CreateFromQuakeEntity(&matrix, touch->fields.server->origin[0], touch->fields.server->origin[1], touch->fields.server->origin[2], pitchsign * touch->fields.server->angles[0], touch->fields.server->angles[1], touch->fields.server->angles[2], 1);
// if the modelindex is 0, it shouldn't be SOLID_BSP!
if (modelindex > 0 && modelindex < MAX_MODELS)
model = sv.models[(int)touch->fields.server->modelindex];
- //pitchsign = 1;
- if (
- ((modelindex = (int)touch->fields.server->modelindex) >= 1 && modelindex < MAX_MODELS && (model = sv.models[(int)touch->fields.server->modelindex]))
- ?
- model->type == mod_alias
- :
- (
- (((unsigned char)PRVM_EDICTFIELDVALUE(touch, prog->fieldoffsets.pflags)->_float) & PFLAGS_FULLDYNAMIC)
- ||
- ((gamemode == GAME_TENEBRAE) && ((unsigned int)touch->fields.server->effects & (16 | 32)))
- )
- )
- pitchsign = -1;
+ pitchsign = SV_GetPitchSign(touch);
}
if (model)
Matrix4x4_CreateFromQuakeEntity(&matrix, touch->fields.server->origin[0], touch->fields.server->origin[1], touch->fields.server->origin[2], pitchsign * touch->fields.server->angles[0], touch->fields.server->angles[1], touch->fields.server->angles[2], 1);
if (modelindex > 0 && modelindex < MAX_MODELS)
model = sv.models[(int)touch->fields.server->modelindex];
//pitchsign = 1;
- if (
- ((modelindex = (int)touch->fields.server->modelindex) >= 1 && modelindex < MAX_MODELS && (model = sv.models[(int)touch->fields.server->modelindex]))
- ?
- model->type == mod_alias
- :
- (
- (((unsigned char)PRVM_EDICTFIELDVALUE(touch, prog->fieldoffsets.pflags)->_float) & PFLAGS_FULLDYNAMIC)
- ||
- ((gamemode == GAME_TENEBRAE) && ((unsigned int)touch->fields.server->effects & (16 | 32)))
- )
- )
- pitchsign = -1;
+ pitchsign = SV_GetPitchSign(touch);
}
if (model)
Matrix4x4_CreateFromQuakeEntity(&matrix, touch->fields.server->origin[0], touch->fields.server->origin[1], touch->fields.server->origin[2], pitchsign * touch->fields.server->angles[0], touch->fields.server->angles[1], touch->fields.server->angles[2], 1);
for (e = 0;e < numcheckentities;e++)
{
prvm_edict_t *check = checkentities[e];
- if (check->fields.server->movetype == MOVETYPE_NONE
- || check->fields.server->movetype == MOVETYPE_PUSH
- || check->fields.server->movetype == MOVETYPE_FOLLOW
- || check->fields.server->movetype == MOVETYPE_NOCLIP
- || check->fields.server->movetype == MOVETYPE_FAKEPUSH)
+ int movetype = (int)check->fields.server->movetype;
+ switch(movetype)
+ {
+ case MOVETYPE_NONE:
+ case MOVETYPE_PUSH:
+ case MOVETYPE_FOLLOW:
+ case MOVETYPE_NOCLIP:
+ case MOVETYPE_FAKEPUSH:
continue;
+ default:
+ break;
+ }
if (check->fields.server->owner == pusherprog)
continue;
VectorCopy (check->fields.server->angles, check->priv.server->moved_fromangles);
moved_edicts[num_moved++] = PRVM_NUM_FOR_EDICT(check);
+ // physics objects need better collisions than this code can do
+ if (movetype == MOVETYPE_PHYSICS)
+ {
+ VectorAdd(check->fields.server->origin, move, check->fields.server->origin);
+ SV_LinkEdict(check);
+ SV_LinkEdict_TouchAreaGrid(check);
+ continue;
+ }
+
// try moving the contacted entity
pusher->fields.server->solid = SOLID_NOT;
if(!SV_PushEntity (&trace, check, move, true, true))
movetime *= 1 - min(1, trace.fraction);
if (ent->fields.server->movetype == MOVETYPE_BOUNCEMISSILE)
{
- ClipVelocity (ent->fields.server->velocity, trace.plane.normal, ent->fields.server->velocity, 2.0);
+ prvm_eval_t *val;
+ float bouncefactor = 1.0f;
+ val = PRVM_EDICTFIELDVALUE(ent, prog->fieldoffsets.bouncefactor);
+ if (val!=0 && val->_float)
+ bouncefactor = val->_float;
+
+ ClipVelocity (ent->fields.server->velocity, trace.plane.normal, ent->fields.server->velocity, 1 + bouncefactor);
ent->fields.server->flags = (int)ent->fields.server->flags & ~FL_ONGROUND;
}
else if (ent->fields.server->movetype == MOVETYPE_BOUNCE)
if (SV_RunThink (ent))
SV_Physics_Toss (ent);
break;
+ case MOVETYPE_PHYSICS:
+ if (SV_RunThink(ent))
+ {
+ SV_LinkEdict(ent);
+ SV_LinkEdict_TouchAreaGrid(ent);
+ }
+ break;
default:
Con_Printf ("SV_Physics: bad movetype %i\n", (int)ent->fields.server->movetype);
break;
SV_RunThink (ent);
SV_WalkMove (ent);
break;
+ case MOVETYPE_PHYSICS:
+ SV_RunThink (ent);
+ break;
default:
Con_Printf ("SV_Physics_ClientEntity: bad movetype %i\n", (int)ent->fields.server->movetype);
break;
prog->globals.server->frametime = sv.frametime;
PRVM_ExecuteProgram (prog->globals.server->StartFrame, "QC function StartFrame is missing");
+ // run physics engine
+ World_Physics_Frame(&sv.world, sv.frametime, sv_gravity.value);
+
//
// treat each object in turn
//