Xonotic
physics.qc File Reference
#include "physics.qh"
#include "input.qh"
+ Include dependency graph for physics.qc:
+ This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Functions

void sys_phys_postupdate (entity this)
 
void sys_phys_simulate (entity this, float dt)
 for players More...
 
void sys_phys_simulate_simple (entity this, float dt)
 for other entities More...
 
void sys_phys_update (entity this, float dt)
 
void sys_phys_update_single (entity this)
 

Variables

int disableclientprediction
 
entity groundentity
 

Function Documentation

◆ sys_phys_postupdate()

void sys_phys_postupdate ( entity  this)

Definition at line 163 of file physics.qc.

References classname, conveyor, flags, IS_ONGROUND, lastclassname, lastflags, lastground, time, and velocity.

Referenced by sys_phys_update().

164 {
165  if (IS_ONGROUND(this)) { this.lastground = time; }
166 // conveyors: then break velocity again
167  if (this.conveyor.active) { this.velocity += this.conveyor.movedir; }
168  this.lastflags = this.flags;
169 
170  this.lastclassname = this.classname;
171 }
string lastclassname
Definition: player.qh:67
#define IS_ONGROUND(s)
Definition: movetypes.qh:16
float lastground
Definition: player.qh:61
string classname
Definition: csprogsdefs.qc:107
entity conveyor
Definition: player.qh:54
float flags
Definition: csprogsdefs.qc:129
float lastflags
Definition: player.qh:60
float time
Definition: csprogsdefs.qc:16
vector velocity
Definition: csprogsdefs.qc:103
+ Here is the caller graph for this function:

◆ sys_phys_simulate()

void sys_phys_simulate ( entity  this,
float  dt 
)

for players

Definition at line 174 of file physics.qc.

References com_in_jump, com_phys_acc_rate, com_phys_acc_rate_air, com_phys_acc_rate_air_stop, com_phys_acc_rate_air_strafe, com_phys_air, com_phys_friction, com_phys_friction_air, com_phys_gravity, com_phys_ground, com_phys_ladder, com_phys_vel_2d, com_phys_vel_max, com_phys_vel_max_air, com_phys_vel_max_air_strafe, com_phys_water, CONTENT_EMPTY, CPM_PM_Aircontrol(), eZ, f2, fabs(), FL_WATERJUMP, flags, GeomLerp(), IS_DUCKED, IS_ONSLICK, IsMoveInDirection(), ladder_entity, max(), min(), MOVE_NOMONSTERS, movement, normalize(), origin, PHYS_ACCELERATE, PHYS_AIRACCEL_QW, PHYS_AIRACCEL_QW_STRETCHFACTOR, PHYS_AIRACCEL_SIDEWAYS_FRICTION, PHYS_AIRCONTROL, PHYS_AIRSPEEDLIMIT_NONQW, PHYS_AIRSTOPACCELERATE, PHYS_AIRSTRAFEACCEL_QW, PHYS_AIRSTRAFEACCELERATE, PHYS_FRICTION, PHYS_FRICTION_SLICK, PHYS_FROZEN, PHYS_INPUT_BUTTON_CROUCH, PHYS_MAXAIRSTRAFESPEED, PHYS_MAXSPEED, PHYS_STOPSPEED, PHYS_WARSOWBUNNY_TURNACCEL, PM_Accelerate(), PM_AirAccelerate(), SET_JUMP_HELD, sqrt(), trace_startsolid, UNSET_ONGROUND, v_angle, vec2, vector(), velocity, viewloc, vlen(), vlen2, vmul, waterlevel, WATERLEVEL_NONE, WATERLEVEL_SUBMERGED, WATERLEVEL_SWIMMING, WATERLEVEL_WETFEET, and watertype.

Referenced by sys_phys_update().

175 {
176  if (!this.com_phys_ground && !this.com_phys_air) {
177  // noclipping
178  // flying
179  // on a spawnfunc_func_ladder
180  // swimming in spawnfunc_func_water
181  // swimming
182  UNSET_ONGROUND(this);
183 
184  if (this.com_phys_friction_air) {
185  const float grav = -this.com_phys_gravity;
186  this.velocity_z += grav / 2;
187  this.velocity = this.velocity * (1 - dt * this.com_phys_friction);
188  this.velocity_z += grav / 2;
189  }
190  }
191 
192  if (this.com_phys_water) {
193  // water jump only in certain situations
194  // this mimics quakeworld code
195  if (this.com_in_jump && this.waterlevel == WATERLEVEL_SWIMMING && this.velocity_z >= -180 && !this.viewloc && !PHYS_FROZEN(this)) {
196  vector yawangles = '0 1 0' * this.v_angle.y;
197  vector forward, right, up;
198  MAKE_VECTORS(yawangles, forward, right, up);
199  vector spot = this.origin + 24 * forward;
200  spot_z += 8;
201  traceline(spot, spot, MOVE_NOMONSTERS, this);
202  if (trace_startsolid) {
203  spot_z += 24;
204  traceline(spot, spot, MOVE_NOMONSTERS, this);
205  if (!trace_startsolid) {
206  this.velocity = forward * 50;
207  this.velocity_z = 310;
208  UNSET_ONGROUND(this);
209  SET_JUMP_HELD(this);
210  }
211  }
212  }
213  }
214 
215  vector forward, right, up;
216  MAKE_VECTORS(vmul(this.v_angle, (this.com_phys_vel_2d ? '0 1 0' : '1 1 1')), forward, right, up);
217  // wishvel = forward * PHYS_CS(this).movement.x + right * PHYS_CS(this).movement.y + up * PHYS_CS(this).movement.z;
218  vector wishvel = forward * PHYS_CS(this).movement.x
219  + right * PHYS_CS(this).movement.y
220  + '0 0 1' * PHYS_CS(this).movement.z * (this.com_phys_vel_2d ? 0 : 1);
221  if (this.com_phys_water) {
222  if (PHYS_FROZEN(this))
223  {
224  if(this.waterlevel >= WATERLEVEL_SUBMERGED && this.velocity.z >= -70) // don't change the speed too abruptally
225  wishvel = '0 0 160'; // resurface
226  else if(this.waterlevel >= WATERLEVEL_SWIMMING && this.velocity.z > 0)
227  wishvel = eZ * 1.3 * min(this.velocity.z, 160); // resurface a bit more above the surface
228  }
229  else
230  {
231  if (PHYS_INPUT_BUTTON_CROUCH(this)) {
232  wishvel.z = -PHYS_MAXSPEED(this);
233  }
234  if (this.viewloc) {
235  wishvel.z = -160; // drift anyway
236  } else if (wishvel == '0 0 0') {
237  wishvel = '0 0 -60'; // drift towards bottom
238  }
239  }
240  }
241  if (this.com_phys_ladder) {
242  if (this.viewloc) {
243  wishvel.z = PHYS_CS(this).movement_old.x;
244  }
245  if (this.ladder_entity.classname == "func_water") {
246  float f = vlen(wishvel);
247  if (f > this.ladder_entity.speed) {
248  wishvel *= (this.ladder_entity.speed / f);
249  }
250 
251  this.watertype = this.ladder_entity.skin;
252  f = this.ladder_entity.origin_z + this.ladder_entity.maxs_z;
253  if ((this.origin_z + this.view_ofs_z) < f) {
255  } else if ((this.origin_z + (this.mins_z + this.maxs_z) * 0.5) < f) {
257  } else if ((this.origin_z + this.mins_z + 1) < f) {
259  } else {
261  this.watertype = CONTENT_EMPTY;
262  }
263  }
264  }
265  // acceleration
266  const vector wishdir = normalize(wishvel);
267  float wishspeed = min(vlen(wishvel), this.com_phys_vel_max);
268 
269  if (this.com_phys_air) {
270  if (!(this.flags & FL_WATERJUMP)) {
271  // apply air speed limit
272  float airaccelqw = PHYS_AIRACCEL_QW(this);
273  float wishspeed0 = wishspeed;
274  const float maxairspd = this.com_phys_vel_max;
275  wishspeed = min(wishspeed, maxairspd);
276  if (IS_DUCKED(this)) {
277  wishspeed *= 0.5;
278  }
279  float airaccel = this.com_phys_acc_rate_air;
280 
281  float accelerating = (this.velocity * wishdir > 0);
282  float wishspeed2 = wishspeed;
283 
284  // CPM: air control
285  if (PHYS_AIRSTOPACCELERATE(this)) {
286  vector curdir = normalize(vec2(this.velocity));
287  airaccel += (this.com_phys_acc_rate_air_stop - airaccel) * max(0, -(curdir * wishdir));
288  }
289  // note that for straight forward jumping:
290  // step = accel * dt * wishspeed0;
291  // accel = bound(0, wishspeed - vel_xy_current, step) * accelqw + step * (1 - accelqw);
292  // -->
293  // dv/dt = accel * maxspeed (when slow)
294  // dv/dt = accel * maxspeed * (1 - accelqw) (when fast)
295  // log dv/dt = logaccel + logmaxspeed (when slow)
296  // log dv/dt = logaccel + logmaxspeed + log(1 - accelqw) (when fast)
297  float strafity = IsMoveInDirection(PHYS_CS(this).movement, -90) + IsMoveInDirection(PHYS_CS(this).movement, +90); // if one is nonzero, other is always zero
298  if (PHYS_MAXAIRSTRAFESPEED(this)) {
299  wishspeed =
300  min(wishspeed,
302  }
303  if (PHYS_AIRSTRAFEACCELERATE(this)) {
304  airaccel = GeomLerp(airaccel, strafity, this.com_phys_acc_rate_air_strafe);
305  }
306  if (PHYS_AIRSTRAFEACCEL_QW(this)) {
307  airaccelqw =
308  (((strafity > 0.5 ? PHYS_AIRSTRAFEACCEL_QW(this) : PHYS_AIRACCEL_QW(this)) >= 0) ? +1 : -1)
309  *
310  (1 - GeomLerp(1 - fabs(PHYS_AIRACCEL_QW(this)), strafity, 1 - fabs(PHYS_AIRSTRAFEACCEL_QW(this))));
311  }
312  // !CPM
313 
314  if (PHYS_WARSOWBUNNY_TURNACCEL(this) && accelerating && PHYS_CS(this).movement.y == 0 && PHYS_CS(this).movement.x != 0) {
315  PM_AirAccelerate(this, dt, wishdir, wishspeed2);
316  } else {
317  float sidefric = maxairspd ? (PHYS_AIRACCEL_SIDEWAYS_FRICTION(this) / maxairspd) : 0;
318  PM_Accelerate(this, dt, wishdir, wishspeed, wishspeed0, airaccel, airaccelqw,
320  }
321 
322  if (PHYS_AIRCONTROL(this)) {
323  CPM_PM_Aircontrol(this, dt, wishdir, wishspeed2);
324  }
325  }
326  } else {
327  if (this.com_phys_ground && IS_DUCKED(this)) { wishspeed *= 0.5; }
328  if (this.com_phys_water) {
329  wishspeed *= 0.7;
330 
331  // if (!(this.flags & FL_WATERJUMP)) // TODO: use
332  {
333  // water friction
334  float f = 1 - dt * PHYS_FRICTION(this);
335  f = min(max(0, f), 1);
336  this.velocity *= f;
337 
338  f = wishspeed - this.velocity * wishdir;
339  if (f > 0) {
340  float accelspeed = min(PHYS_ACCELERATE(this) * dt * wishspeed, f);
341  this.velocity += accelspeed * wishdir;
342  }
343 
344  // holding jump button swims upward slowly
345  if (this.com_in_jump && !this.viewloc && !PHYS_FROZEN(this)) {
346  // was:
347  // lava: 50
348  // slime: 80
349  // water: 100
350  // idea: double those
351  this.velocity_z = 200;
352  if (this.waterlevel >= WATERLEVEL_SUBMERGED) {
353  this.velocity_z = PHYS_MAXSPEED(this) * 0.7;
354  }
355  }
356  }
357  if (this.viewloc) {
358  const float addspeed = wishspeed - this.velocity * wishdir;
359  if (addspeed > 0) {
360  const float accelspeed = min(PHYS_ACCELERATE(this) * dt * wishspeed, addspeed);
361  this.velocity += accelspeed * wishdir;
362  }
363  } else {
364  // water acceleration
365  PM_Accelerate(this, dt, wishdir, wishspeed, wishspeed, this.com_phys_acc_rate, 1, 0, 0, 0);
366  }
367  return;
368  }
369  if (this.com_phys_ground) {
370  // apply edge friction
371  const float f2 = vlen2(vec2(this.velocity));
372  if (f2 > 0) {
373  // TODO: apply edge friction
374  // apply ground friction
375  const int realfriction = (IS_ONSLICK(this))
376  ? PHYS_FRICTION_SLICK(this)
377  : PHYS_FRICTION(this);
378 
379  float f = sqrt(f2);
380  f = 1 - dt * realfriction
381  * ((f < PHYS_STOPSPEED(this)) ? (PHYS_STOPSPEED(this) / f) : 1);
382  f = max(0, f);
383  this.velocity *= f;
384  /*
385  Mathematical analysis time!
386 
387  Our goal is to invert this mess.
388 
389  For the two cases we get:
390  v = v0 * (1 - dt * (PHYS_STOPSPEED(this) / v0) * PHYS_FRICTION(this))
391  = v0 - dt * PHYS_STOPSPEED(this) * PHYS_FRICTION(this)
392  v0 = v + dt * PHYS_STOPSPEED(this) * PHYS_FRICTION(this)
393  and
394  v = v0 * (1 - dt * PHYS_FRICTION(this))
395  v0 = v / (1 - dt * PHYS_FRICTION(this))
396 
397  These cases would be chosen ONLY if:
398  v0 < PHYS_STOPSPEED(this)
399  v + dt * PHYS_STOPSPEED(this) * PHYS_FRICTION(this) < PHYS_STOPSPEED(this)
400  v < PHYS_STOPSPEED(this) * (1 - dt * PHYS_FRICTION(this))
401  and, respectively:
402  v0 >= PHYS_STOPSPEED(this)
403  v / (1 - dt * PHYS_FRICTION(this)) >= PHYS_STOPSPEED(this)
404  v >= PHYS_STOPSPEED(this) * (1 - dt * PHYS_FRICTION(this))
405  */
406  }
407  const float addspeed = wishspeed - this.velocity * wishdir;
408  if (addspeed > 0) {
409  const float accelspeed = min(PHYS_ACCELERATE(this) * dt * wishspeed, addspeed);
410  this.velocity += accelspeed * wishdir;
411  }
412  return;
413  }
414 
415  if (!(this.flags & FL_WATERJUMP)) {
416  PM_Accelerate(this, dt, wishdir, wishspeed, wishspeed, this.com_phys_acc_rate, 1, 0, 0, 0);
417  }
418  }
419 }
#define PHYS_INPUT_BUTTON_CROUCH(s)
Definition: player.qh:150
#define PHYS_FRICTION_SLICK(s)
Definition: player.qh:112
void CPM_PM_Aircontrol(entity this, float dt, vector wishdir, float wishspeed)
Definition: player.qc:177
float watertype
Definition: progsdefs.qc:182
const int WATERLEVEL_SUBMERGED
Definition: movetypes.qh:14
#define PHYS_ACCELERATE(s)
Definition: player.qh:91
float waterlevel
Definition: progsdefs.qc:181
#define IS_DUCKED(s)
Definition: player.qh:206
#define PHYS_FRICTION(s)
Definition: player.qh:110
void PM_Accelerate(entity this, float dt, vector wishdir, float wishspeed, float wishspeed0, float accel, float accelqw, float stretchfactor, float sidefric, float speedlimit)
Definition: player.qc:223
bool com_phys_ladder
Definition: physics.qh:21
float com_phys_acc_rate_air_strafe
Definition: physics.qh:12
float com_phys_acc_rate_air
Definition: physics.qh:11
#define PHYS_AIRSTRAFEACCEL_QW(s)
Definition: player.qh:104
#define PHYS_STOPSPEED(s)
Definition: player.qh:134
vector v_angle
Definition: progsdefs.qc:161
#define PHYS_AIRACCEL_SIDEWAYS_FRICTION(s)
Definition: player.qh:95
bool com_phys_ground
Definition: physics.qh:19
origin
Definition: ent_cs.qc:114
float IsMoveInDirection(vector mv, float ang)
Definition: player.qc:106
float com_phys_acc_rate_air_stop
Definition: physics.qh:13
bool com_in_jump
Definition: input.qh:6
#define UNSET_ONGROUND(s)
Definition: movetypes.qh:18
float com_phys_vel_max_air
Definition: physics.qh:8
const int WATERLEVEL_NONE
Definition: movetypes.qh:11
void PM_AirAccelerate(entity this, float dt, vector wishdir, float wishspeed)
Definition: player.qc:287
#define vmul(a, b)
Definition: vector.qh:38
#define PHYS_FROZEN(s)
Definition: player.qh:114
float com_phys_vel_max_air_strafe
Definition: physics.qh:9
#define PHYS_AIRSTOPACCELERATE(s)
Definition: player.qh:102
const float CONTENT_EMPTY
Definition: csprogsdefs.qc:236
const float MOVE_NOMONSTERS
Definition: csprogsdefs.qc:253
spree_inf s1 s2 s3loc s2 spree_inf s1 s2 s3loc s2 spree_inf s1 s2 s3loc s2 s1 s2loc s1 s2loc s1 s2loc s1 s2loc s1 s2loc s1 s2loc s1 s2loc s1 s2 f1 f1points f2
Definition: all.inc:348
#define vlen2(v)
Definition: vector.qh:4
#define PHYS_WARSOWBUNNY_TURNACCEL(s)
Definition: player.qh:142
float GeomLerp(float a, float _lerp, float b)
Definition: player.qc:115
#define IS_ONSLICK(s)
Definition: movetypes.qh:19
float com_phys_friction
Definition: physics.qh:14
entity this
Definition: self.qh:83
const int WATERLEVEL_WETFEET
Definition: movetypes.qh:12
float com_phys_acc_rate
Definition: physics.qh:10
#define SET_JUMP_HELD(s)
Definition: player.qh:200
vector movement
#define PHYS_AIRACCEL_QW_STRETCHFACTOR(s)
Definition: player.qh:94
entity ladder_entity
Definition: ladder.qh:11
vector(float skel, float bonenum) _skel_get_boneabs_hidden
bool com_phys_air
Definition: physics.qh:20
float com_phys_vel_max
Definition: physics.qh:7
entity viewloc
Definition: viewloc.qh:13
float flags
Definition: csprogsdefs.qc:129
const vector eZ
Definition: vector.qh:46
#define PHYS_AIRACCEL_QW(s)
Definition: player.qh:93
#define PHYS_AIRCONTROL(s)
Definition: player.qh:96
bool com_phys_water
Definition: physics.qh:23
bool com_phys_vel_2d
Definition: physics.qh:22
const int WATERLEVEL_SWIMMING
Definition: movetypes.qh:13
float com_phys_gravity
Definition: physics.qh:16
#define PHYS_MAXAIRSTRAFESPEED(s)
Definition: player.qh:131
#define vec2(...)
Definition: vector.qh:90
#define PHYS_AIRSPEEDLIMIT_NONQW(s)
Definition: player.qh:101
float trace_startsolid
Definition: csprogsdefs.qc:35
#define PHYS_AIRSTRAFEACCELERATE(s)
Definition: player.qh:103
vector velocity
Definition: csprogsdefs.qc:103
#define PHYS_MAXSPEED(s)
Definition: player.qh:132
float FL_WATERJUMP
Definition: progsdefs.qc:242
bool com_phys_friction_air
Definition: physics.qh:24
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ sys_phys_simulate_simple()

void sys_phys_simulate_simple ( entity  this,
float  dt 
)

for other entities

Definition at line 423 of file physics.qc.

References absmax, absmin, angles, avelocity, boxesoverlap(), ClipVelocity, com_phys_gravity_factor, com_phys_pos, com_phys_vel, entity(), groundentity, if(), IS_ONGROUND, maxs, min(), mins, MOVE_NORMAL, NULL, setorigin(), solid, SOLID_NOT, SOLID_TRIGGER, string_null, trace_dphitcontents, trace_dphitq3surfaceflags, trace_dphittexturename, trace_dpstartcontents, trace_endpos, trace_ent, trace_fraction, trace_plane_dist, trace_plane_normal, trace_startsolid, vector(), vlen(), and void.

Referenced by sys_phys_update(), and sys_phys_update_single().

424 {
425  vector mn = this.mins;
426  vector mx = this.maxs;
427 
428  vector g = '0 0 0';
429  if (this.com_phys_gravity_factor && !g) g = '0 0 -1' * PHYS_GRAVITY(NULL);
430 
431  vector vel = this.com_phys_vel;
432  vector pos = this.com_phys_pos;
433 
434  // SV_Physics_Toss
435 
436  vel += g * dt;
437 
438  this.angles += dt * this.avelocity;
439  float movetime = dt;
440  for (int i = 0; i < MAX_CLIP_PLANES && movetime > 0; i++) {
441  vector push = vel * movetime;
442  vector p0 = pos;
443  vector p1 = p0 + push;
444  // SV_PushEntity
445  tracebox(p0, mn, mx, p1, MOVE_NORMAL, this);
446  if (!trace_startsolid) {
447  bool hit = trace_fraction < 1;
448  pos = trace_endpos;
449  entity ent = trace_ent;
450  // SV_LinkEdict_TouchAreaGrid
451  if (this.solid != SOLID_NOT) {
452  FOREACH_ENTITY_RADIUS_ORDERED(0.5 * (this.absmin + this.absmax), 0.5 * vlen(this.absmax - this.absmin), true, {
453  if (it.solid != SOLID_TRIGGER || it == this) continue;
454  if (gettouch(it) && boxesoverlap(it.absmin, it.absmax, this.absmin, this.absmax)) {
455  // SV_LinkEdict_TouchAreaGrid_Call
456  trace_allsolid = false;
457  trace_startsolid = false;
458  trace_fraction = 1;
459  trace_inwater = false;
460  trace_inopen = true;
461  trace_endpos = it.origin;
462  trace_plane_normal = '0 0 1';
463  trace_plane_dist = 0;
464  trace_ent = this;
465  trace_dpstartcontents = 0;
466  trace_dphitcontents = 0;
467  trace_dphitq3surfaceflags = 0;
468  trace_dphittexturename = string_null;
469  gettouch(it)(this, it);
470  vel = this.velocity;
471  }
472  });
473  }
474  if (hit && this.solid >= SOLID_TRIGGER && (!IS_ONGROUND(this) || this.groundentity != ent)) {
475  // SV_Impact (ent, trace);
476  tracebox(p0, mn, mx, p1, MOVE_NORMAL, this);
477  void(entity, entity) touched = gettouch(this);
478  if (touched && this.solid != SOLID_NOT) {
479  touched(ent, this);
480  }
481  void(entity, entity) touched2 = gettouch(ent);
482  if (this && ent && touched2 && ent.solid != SOLID_NOT) {
483  trace_endpos = ent.origin;
484  trace_plane_normal *= -1;
485  trace_plane_dist *= -1;
486  trace_ent = this;
491  touched2(this, ent);
492  }
493  }
494  }
495  // end SV_PushEntity
496  if (wasfreed(this)) { return; }
497  tracebox(p0, mn, mx, p1, MOVE_NORMAL, this);
498  if (trace_fraction == 1) { break; }
499  movetime *= 1 - min(1, trace_fraction);
500  ClipVelocity(vel, trace_plane_normal, vel, 1);
501  }
502 
503  this.com_phys_vel = vel;
504  this.com_phys_pos = pos;
505  setorigin(this, this.com_phys_pos);
506 }
const float SOLID_NOT
Definition: csprogsdefs.qc:244
string string_null
Definition: nil.qh:9
float trace_plane_dist
Definition: csprogsdefs.qc:39
float trace_dphitq3surfaceflags
float trace_dphitcontents
entity() spawn
const float MOVE_NORMAL
Definition: csprogsdefs.qc:252
#define IS_ONGROUND(s)
Definition: movetypes.qh:16
vector maxs
Definition: csprogsdefs.qc:113
vector com_phys_pos
Definition: physics.qh:4
float com_phys_gravity_factor
Definition: physics.qh:17
vector avelocity
Definition: csprogsdefs.qc:105
#define ClipVelocity(in, normal, out, overbounce)
Definition: vector.qh:156
entity trace_ent
Definition: csprogsdefs.qc:40
string trace_dphittexturename
vector absmax
Definition: csprogsdefs.qc:92
vector mins
Definition: csprogsdefs.qc:113
ERASEABLE float boxesoverlap(vector m1, vector m2, vector m3, vector m4)
requires that m2>m1 in all coordinates, and that m4>m3
Definition: vector.qh:73
vector com_phys_vel
Definition: physics.qh:6
#define NULL
Definition: post.qh:17
float trace_dpstartcontents
vector trace_endpos
Definition: csprogsdefs.qc:37
vector(float skel, float bonenum) _skel_get_boneabs_hidden
const float SOLID_TRIGGER
Definition: csprogsdefs.qc:245
setorigin(ent, v)
vector trace_plane_normal
Definition: csprogsdefs.qc:38
vector angles
Definition: csprogsdefs.qc:104
float trace_startsolid
Definition: csprogsdefs.qc:35
void
Definition: self.qh:83
vector absmin
Definition: csprogsdefs.qc:92
if(IS_DEAD(this))
Definition: impulse.qc:92
float trace_fraction
Definition: csprogsdefs.qc:36
float solid
Definition: csprogsdefs.qc:99
entity groundentity
Definition: physics.qc:421
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ sys_phys_update()

void sys_phys_update ( entity  this,
float  dt 
)

Definition at line 11 of file physics.qc.

References absmax, absmin, angles, CheckPlayerJump(), com_phys_acc_rate, com_phys_acc_rate_air, com_phys_acc_rate_air_stop, com_phys_acc_rate_air_strafe, com_phys_air, com_phys_friction, com_phys_friction_air, com_phys_gravity, com_phys_ground, com_phys_ladder, com_phys_vel_2d, com_phys_vel_max, com_phys_vel_max_air, com_phys_vel_max_air_strafe, com_phys_water, CONTENT_LAVA, CONTENT_SLIME, CONTENT_WATER, conveyor, disableclientprediction, emit, FL_WATERJUMP, flags, IS_CLIENT, IS_DEAD, IS_ONGROUND, IS_ONSLICK, IS_PLAYER, IS_SVQC, IsFlying(), ITEMS_STAT, jumppadcount, ladder_entity, lastground, min(), move_movetype, move_qcphysics, movedir, MOVETYPE_FLY, MOVETYPE_FLY_WORLDONLY, MOVETYPE_FOLLOW, MOVETYPE_NOCLIP, MOVETYPE_NONE, MUTATOR_CALLHOOK, PHYS_ACCELERATE, PHYS_AIRACCELERATE, PHYS_AIRSTOPACCELERATE, PHYS_AIRSTRAFEACCELERATE, PHYS_FRICTION, PHYS_FRICTION_ONLAND, PHYS_INPUT_BUTTON_MASK, PHYS_MAXAIRSPEED, PHYS_MAXAIRSTRAFESPEED, PHYS_MAXSPEED, PHYS_SLICK_APPLYGRAVITY, PM_check_blocked(), PM_check_frozen(), PM_check_hitground(), PM_check_slick(), PM_Footsteps(), PM_jetpack(), sys_in_update(), sys_phys_ai(), sys_phys_fix(), sys_phys_fixspeed(), sys_phys_monitor(), sys_phys_override(), sys_phys_postupdate(), sys_phys_pregame_hold(), sys_phys_simulate(), sys_phys_simulate_simple(), sys_phys_spectator_control(), teleport_time, time, v_angle, vector(), velocity, viewloc_PlayerPhysics(), WAS_ONGROUND, wasFlying, waterlevel, WATERLEVEL_NONE, and WATERLEVEL_SWIMMING.

Referenced by IsFlying(), and StartFrame().

12 {
13  if (!IS_CLIENT(this)) {
14  sys_phys_simulate_simple(this, dt);
15  return;
16  }
17  sys_in_update(this, dt);
18 
19  sys_phys_fix(this, dt);
20  if (sys_phys_override(this, dt))
21  return;
22 
23  sys_phys_monitor(this, dt);
24 
25  PHYS_CS(this).movement_old = PHYS_CS(this).movement;
26  PHYS_CS(this).v_angle_old = this.v_angle;
27  PHYS_CS(this).buttons_old = PHYS_INPUT_BUTTON_MASK(this);
28 
29  sys_phys_ai(this);
30 
32 
33  if (IS_SVQC) {
34  if (this.move_movetype == MOVETYPE_NONE) { return; }
35  // when we get here, disableclientprediction cannot be 2
36  if(this.move_movetype == MOVETYPE_FOLLOW) // not compatible with prediction
37  this.disableclientprediction = 1;
38  else if(this.move_qcphysics)
39  this.disableclientprediction = -1;
40  else
41  this.disableclientprediction = 0;
42  }
43 
45 
46  PM_check_frozen(this);
47 
48  PM_check_blocked(this);
49 
50  float maxspeed_mod = 1;
51 
52 // conveyors: first fix velocity
53  if (this.conveyor.active) { this.velocity -= this.conveyor.movedir; }
54  MUTATOR_CALLHOOK(PlayerPhysics, this, dt);
55 
56  if (!IS_PLAYER(this)) {
58  maxspeed_mod = STAT(SPECTATORSPEED, this);
59  }
60  sys_phys_fixspeed(this, maxspeed_mod);
61 
62  if (IS_DEAD(this)) {
63  // handle water here
64  vector midpoint = ((this.absmin + this.absmax) * 0.5);
65  int cont = pointcontents(midpoint);
66  if (cont == CONTENT_WATER || cont == CONTENT_LAVA || cont == CONTENT_SLIME) {
67  this.velocity = this.velocity * 0.5;
68 
69  // do we want this?
70  // if(pointcontents(midpoint + '0 0 2') == CONTENT_WATER)
71  // { this.velocity_z = 70; }
72  }
73  sys_phys_postupdate(this);
74  return;
75  }
76 
77  PM_check_slick(this);
78 
79  if (IS_SVQC && !PHYS_FIXANGLE(this)) { this.angles = '0 1 0' * this.v_angle.y; }
80  if (IS_PLAYER(this)) {
81  if (IS_ONGROUND(this)) {
82  PM_check_hitground(this);
83  PM_Footsteps(this);
84  } else if (IsFlying(this)) {
85  this.wasFlying = true;
86  }
87  CheckPlayerJump(this);
88  }
89 
90  if (this.flags & FL_WATERJUMP) {
91  this.velocity_x = this.movedir.x;
92  this.velocity_y = this.movedir.y;
93  if (time > this.teleport_time || this.waterlevel == WATERLEVEL_NONE) {
94  this.flags &= ~FL_WATERJUMP;
95  this.teleport_time = 0;
96  }
97  } else if (MUTATOR_CALLHOOK(PM_Physics, this, maxspeed_mod, dt)) {
98  // handled
99  } else if (this.move_movetype == MOVETYPE_NOCLIP
100  || this.move_movetype == MOVETYPE_FLY
102  || MUTATOR_CALLHOOK(IsFlying, this)) {
103  this.com_phys_friction = PHYS_FRICTION(this);
104  this.com_phys_vel_max = PHYS_MAXSPEED(this) * maxspeed_mod;
105  this.com_phys_acc_rate = PHYS_ACCELERATE(this) * maxspeed_mod;
106  this.com_phys_friction_air = true;
107  sys_phys_simulate(this, dt);
108  this.com_phys_friction_air = false;
109  } else if (this.waterlevel >= WATERLEVEL_SWIMMING) {
110  this.com_phys_vel_max = PHYS_MAXSPEED(this) * maxspeed_mod;
111  this.com_phys_acc_rate = PHYS_ACCELERATE(this) * maxspeed_mod;
112  this.com_phys_water = true;
113  sys_phys_simulate(this, dt);
114  this.com_phys_water = false;
115  this.jumppadcount = 0;
116  } else if (this.ladder_entity) {
117  this.com_phys_friction = PHYS_FRICTION(this);
118  this.com_phys_vel_max = PHYS_MAXSPEED(this) * maxspeed_mod;
119  this.com_phys_acc_rate = PHYS_ACCELERATE(this) * maxspeed_mod;
120  this.com_phys_gravity = -PHYS_GRAVITY(this) * dt;
121  if (PHYS_ENTGRAVITY(this)) { this.com_phys_gravity *= PHYS_ENTGRAVITY(this); }
122  this.com_phys_ladder = true;
123  this.com_phys_friction_air = true;
124  sys_phys_simulate(this, dt);
125  this.com_phys_friction_air = false;
126  this.com_phys_ladder = false;
127  this.com_phys_gravity = 0;
128  } else if (ITEMS_STAT(this) & IT_USING_JETPACK) {
129  PM_jetpack(this, maxspeed_mod, dt);
130  } else if (IS_ONGROUND(this) && (!IS_ONSLICK(this) || !PHYS_SLICK_APPLYGRAVITY(this))) {
131  if (!WAS_ONGROUND(this)) {
132  emit(phys_land, this);
133  if (this.lastground < time - 0.3) {
134  this.velocity *= (1 - PHYS_FRICTION_ONLAND(this));
135  }
136  }
137  this.com_phys_vel_max = PHYS_MAXSPEED(this) * maxspeed_mod;
138  this.com_phys_gravity = -PHYS_GRAVITY(this) * dt;
139  if (PHYS_ENTGRAVITY(this)) { this.com_phys_gravity *= PHYS_ENTGRAVITY(this); }
140  this.com_phys_ground = true;
141  this.com_phys_vel_2d = true;
142  sys_phys_simulate(this, dt);
143  this.com_phys_vel_2d = false;
144  this.com_phys_ground = false;
145  this.com_phys_gravity = 0;
146  } else {
147  this.com_phys_acc_rate_air = PHYS_AIRACCELERATE(this) * min(maxspeed_mod, 1);
148  this.com_phys_acc_rate_air_stop = PHYS_AIRSTOPACCELERATE(this) * maxspeed_mod;
149  this.com_phys_acc_rate_air_strafe = PHYS_AIRSTRAFEACCELERATE(this) * maxspeed_mod;
150  this.com_phys_vel_max_air_strafe = PHYS_MAXAIRSTRAFESPEED(this) * maxspeed_mod;
151  this.com_phys_vel_max_air = PHYS_MAXAIRSPEED(this) * maxspeed_mod;
152  this.com_phys_vel_max = PHYS_MAXAIRSPEED(this) * min(maxspeed_mod, 1);
153  this.com_phys_air = true;
154  this.com_phys_vel_2d = true;
155  sys_phys_simulate(this, dt);
156  this.com_phys_vel_2d = false;
157  this.com_phys_air = false;
158  }
159 
160  sys_phys_postupdate(this);
161 }
float MOVETYPE_NONE
Definition: progsdefs.qc:246
void CheckPlayerJump(entity this)
Definition: player.qc:473
#define PHYS_MAXAIRSPEED(s)
Definition: player.qh:130
const float CONTENT_LAVA
Definition: csprogsdefs.qc:240
#define WAS_ONGROUND(s)
Definition: player.qh:203
#define PHYS_ACCELERATE(s)
Definition: player.qh:91
float waterlevel
Definition: progsdefs.qc:181
#define IS_CLIENT(v)
Definition: utils.qh:13
bool sys_phys_override(entity this, float dt)
Definition: cl_physics.qc:13
void sys_phys_simulate(entity this, float dt)
for players
Definition: physics.qc:174
float teleport_time
Definition: player.qh:212
#define PHYS_FRICTION(s)
Definition: player.qh:110
void PM_check_slick(entity this)
Definition: player.qc:670
bool move_qcphysics
Definition: physics.qh:25
void PM_check_hitground(entity this)
Definition: player.qc:624
void sys_phys_postupdate(entity this)
Definition: physics.qc:163
bool com_phys_ladder
Definition: physics.qh:21
float com_phys_acc_rate_air_strafe
Definition: physics.qh:12
float com_phys_acc_rate_air
Definition: physics.qh:11
vector v_angle
Definition: progsdefs.qc:161
#define IS_ONGROUND(s)
Definition: movetypes.qh:16
#define PHYS_INPUT_BUTTON_MASK(s)
Definition: player.qh:185
float lastground
Definition: player.qh:61
void sys_phys_fixspeed(entity this, float maxspeed_mod)
Definition: cl_physics.qc:27
float jumppadcount
Definition: jumppads.qh:15
bool com_phys_ground
Definition: physics.qh:19
bool wasFlying
Definition: player.qh:62
float com_phys_acc_rate_air_stop
Definition: physics.qh:13
#define PHYS_SLICK_APPLYGRAVITY(s)
Definition: player.qh:144
#define ITEMS_STAT(s)
Definition: player.qh:210
float move_movetype
Definition: movetypes.qh:76
float com_phys_vel_max_air
Definition: physics.qh:8
void sys_phys_simulate_simple(entity this, float dt)
for other entities
Definition: physics.qc:423
const int WATERLEVEL_NONE
Definition: movetypes.qh:11
void viewloc_PlayerPhysics(entity this)
Definition: viewloc.qc:13
float com_phys_vel_max_air_strafe
Definition: physics.qh:9
vector absmax
Definition: csprogsdefs.qc:92
#define PHYS_AIRSTOPACCELERATE(s)
Definition: player.qh:102
vector movedir
Definition: progsdefs.qc:203
void PM_Footsteps(entity this)
Definition: player.qc:649
const float CONTENT_SLIME
Definition: csprogsdefs.qc:239
entity conveyor
Definition: player.qh:54
const float CONTENT_WATER
Definition: csprogsdefs.qc:238
void PM_check_frozen(entity this)
Definition: player.qc:609
#define PHYS_AIRACCELERATE(s)
Definition: player.qh:92
float MOVETYPE_FLY_WORLDONLY
#define IS_ONSLICK(s)
Definition: movetypes.qh:19
float com_phys_friction
Definition: physics.qh:14
void sys_phys_ai(entity this)
Definition: cl_physics.qc:21
void PM_jetpack(entity this, float maxspd_mod, float dt)
Definition: player.qc:695
void PM_check_blocked(entity this)
Definition: player.qc:683
#define IS_DEAD(s)
Definition: utils.qh:26
void sys_phys_pregame_hold(entity this)
Definition: cl_physics.qc:23
bool IsFlying(entity this)
Definition: player.qc:804
float com_phys_acc_rate
Definition: physics.qh:10
entity ladder_entity
Definition: ladder.qh:11
#define IS_SVQC
Definition: _all.inc:14
vector(float skel, float bonenum) _skel_get_boneabs_hidden
bool com_phys_air
Definition: physics.qh:20
float com_phys_vel_max
Definition: physics.qh:7
float MOVETYPE_NOCLIP
Definition: progsdefs.qc:254
float flags
Definition: csprogsdefs.qc:129
float MOVETYPE_FOLLOW
bool com_phys_water
Definition: physics.qh:23
bool com_phys_vel_2d
Definition: physics.qh:22
const int WATERLEVEL_SWIMMING
Definition: movetypes.qh:13
void sys_in_update(entity this, float dt)
Definition: input.qc:3
float com_phys_gravity
Definition: physics.qh:16
#define MUTATOR_CALLHOOK(id,...)
Definition: base.qh:140
#define PHYS_MAXAIRSTRAFESPEED(s)
Definition: player.qh:131
#define emit(T,...)
Definition: lib.qh:17
void sys_phys_fix(entity this, float dt)
Definition: cl_physics.qc:3
vector angles
Definition: csprogsdefs.qc:104
vector absmin
Definition: csprogsdefs.qc:92
#define PHYS_AIRSTRAFEACCELERATE(s)
Definition: player.qh:103
float time
Definition: csprogsdefs.qc:16
void sys_phys_monitor(entity this, float dt)
Definition: cl_physics.qc:19
vector velocity
Definition: csprogsdefs.qc:103
#define PHYS_MAXSPEED(s)
Definition: player.qh:132
float MOVETYPE_FLY
Definition: progsdefs.qc:251
#define IS_PLAYER(v)
Definition: utils.qh:9
float FL_WATERJUMP
Definition: progsdefs.qc:242
int disableclientprediction
Definition: physics.qc:4
bool com_phys_friction_air
Definition: physics.qh:24
#define PHYS_FRICTION_ONLAND(s)
Definition: player.qh:111
void sys_phys_spectator_control(entity this)
Definition: cl_physics.qc:25
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ sys_phys_update_single()

void sys_phys_update_single ( entity  this)

Definition at line 508 of file physics.qc.

References frametime, and sys_phys_simulate_simple().

509 {
511 }
void sys_phys_simulate_simple(entity this, float dt)
for other entities
Definition: physics.qc:423
float frametime
Definition: csprogsdefs.qc:17
+ Here is the call graph for this function:

Variable Documentation

◆ disableclientprediction

int disableclientprediction

Definition at line 4 of file physics.qc.

Referenced by sys_phys_update().

◆ groundentity

entity groundentity

Definition at line 421 of file physics.qc.

Referenced by sys_phys_simulate_simple().