+ // set buttons and impulse
+ cl.cmd.buttons = bits;
+ cl.cmd.impulse = in_impulse;
+
+ // set viewangles
+ VectorCopy(cl.viewangles, cl.cmd.viewangles);
+
+ msecdelta = (int)(floor(cl.cmd.time * 1000) - floor(cl.movecmd[1].time * 1000));
+ cl.cmd.msec = (unsigned char)bound(0, msecdelta, 255);
+ // ridiculous value rejection (matches qw)
+ if (cl.cmd.msec > 250)
+ cl.cmd.msec = 100;
+ cl.cmd.frametime = cl.cmd.msec * (1.0 / 1000.0);
+
+ cl.cmd.predicted = cl_movement.integer;
+
+ // movement is set by input code (forwardmove/sidemove/upmove)
+ // always dump the first two moves, because they may contain leftover inputs from the last level
+ if (cl.cmd.sequence <= 2)
+ cl.cmd.forwardmove = cl.cmd.sidemove = cl.cmd.upmove = cl.cmd.impulse = cl.cmd.buttons = 0;
+
+ cl.cmd.jump = (cl.cmd.buttons & 2) != 0;
+ cl.cmd.crouch = 0;
+ switch (cls.protocol)
+ {
+ case PROTOCOL_QUAKEWORLD:
+ case PROTOCOL_QUAKE:
+ case PROTOCOL_QUAKEDP:
+ case PROTOCOL_NEHAHRAMOVIE:
+ case PROTOCOL_NEHAHRABJP:
+ case PROTOCOL_NEHAHRABJP2:
+ case PROTOCOL_NEHAHRABJP3:
+ case PROTOCOL_DARKPLACES1:
+ case PROTOCOL_DARKPLACES2:
+ case PROTOCOL_DARKPLACES3:
+ case PROTOCOL_DARKPLACES4:
+ case PROTOCOL_DARKPLACES5:
+ break;
+ case PROTOCOL_DARKPLACES6:
+ case PROTOCOL_DARKPLACES7:
+ // FIXME: cl.movecmd[0].buttons & 16 is +button5, Nexuiz specific
+ cl.cmd.crouch = (cl.cmd.buttons & 16) != 0;
+ break;
+ case PROTOCOL_UNKNOWN:
+ break;
+ }
+
+ cl.movecmd[0] = cl.cmd;
+
+ // don't predict more than 200fps
+ if (realtime >= cl.lastpackettime + 0.005)
+ cl.movement_replay = true; // redo the prediction
+
+ // now decide whether to actually send this move
+ // (otherwise it is only for prediction)
+
+ // don't send too often or else network connections can get clogged by a
+ // high renderer framerate