1 /*
2 ===========================================================================
3
4 Return to Castle Wolfenstein multiplayer GPL Source Code
5 Copyright (C) 1999-2010 id Software LLC, a ZeniMax Media company.
6
7 This file is part of the Return to Castle Wolfenstein multiplayer GPL Source Code (RTCW MP Source Code).
8
9 RTCW MP Source Code is free software: you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation, either version 3 of the License, or
12 (at your option) any later version.
13
14 RTCW MP Source Code is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
18
19 You should have received a copy of the GNU General Public License
20 along with RTCW MP Source Code. If not, see <http://www.gnu.org/licenses/>.
21
22 In addition, the RTCW MP Source Code is also subject to certain additional terms. You should have received a copy of these additional terms immediately following the terms and conditions of the GNU General Public License which accompanied the RTCW MP Source Code. If not, please request a copy in writing from id Software at the address below.
23
24 If you have questions concerning this license or the applicable additional terms, you may contact in writing id Software LLC, c/o ZeniMax Media Inc., Suite 120, Rockville, Maryland 20850 USA.
25
26 ===========================================================================
27 */
28
29 // cl.input.c -- builds an intended movement command to send to the server
30
31 #include "client.h"
32
33 unsigned frame_msec;
34 int old_com_frameTime;
35
36 /*
37 ===============================================================================
38
39 KEY BUTTONS
40
41 Continuous button event tracking is complicated by the fact that two different
42 input sources (say, mouse button 1 and the control key) can both press the
43 same button, but the button should only be released when both of the
44 pressing key have been released.
45
46 When a key event issues a button command (+forward, +attack, etc), it appends
47 its key number as argv(1) so it can be matched up with the release.
48
49 argv(2) will be set to the time the event happened, which allows exact
50 control even at low framerates when the down and up events may both get qued
51 at the same time.
52
53 ===============================================================================
54 */
55
56 static kbutton_t kb[NUM_BUTTONS];
57
58 #ifdef USE_VOIP
59 kbutton_t in_voiprecord;
60 #endif
61
IN_MLookDown(void)62 void IN_MLookDown( void ) {
63 kb[KB_MLOOK].active = qtrue;
64 }
65
IN_MLookUp(void)66 void IN_MLookUp( void ) {
67 kb[KB_MLOOK].active = qfalse;
68 if ( !cl_freelook->integer ) {
69 IN_CenterView();
70 }
71 }
72
IN_KeyDown(kbutton_t * b)73 void IN_KeyDown( kbutton_t *b ) {
74 int k;
75 char *c;
76
77 c = Cmd_Argv( 1 );
78 if ( c[0] ) {
79 k = atoi( c );
80 } else {
81 k = -1; // typed manually at the console for continuous down
82 }
83
84 if ( k == b->down[0] || k == b->down[1] ) {
85 return; // repeating key
86 }
87
88 if ( !b->down[0] ) {
89 b->down[0] = k;
90 } else if ( !b->down[1] ) {
91 b->down[1] = k;
92 } else {
93 Com_Printf( "Three keys down for a button!\n" );
94 return;
95 }
96
97 if ( b->active ) {
98 return; // still down
99 }
100
101 // save timestamp for partial frame summing
102 c = Cmd_Argv( 2 );
103 b->downtime = atoi( c );
104
105 b->active = qtrue;
106 b->wasPressed = qtrue;
107 }
108
IN_KeyUp(kbutton_t * b)109 void IN_KeyUp( kbutton_t *b ) {
110 int k;
111 char *c;
112 unsigned uptime;
113
114 c = Cmd_Argv( 1 );
115 if ( c[0] ) {
116 k = atoi( c );
117 } else {
118 // typed manually at the console, assume for unsticking, so clear all
119 b->down[0] = b->down[1] = 0;
120 b->active = qfalse;
121 return;
122 }
123
124 if ( b->down[0] == k ) {
125 b->down[0] = 0;
126 } else if ( b->down[1] == k ) {
127 b->down[1] = 0;
128 } else {
129 return; // key up without coresponding down (menu pass through)
130 }
131 if ( b->down[0] || b->down[1] ) {
132 return; // some other key is still holding it down
133 }
134
135 b->active = qfalse;
136
137 // save timestamp for partial frame summing
138 c = Cmd_Argv( 2 );
139 uptime = atoi( c );
140 if ( uptime ) {
141 b->msec += uptime - b->downtime;
142 } else {
143 b->msec += frame_msec / 2;
144 }
145
146 b->active = qfalse;
147 }
148
149
150
151 /*
152 ===============
153 CL_KeyState
154
155 Returns the fraction of the frame that the key was down
156 ===============
157 */
CL_KeyState(kbutton_t * key)158 float CL_KeyState( kbutton_t *key ) {
159 float val;
160 int msec;
161
162 msec = key->msec;
163 key->msec = 0;
164
165 if ( key->active ) {
166 // still down
167 if ( !key->downtime ) {
168 msec = com_frameTime;
169 } else {
170 msec += com_frameTime - key->downtime;
171 }
172 key->downtime = com_frameTime;
173 }
174
175 #if 0
176 if ( msec ) {
177 Com_Printf( "%i ", msec );
178 }
179 #endif
180
181 val = (float)msec / frame_msec;
182 if ( val < 0 ) {
183 val = 0;
184 }
185 if ( val > 1 ) {
186 val = 1;
187 }
188
189 return val;
190 }
191
192
193
IN_UpDown(void)194 void IN_UpDown( void ) {IN_KeyDown( &kb[KB_UP] );}
IN_UpUp(void)195 void IN_UpUp( void ) {IN_KeyUp( &kb[KB_UP] );}
IN_DownDown(void)196 void IN_DownDown( void ) {IN_KeyDown( &kb[KB_DOWN] );}
IN_DownUp(void)197 void IN_DownUp( void ) {IN_KeyUp( &kb[KB_DOWN] );}
IN_LeftDown(void)198 void IN_LeftDown( void ) {IN_KeyDown( &kb[KB_LEFT] );}
IN_LeftUp(void)199 void IN_LeftUp( void ) {IN_KeyUp( &kb[KB_LEFT] );}
IN_RightDown(void)200 void IN_RightDown( void ) {IN_KeyDown( &kb[KB_RIGHT] );}
IN_RightUp(void)201 void IN_RightUp( void ) {IN_KeyUp( &kb[KB_RIGHT] );}
IN_ForwardDown(void)202 void IN_ForwardDown( void ) {IN_KeyDown( &kb[KB_FORWARD] );}
IN_ForwardUp(void)203 void IN_ForwardUp( void ) {IN_KeyUp( &kb[KB_FORWARD] );}
IN_BackDown(void)204 void IN_BackDown( void ) {IN_KeyDown( &kb[KB_BACK] );}
IN_BackUp(void)205 void IN_BackUp( void ) {IN_KeyUp( &kb[KB_BACK] );}
IN_LookupDown(void)206 void IN_LookupDown( void ) {IN_KeyDown( &kb[KB_LOOKUP] );}
IN_LookupUp(void)207 void IN_LookupUp( void ) {IN_KeyUp( &kb[KB_LOOKUP] );}
IN_LookdownDown(void)208 void IN_LookdownDown( void ) {IN_KeyDown( &kb[KB_LOOKDOWN] );}
IN_LookdownUp(void)209 void IN_LookdownUp( void ) {IN_KeyUp( &kb[KB_LOOKDOWN] );}
IN_MoveleftDown(void)210 void IN_MoveleftDown( void ) {IN_KeyDown( &kb[KB_MOVELEFT] );}
IN_MoveleftUp(void)211 void IN_MoveleftUp( void ) {IN_KeyUp( &kb[KB_MOVELEFT] );}
IN_MoverightDown(void)212 void IN_MoverightDown( void ) {IN_KeyDown( &kb[KB_MOVERIGHT] );}
IN_MoverightUp(void)213 void IN_MoverightUp( void ) {IN_KeyUp( &kb[KB_MOVERIGHT] );}
214
IN_SpeedDown(void)215 void IN_SpeedDown( void ) {IN_KeyDown( &kb[KB_SPEED] );}
IN_SpeedUp(void)216 void IN_SpeedUp( void ) {IN_KeyUp( &kb[KB_SPEED] );}
IN_StrafeDown(void)217 void IN_StrafeDown( void ) {IN_KeyDown( &kb[KB_STRAFE] );}
IN_StrafeUp(void)218 void IN_StrafeUp( void ) {IN_KeyUp( &kb[KB_STRAFE] );}
219
220 #ifdef USE_VOIP
IN_VoipRecordDown(void)221 void IN_VoipRecordDown(void)
222 {
223 IN_KeyDown(&in_voiprecord);
224 Cvar_Set("cl_voipSend", "1");
225 }
226
IN_VoipRecordUp(void)227 void IN_VoipRecordUp(void)
228 {
229 IN_KeyUp(&in_voiprecord);
230 Cvar_Set("cl_voipSend", "0");
231 }
232 #endif
233
IN_Button0Down(void)234 void IN_Button0Down( void ) {IN_KeyDown( &kb[KB_BUTTONS0] );}
IN_Button0Up(void)235 void IN_Button0Up( void ) {IN_KeyUp( &kb[KB_BUTTONS0] );}
IN_Button1Down(void)236 void IN_Button1Down( void ) {IN_KeyDown( &kb[KB_BUTTONS1] );}
IN_Button1Up(void)237 void IN_Button1Up( void ) {IN_KeyUp( &kb[KB_BUTTONS1] );}
IN_UseItemDown(void)238 void IN_UseItemDown( void ) {IN_KeyDown( &kb[KB_BUTTONS2] );}
IN_UseItemUp(void)239 void IN_UseItemUp( void ) {IN_KeyUp( &kb[KB_BUTTONS2] );}
IN_Button3Down(void)240 void IN_Button3Down( void ) {IN_KeyDown( &kb[KB_BUTTONS3] );}
IN_Button3Up(void)241 void IN_Button3Up( void ) {IN_KeyUp( &kb[KB_BUTTONS3] );}
IN_Button4Down(void)242 void IN_Button4Down( void ) {IN_KeyDown( &kb[KB_BUTTONS4] );}
IN_Button4Up(void)243 void IN_Button4Up( void ) {IN_KeyUp( &kb[KB_BUTTONS4] );}
244 // void IN_Button5Down(void) {IN_KeyDown(&kb[KB_BUTTONS5]);}
245 // void IN_Button5Up(void) {IN_KeyUp(&kb[KB_BUTTONS5]);}
246
247 // void IN_Button6Down(void) {IN_KeyDown(&kb[KB_BUTTONS6]);}
248 // void IN_Button6Up(void) {IN_KeyUp(&kb[KB_BUTTONS6]);}
249
250 // Rafael activate
IN_ActivateDown(void)251 void IN_ActivateDown( void ) {IN_KeyDown( &kb[KB_BUTTONS6] );}
IN_ActivateUp(void)252 void IN_ActivateUp( void ) {IN_KeyUp( &kb[KB_BUTTONS6] );}
253 // done.
254
255 // Rafael Kick
IN_KickDown(void)256 void IN_KickDown( void ) {IN_KeyDown( &kb[KB_KICK] );}
IN_KickUp(void)257 void IN_KickUp( void ) {IN_KeyUp( &kb[KB_KICK] );}
258 // done.
259
IN_SprintDown(void)260 void IN_SprintDown( void ) {IN_KeyDown( &kb[KB_BUTTONS5] );}
IN_SprintUp(void)261 void IN_SprintUp( void ) {IN_KeyUp( &kb[KB_BUTTONS5] );}
262
263
264 // wbuttons (wolf buttons)
IN_Wbutton0Down(void)265 void IN_Wbutton0Down( void ) { IN_KeyDown( &kb[KB_WBUTTONS0] ); } //----(SA) secondary fire button
IN_Wbutton0Up(void)266 void IN_Wbutton0Up( void ) { IN_KeyUp( &kb[KB_WBUTTONS0] ); }
IN_ZoomDown(void)267 void IN_ZoomDown( void ) { IN_KeyDown( &kb[KB_WBUTTONS1] ); } //----(SA) zoom key
IN_ZoomUp(void)268 void IN_ZoomUp( void ) { IN_KeyUp( &kb[KB_WBUTTONS1] ); }
IN_QuickGrenDown(void)269 void IN_QuickGrenDown( void ) { IN_KeyDown( &kb[KB_WBUTTONS2] ); } //----(SA) "Quickgrenade"
IN_QuickGrenUp(void)270 void IN_QuickGrenUp( void ) { IN_KeyUp( &kb[KB_WBUTTONS2] ); }
IN_ReloadDown(void)271 void IN_ReloadDown( void ) { IN_KeyDown( &kb[KB_WBUTTONS3] ); } //----(SA) manual weapon re-load
IN_ReloadUp(void)272 void IN_ReloadUp( void ) { IN_KeyUp( &kb[KB_WBUTTONS3] ); }
IN_LeanLeftDown(void)273 void IN_LeanLeftDown( void ) { IN_KeyDown( &kb[KB_WBUTTONS4] ); } //----(SA) lean left
IN_LeanLeftUp(void)274 void IN_LeanLeftUp( void ) { IN_KeyUp( &kb[KB_WBUTTONS4] ); }
IN_LeanRightDown(void)275 void IN_LeanRightDown( void ) { IN_KeyDown( &kb[KB_WBUTTONS5] ); } //----(SA) lean right
IN_LeanRightUp(void)276 void IN_LeanRightUp( void ) { IN_KeyUp( &kb[KB_WBUTTONS5] ); }
277
278 // JPW NERVE
IN_MP_DropWeaponDown(void)279 void IN_MP_DropWeaponDown( void ) {IN_KeyDown( &kb[KB_WBUTTONS6] );}
IN_MP_DropWeaponUp(void)280 void IN_MP_DropWeaponUp( void ) {IN_KeyUp( &kb[KB_WBUTTONS6] );}
281 // jpw
282
283 // unused
IN_Wbutton7Down(void)284 void IN_Wbutton7Down( void ) { IN_KeyDown( &kb[KB_WBUTTONS7] ); }
IN_Wbutton7Up(void)285 void IN_Wbutton7Up( void ) { IN_KeyUp( &kb[KB_WBUTTONS7] ); }
286
IN_CenterView(void)287 void IN_CenterView( void ) {
288 qboolean ok = qtrue;
289 if ( cgvm ) {
290 ok = VM_Call( cgvm, CG_CHECKCENTERVIEW );
291 }
292 if ( ok ) {
293 cl.viewangles[PITCH] = -SHORT2ANGLE( cl.snap.ps.delta_angles[PITCH] );
294 }
295 }
296
IN_Notebook(void)297 void IN_Notebook( void ) {
298 //if ( cls.state == CA_ACTIVE && !clc.demoplaying ) {
299 //VM_Call( uivm, UI_SET_ACTIVE_MENU, UIMENU_NOTEBOOK); // startup notebook
300 //}
301 }
302
IN_Help(void)303 void IN_Help( void ) {
304 if ( clc.state == CA_ACTIVE && !clc.demoplaying ) {
305 VM_Call( uivm, UI_SET_ACTIVE_MENU, UIMENU_HELP ); // startup help system
306 }
307 }
308
309
310 //==========================================================================
311
312 cvar_t *cl_yawspeed;
313 cvar_t *cl_pitchspeed;
314
315 cvar_t *cl_run;
316
317 cvar_t *cl_anglespeedkey;
318
319 cvar_t *cl_recoilPitch;
320
321 cvar_t *cl_bypassMouseInput; // NERVE - SMF
322
323 /*
324 ================
325 CL_AdjustAngles
326
327 Moves the local angle positions
328 ================
329 */
CL_AdjustAngles(void)330 void CL_AdjustAngles( void ) {
331 float speed;
332
333 if ( kb[KB_SPEED].active ) {
334 speed = 0.001 * cls.frametime * cl_anglespeedkey->value;
335 } else {
336 speed = 0.001 * cls.frametime;
337 }
338
339 if ( !kb[KB_STRAFE].active ) {
340 cl.viewangles[YAW] -= speed * cl_yawspeed->value * CL_KeyState( &kb[KB_RIGHT] );
341 cl.viewangles[YAW] += speed * cl_yawspeed->value * CL_KeyState( &kb[KB_LEFT] );
342 }
343
344 cl.viewangles[PITCH] -= speed * cl_pitchspeed->value * CL_KeyState( &kb[KB_LOOKUP] );
345 cl.viewangles[PITCH] += speed * cl_pitchspeed->value * CL_KeyState( &kb[KB_LOOKDOWN] );
346 }
347
348 /*
349 ================
350 CL_KeyMove
351
352 Sets the usercmd_t based on key states
353 ================
354 */
CL_KeyMove(usercmd_t * cmd)355 void CL_KeyMove( usercmd_t *cmd ) {
356 int movespeed;
357 int forward, side, up;
358 // Rafael Kick
359 int kick;
360 // done
361
362 //
363 // adjust for speed key / running
364 // the walking flag is to keep animations consistant
365 // even during acceleration and develeration
366 //
367 if ( kb[KB_SPEED].active ^ cl_run->integer ) {
368 movespeed = 127;
369 cmd->buttons &= ~BUTTON_WALKING;
370 } else {
371 cmd->buttons |= BUTTON_WALKING;
372 movespeed = 64;
373 }
374
375 forward = 0;
376 side = 0;
377 up = 0;
378 if ( kb[KB_STRAFE].active ) {
379 side += movespeed * CL_KeyState( &kb[KB_RIGHT] );
380 side -= movespeed * CL_KeyState( &kb[KB_LEFT] );
381 }
382
383 side += movespeed * CL_KeyState( &kb[KB_MOVERIGHT] );
384 side -= movespeed * CL_KeyState( &kb[KB_MOVELEFT] );
385
386 //----(SA) added
387 if ( cmd->buttons & BUTTON_ACTIVATE ) {
388 if ( side > 0 ) {
389 cmd->wbuttons |= WBUTTON_LEANRIGHT;
390 } else if ( side < 0 ) {
391 cmd->wbuttons |= WBUTTON_LEANLEFT;
392 }
393
394 side = 0; // disallow the strafe when holding 'activate'
395 }
396 //----(SA) end
397
398 up += movespeed * CL_KeyState( &kb[KB_UP] );
399 up -= movespeed * CL_KeyState( &kb[KB_DOWN] );
400
401 forward += movespeed * CL_KeyState( &kb[KB_FORWARD] );
402 forward -= movespeed * CL_KeyState( &kb[KB_BACK] );
403
404 // Rafael Kick
405 kick = CL_KeyState( &kb[KB_KICK] );
406 // done
407
408 if ( !( cl.snap.ps.persistant[PERS_HWEAPON_USE] ) ) {
409 cmd->forwardmove = ClampChar( forward );
410 cmd->rightmove = ClampChar( side );
411 cmd->upmove = ClampChar( up );
412
413 // Rafael - Kick
414 cmd->wolfkick = ClampChar( kick );
415 // done
416
417 }
418 }
419
420 /*
421 =================
422 CL_MouseEvent
423 =================
424 */
CL_MouseEvent(int dx,int dy,int time)425 void CL_MouseEvent( int dx, int dy, int time ) {
426 if ( Key_GetCatcher( ) & KEYCATCH_UI ) {
427 // NERVE - SMF - if we just want to pass it along to game
428 if ( cl_bypassMouseInput->integer == 1 ) {
429 cl.mouseDx[cl.mouseIndex] += dx;
430 cl.mouseDy[cl.mouseIndex] += dy;
431 } else {
432 VM_Call( uivm, UI_MOUSE_EVENT, dx, dy );
433 }
434
435 } else if (Key_GetCatcher( ) & KEYCATCH_CGAME) {
436 VM_Call( cgvm, CG_MOUSE_EVENT, dx, dy );
437 } else {
438 cl.mouseDx[cl.mouseIndex] += dx;
439 cl.mouseDy[cl.mouseIndex] += dy;
440 }
441 }
442
443 /*
444 =================
445 CL_JoystickEvent
446
447 Joystick values stay set until changed
448 =================
449 */
CL_JoystickEvent(int axis,int value,int time)450 void CL_JoystickEvent( int axis, int value, int time ) {
451 if ( axis < 0 || axis >= MAX_JOYSTICK_AXIS ) {
452 Com_Error( ERR_DROP, "CL_JoystickEvent: bad axis %i", axis );
453 }
454 cl.joystickAxis[axis] = value;
455 }
456
457 /*
458 =================
459 CL_JoystickMove
460 =================
461 */
CL_JoystickMove(usercmd_t * cmd)462 void CL_JoystickMove( usercmd_t *cmd ) {
463 float anglespeed;
464
465 float yaw = j_yaw->value * cl.joystickAxis[j_yaw_axis->integer];
466 float right = j_side->value * cl.joystickAxis[j_side_axis->integer];
467 float forward = j_forward->value * cl.joystickAxis[j_forward_axis->integer];
468 float pitch = j_pitch->value * cl.joystickAxis[j_pitch_axis->integer];
469 float up = j_up->value * cl.joystickAxis[j_up_axis->integer];
470
471 if ( !( kb[KB_SPEED].active ^ cl_run->integer ) ) {
472 cmd->buttons |= BUTTON_WALKING;
473 }
474
475 if ( kb[KB_SPEED].active ) {
476 anglespeed = 0.001 * cls.frametime * cl_anglespeedkey->value;
477 } else {
478 anglespeed = 0.001 * cls.frametime;
479 }
480
481 if ( !kb[KB_STRAFE].active ) {
482 cl.viewangles[YAW] += anglespeed * yaw;
483 cmd->rightmove = ClampChar( cmd->rightmove + (int)right );
484 } else {
485 cl.viewangles[YAW] += anglespeed * right;
486 cmd->rightmove = ClampChar( cmd->rightmove + (int)yaw );
487 }
488 if ( kb[KB_MLOOK].active ) {
489 cl.viewangles[PITCH] += anglespeed * forward;
490 cmd->forwardmove = ClampChar( cmd->forwardmove + (int)pitch );
491 } else {
492 cl.viewangles[PITCH] += anglespeed * pitch;
493 cmd->forwardmove = ClampChar( cmd->forwardmove + (int)forward );
494 }
495
496 cmd->upmove = ClampChar( cmd->upmove + (int)up );
497 }
498
499 /*
500 =================
501 CL_MouseMove
502 =================
503 */
CL_MouseMove(usercmd_t * cmd)504 void CL_MouseMove(usercmd_t *cmd) {
505 float mx, my;
506
507 // allow mouse smoothing
508 if ( m_filter->integer ) {
509 mx = ( cl.mouseDx[0] + cl.mouseDx[1] ) * 0.5f;
510 my = ( cl.mouseDy[0] + cl.mouseDy[1] ) * 0.5f;
511 } else {
512 mx = cl.mouseDx[cl.mouseIndex];
513 my = cl.mouseDy[cl.mouseIndex];
514 }
515 cl.mouseIndex ^= 1;
516 cl.mouseDx[cl.mouseIndex] = 0;
517 cl.mouseDy[cl.mouseIndex] = 0;
518
519 if (mx == 0.0f && my == 0.0f)
520 return;
521
522 if (cl_mouseAccel->value != 0.0f)
523 {
524 if(cl_mouseAccelStyle->integer == 0)
525 {
526 float accelSensitivity;
527 float rate;
528
529 rate = sqrt(mx * mx + my * my) / (float) frame_msec;
530
531 accelSensitivity = cl_sensitivity->value + rate * cl_mouseAccel->value;
532 mx *= accelSensitivity;
533 my *= accelSensitivity;
534
535 if(cl_showMouseRate->integer)
536 Com_Printf("rate: %f, accelSensitivity: %f\n", rate, accelSensitivity);
537 }
538 else
539 {
540 float rate[2];
541 float power[2];
542
543 // sensitivity remains pretty much unchanged at low speeds
544 // cl_mouseAccel is a power value to how the acceleration is shaped
545 // cl_mouseAccelOffset is the rate for which the acceleration will have doubled the non accelerated amplification
546 // NOTE: decouple the config cvars for independent acceleration setup along X and Y?
547
548 rate[0] = fabs(mx) / (float) frame_msec;
549 rate[1] = fabs(my) / (float) frame_msec;
550 power[0] = powf(rate[0] / cl_mouseAccelOffset->value, cl_mouseAccel->value);
551 power[1] = powf(rate[1] / cl_mouseAccelOffset->value, cl_mouseAccel->value);
552
553 mx = cl_sensitivity->value * (mx + ((mx < 0) ? -power[0] : power[0]) * cl_mouseAccelOffset->value);
554 my = cl_sensitivity->value * (my + ((my < 0) ? -power[1] : power[1]) * cl_mouseAccelOffset->value);
555
556 if(cl_showMouseRate->integer)
557 Com_Printf("ratex: %f, ratey: %f, powx: %f, powy: %f\n", rate[0], rate[1], power[0], power[1]);
558 }
559 }
560 else
561 {
562 // Rafael - mg42
563 if ( cl.snap.ps.persistant[PERS_HWEAPON_USE] ) {
564 mx *= 2.5; //(accelSensitivity * 0.1);
565 my *= 2; //(accelSensitivity * 0.075);
566 } else
567 {
568 mx *= cl_sensitivity->value;
569 my *= cl_sensitivity->value;
570 }
571 }
572
573 // ingame FOV
574 mx *= cl.cgameSensitivity;
575 my *= cl.cgameSensitivity;
576
577 // add mouse X/Y movement to cmd
578 if ( kb[KB_STRAFE].active ) {
579 cmd->rightmove = ClampChar( cmd->rightmove + m_side->value * mx );
580 } else {
581 cl.viewangles[YAW] -= m_yaw->value * mx;
582 }
583
584 if ( ( kb[KB_MLOOK].active || cl_freelook->integer ) && !kb[KB_STRAFE].active ) {
585 cl.viewangles[PITCH] += m_pitch->value * my;
586 } else {
587 cmd->forwardmove = ClampChar( cmd->forwardmove - m_forward->value * my );
588 }
589 }
590
591
592 /*
593 ==============
594 CL_CmdButtons
595 ==============
596 */
CL_CmdButtons(usercmd_t * cmd)597 void CL_CmdButtons( usercmd_t *cmd ) {
598 int i;
599
600 //
601 // figure button bits
602 // send a button bit even if the key was pressed and released in
603 // less than a frame
604 //
605 for ( i = 0 ; i < 7 ; i++ ) {
606 if ( kb[KB_BUTTONS0 + i].active || kb[KB_BUTTONS0 + i].wasPressed ) {
607 cmd->buttons |= 1 << i;
608 }
609 kb[KB_BUTTONS0 + i].wasPressed = qfalse;
610 }
611
612 for ( i = 0 ; i < 7 ; i++ ) {
613 if ( kb[KB_WBUTTONS0 + i].active || kb[KB_WBUTTONS0 + i].wasPressed ) {
614 cmd->wbuttons |= 1 << i;
615 }
616 kb[KB_WBUTTONS0 + i].wasPressed = qfalse;
617 }
618
619 if ( Key_GetCatcher( ) && !cl_bypassMouseInput->integer ) {
620 cmd->buttons |= BUTTON_TALK;
621 }
622
623 // allow the game to know if any key at all is
624 // currently pressed, even if it isn't bound to anything
625 if ( anykeydown && ( Key_GetCatcher( ) == 0 || cl_bypassMouseInput->integer ) ) {
626 cmd->buttons |= BUTTON_ANY;
627 }
628 }
629
630
631 /*
632 ==============
633 CL_FinishMove
634 ==============
635 */
CL_FinishMove(usercmd_t * cmd)636 void CL_FinishMove( usercmd_t *cmd ) {
637 int i;
638
639 // copy the state that the cgame is currently sending
640 cmd->weapon = cl.cgameUserCmdValue;
641
642 cmd->holdable = cl.cgameUserHoldableValue; //----(SA) modified
643
644 cmd->mpSetup = cl.cgameMpSetup; // NERVE - SMF
645 cmd->identClient = cl.cgameMpIdentClient; // NERVE - SMF
646
647 // send the current server time so the amount of movement
648 // can be determined without allowing cheating
649 cmd->serverTime = cl.serverTime;
650
651 for ( i = 0 ; i < 3 ; i++ ) {
652 cmd->angles[i] = ANGLE2SHORT( cl.viewangles[i] );
653 }
654 }
655
656
657 /*
658 =================
659 CL_CreateCmd
660 =================
661 */
CL_CreateCmd(void)662 usercmd_t CL_CreateCmd( void ) {
663 usercmd_t cmd;
664 vec3_t oldAngles;
665 float recoilAdd;
666
667 VectorCopy( cl.viewangles, oldAngles );
668
669 // keyboard angle adjustment
670 CL_AdjustAngles();
671
672 memset( &cmd, 0, sizeof( cmd ) );
673
674 CL_CmdButtons( &cmd );
675
676 // get basic movement from keyboard
677 CL_KeyMove( &cmd );
678
679 // get basic movement from mouse
680 CL_MouseMove( &cmd );
681
682 // get basic movement from joystick
683 CL_JoystickMove( &cmd );
684
685 // check to make sure the angles haven't wrapped
686 if ( cl.viewangles[PITCH] - oldAngles[PITCH] > 90 ) {
687 cl.viewangles[PITCH] = oldAngles[PITCH] + 90;
688 } else if ( oldAngles[PITCH] - cl.viewangles[PITCH] > 90 ) {
689 cl.viewangles[PITCH] = oldAngles[PITCH] - 90;
690 }
691
692 // RF, set the kickAngles so aiming is effected
693 recoilAdd = cl_recoilPitch->value;
694 if ( fabs( cl.viewangles[PITCH] + recoilAdd ) < 40 ) {
695 cl.viewangles[PITCH] += recoilAdd;
696 }
697 // the recoilPitch has been used, so clear it out
698 cl_recoilPitch->value = 0;
699
700 // store out the final values
701 CL_FinishMove( &cmd );
702
703 // draw debug graphs of turning for mouse testing
704 if ( cl_debugMove->integer ) {
705 if ( cl_debugMove->integer == 1 ) {
706 SCR_DebugGraph( fabs(cl.viewangles[YAW] - oldAngles[YAW]) );
707 }
708 if ( cl_debugMove->integer == 2 ) {
709 SCR_DebugGraph( fabs(cl.viewangles[PITCH] - oldAngles[PITCH]) );
710 }
711 }
712
713 return cmd;
714 }
715
716
717 /*
718 =================
719 CL_CreateNewCommands
720
721 Create a new usercmd_t structure for this frame
722 =================
723 */
CL_CreateNewCommands(void)724 void CL_CreateNewCommands( void ) {
725 int cmdNum;
726
727 // no need to create usercmds until we have a gamestate
728 if ( clc.state < CA_PRIMED ) {
729 return;
730 }
731
732 frame_msec = com_frameTime - old_com_frameTime;
733
734 // if running over 1000fps, act as if each frame is 1ms
735 // prevents divisions by zero
736 if ( frame_msec < 1 ) {
737 frame_msec = 1;
738 }
739
740 // if running less than 5fps, truncate the extra time to prevent
741 // unexpected moves after a hitch
742 if ( frame_msec > 200 ) {
743 frame_msec = 200;
744 }
745 old_com_frameTime = com_frameTime;
746
747
748 // generate a command for this frame
749 cl.cmdNumber++;
750 cmdNum = cl.cmdNumber & CMD_MASK;
751 cl.cmds[cmdNum] = CL_CreateCmd();
752 }
753
754 /*
755 =================
756 CL_ReadyToSendPacket
757
758 Returns qfalse if we are over the maxpackets limit
759 and should choke back the bandwidth a bit by not sending
760 a packet this frame. All the commands will still get
761 delivered in the next packet, but saving a header and
762 getting more delta compression will reduce total bandwidth.
763 =================
764 */
CL_ReadyToSendPacket(void)765 qboolean CL_ReadyToSendPacket( void ) {
766 int oldPacketNum;
767 int delta;
768
769 // don't send anything if playing back a demo
770 if ( clc.demoplaying || clc.state == CA_CINEMATIC ) {
771 return qfalse;
772 }
773
774 // If we are downloading, we send no less than 50ms between packets
775 if ( *clc.downloadTempName &&
776 cls.realtime - clc.lastPacketSentTime < 50 ) {
777 return qfalse;
778 }
779
780 // if we don't have a valid gamestate yet, only send
781 // one packet a second
782 if ( clc.state != CA_ACTIVE &&
783 clc.state != CA_PRIMED &&
784 !*clc.downloadTempName &&
785 cls.realtime - clc.lastPacketSentTime < 1000 ) {
786 return qfalse;
787 }
788
789 // send every frame for loopbacks
790 if ( clc.netchan.remoteAddress.type == NA_LOOPBACK ) {
791 return qtrue;
792 }
793
794 // send every frame for LAN
795 if ( cl_lanForcePackets->integer && Sys_IsLANAddress( clc.netchan.remoteAddress ) ) {
796 return qtrue;
797 }
798
799 // check for exceeding cl_maxpackets
800 if ( cl_maxpackets->integer < 25 ) {
801 Cvar_Set( "cl_maxpackets", "25" );
802 } else if ( cl_maxpackets->integer > 125 ) {
803 Cvar_Set( "cl_maxpackets", "125" );
804 }
805 oldPacketNum = ( clc.netchan.outgoingSequence - 1 ) & PACKET_MASK;
806 delta = cls.realtime - cl.outPackets[ oldPacketNum ].p_realtime;
807 if ( delta < 1000 / cl_maxpackets->integer ) {
808 // the accumulated commands will go out in the next packet
809 return qfalse;
810 }
811
812 return qtrue;
813 }
814
815 /*
816 ===================
817 CL_WritePacket
818
819 Create and send the command packet to the server
820 Including both the reliable commands and the usercmds
821
822 During normal gameplay, a client packet will contain something like:
823
824 4 sequence number
825 2 qport
826 4 serverid
827 4 acknowledged sequence number
828 4 clc.serverCommandSequence
829 <optional reliable commands>
830 1 clc_move or clc_moveNoDelta
831 1 command count
832 <count * usercmds>
833
834 ===================
835 */
CL_WritePacket(void)836 void CL_WritePacket( void ) {
837 msg_t buf;
838 byte data[MAX_MSGLEN];
839 int i, j;
840 usercmd_t *cmd, *oldcmd;
841 usercmd_t nullcmd;
842 int packetNum;
843 int oldPacketNum;
844 int count, key;
845
846 // don't send anything if playing back a demo
847 if ( clc.demoplaying || clc.state == CA_CINEMATIC ) {
848 return;
849 }
850
851 memset( &nullcmd, 0, sizeof( nullcmd ) );
852 oldcmd = &nullcmd;
853
854 MSG_Init( &buf, data, sizeof( data ) );
855
856 MSG_Bitstream( &buf );
857 // write the current serverId so the server
858 // can tell if this is from the current gameState
859 MSG_WriteLong( &buf, cl.serverId );
860
861 // write the last message we received, which can
862 // be used for delta compression, and is also used
863 // to tell if we dropped a gamestate
864 MSG_WriteLong( &buf, clc.serverMessageSequence );
865
866 // write the last reliable message we received
867 MSG_WriteLong( &buf, clc.serverCommandSequence );
868
869 // write any unacknowledged clientCommands
870 for ( i = clc.reliableAcknowledge + 1 ; i <= clc.reliableSequence ; i++ ) {
871 MSG_WriteByte( &buf, clc_clientCommand );
872 MSG_WriteLong( &buf, i );
873 MSG_WriteString( &buf, clc.reliableCommands[ i & ( MAX_RELIABLE_COMMANDS - 1 ) ] );
874 }
875
876 // we want to send all the usercmds that were generated in the last
877 // few packet, so even if a couple packets are dropped in a row,
878 // all the cmds will make it to the server
879 if ( cl_packetdup->integer < 0 ) {
880 Cvar_Set( "cl_packetdup", "0" );
881 } else if ( cl_packetdup->integer > 5 ) {
882 Cvar_Set( "cl_packetdup", "5" );
883 }
884 oldPacketNum = ( clc.netchan.outgoingSequence - 1 - cl_packetdup->integer ) & PACKET_MASK;
885 count = cl.cmdNumber - cl.outPackets[ oldPacketNum ].p_cmdNumber;
886 if ( count > MAX_PACKET_USERCMDS ) {
887 count = MAX_PACKET_USERCMDS;
888 Com_Printf( "MAX_PACKET_USERCMDS\n" );
889 }
890
891 #ifdef USE_VOIP
892 if (clc.voipOutgoingDataSize > 0)
893 {
894 if((clc.voipFlags & VOIP_SPATIAL) || Com_IsVoipTarget(clc.voipTargets, sizeof(clc.voipTargets), -1))
895 {
896 MSG_WriteByte (&buf, clc_voipOpus);
897 MSG_WriteByte (&buf, clc.voipOutgoingGeneration);
898 MSG_WriteLong (&buf, clc.voipOutgoingSequence);
899 MSG_WriteByte (&buf, clc.voipOutgoingDataFrames);
900 MSG_WriteData (&buf, clc.voipTargets, sizeof(clc.voipTargets));
901 MSG_WriteByte(&buf, clc.voipFlags);
902 MSG_WriteShort (&buf, clc.voipOutgoingDataSize);
903 MSG_WriteData (&buf, clc.voipOutgoingData, clc.voipOutgoingDataSize);
904
905 // If we're recording a demo, we have to fake a server packet with
906 // this VoIP data so it gets to disk; the server doesn't send it
907 // back to us, and we might as well eliminate concerns about dropped
908 // and misordered packets here.
909 if(clc.demorecording && !clc.demowaiting)
910 {
911 const int voipSize = clc.voipOutgoingDataSize;
912 msg_t fakemsg;
913 byte fakedata[MAX_MSGLEN];
914 MSG_Init (&fakemsg, fakedata, sizeof (fakedata));
915 MSG_Bitstream (&fakemsg);
916 MSG_WriteLong (&fakemsg, clc.reliableAcknowledge);
917 MSG_WriteByte (&fakemsg, svc_voipOpus);
918 MSG_WriteShort (&fakemsg, clc.clientNum);
919 MSG_WriteByte (&fakemsg, clc.voipOutgoingGeneration);
920 MSG_WriteLong (&fakemsg, clc.voipOutgoingSequence);
921 MSG_WriteByte (&fakemsg, clc.voipOutgoingDataFrames);
922 MSG_WriteShort (&fakemsg, clc.voipOutgoingDataSize );
923 MSG_WriteBits (&fakemsg, clc.voipFlags, VOIP_FLAGCNT);
924 MSG_WriteData (&fakemsg, clc.voipOutgoingData, voipSize);
925 MSG_WriteByte (&fakemsg, svc_EOF);
926 CL_WriteDemoMessage (&fakemsg, 0);
927 }
928
929 clc.voipOutgoingSequence += clc.voipOutgoingDataFrames;
930 clc.voipOutgoingDataSize = 0;
931 clc.voipOutgoingDataFrames = 0;
932 }
933 else
934 {
935 // We have data, but no targets. Silently discard all data
936 clc.voipOutgoingDataSize = 0;
937 clc.voipOutgoingDataFrames = 0;
938 }
939 }
940 #endif
941
942 if ( count >= 1 ) {
943 if ( cl_showSend->integer ) {
944 Com_Printf( "(%i)", count );
945 }
946
947 // begin a client move command
948 if ( cl_nodelta->integer || !cl.snap.valid || clc.demowaiting
949 || clc.serverMessageSequence != cl.snap.messageNum ) {
950 MSG_WriteByte( &buf, clc_moveNoDelta );
951 } else {
952 MSG_WriteByte( &buf, clc_move );
953 }
954
955 // write the command count
956 MSG_WriteByte( &buf, count );
957
958 // use the checksum feed in the key
959 key = clc.checksumFeed;
960 // also use the message acknowledge
961 key ^= clc.serverMessageSequence;
962 // also use the last acknowledged server command in the key
963 key ^= MSG_HashKey(clc.serverCommands[ clc.serverCommandSequence & (MAX_RELIABLE_COMMANDS-1) ], 32);
964
965 // write all the commands, including the predicted command
966 for ( i = 0 ; i < count ; i++ ) {
967 j = ( cl.cmdNumber - count + i + 1 ) & CMD_MASK;
968 cmd = &cl.cmds[j];
969 MSG_WriteDeltaUsercmdKey( &buf, key, oldcmd, cmd );
970 oldcmd = cmd;
971 }
972 }
973
974 //
975 // deliver the message
976 //
977 packetNum = clc.netchan.outgoingSequence & PACKET_MASK;
978 cl.outPackets[ packetNum ].p_realtime = cls.realtime;
979 cl.outPackets[ packetNum ].p_serverTime = oldcmd->serverTime;
980 cl.outPackets[ packetNum ].p_cmdNumber = cl.cmdNumber;
981 clc.lastPacketSentTime = cls.realtime;
982
983 if ( cl_showSend->integer ) {
984 Com_Printf( "%i ", buf.cursize );
985 }
986
987 CL_Netchan_Transmit( &clc.netchan, &buf );
988 }
989
990 /*
991 =================
992 CL_SendCmd
993
994 Called every frame to builds and sends a command packet to the server.
995 =================
996 */
CL_SendCmd(void)997 void CL_SendCmd( void ) {
998 // don't send any message if not connected
999 if ( clc.state < CA_CONNECTED ) {
1000 return;
1001 }
1002
1003 // don't send commands if paused
1004 if ( com_sv_running->integer && sv_paused->integer && cl_paused->integer ) {
1005 return;
1006 }
1007
1008 // we create commands even if a demo is playing,
1009 CL_CreateNewCommands();
1010
1011 // don't send a packet if the last packet was sent too recently
1012 if ( !CL_ReadyToSendPacket() ) {
1013 if ( cl_showSend->integer ) {
1014 Com_Printf( ". " );
1015 }
1016 return;
1017 }
1018
1019 CL_WritePacket();
1020 }
1021
1022 /*
1023 ============
1024 CL_InitInput
1025 ============
1026 */
CL_InitInput(void)1027 void CL_InitInput( void ) {
1028 Cmd_AddCommand( "centerview",IN_CenterView );
1029
1030 Cmd_AddCommand( "+moveup",IN_UpDown );
1031 Cmd_AddCommand( "-moveup",IN_UpUp );
1032 Cmd_AddCommand( "+movedown",IN_DownDown );
1033 Cmd_AddCommand( "-movedown",IN_DownUp );
1034 Cmd_AddCommand( "+left",IN_LeftDown );
1035 Cmd_AddCommand( "-left",IN_LeftUp );
1036 Cmd_AddCommand( "+right",IN_RightDown );
1037 Cmd_AddCommand( "-right",IN_RightUp );
1038 Cmd_AddCommand( "+forward",IN_ForwardDown );
1039 Cmd_AddCommand( "-forward",IN_ForwardUp );
1040 Cmd_AddCommand( "+back",IN_BackDown );
1041 Cmd_AddCommand( "-back",IN_BackUp );
1042 Cmd_AddCommand( "+lookup", IN_LookupDown );
1043 Cmd_AddCommand( "-lookup", IN_LookupUp );
1044 Cmd_AddCommand( "+lookdown", IN_LookdownDown );
1045 Cmd_AddCommand( "-lookdown", IN_LookdownUp );
1046 Cmd_AddCommand( "+strafe", IN_StrafeDown );
1047 Cmd_AddCommand( "-strafe", IN_StrafeUp );
1048 Cmd_AddCommand( "+moveleft", IN_MoveleftDown );
1049 Cmd_AddCommand( "-moveleft", IN_MoveleftUp );
1050 Cmd_AddCommand( "+moveright", IN_MoverightDown );
1051 Cmd_AddCommand( "-moveright", IN_MoverightUp );
1052 Cmd_AddCommand( "+speed", IN_SpeedDown );
1053 Cmd_AddCommand( "-speed", IN_SpeedUp );
1054
1055 Cmd_AddCommand( "+attack", IN_Button0Down ); // ---- id (primary firing)
1056 Cmd_AddCommand( "-attack", IN_Button0Up );
1057
1058 Cmd_AddCommand( "+button1", IN_Button1Down );
1059 Cmd_AddCommand( "-button1", IN_Button1Up );
1060
1061 Cmd_AddCommand( "+useitem", IN_UseItemDown );
1062 Cmd_AddCommand( "-useitem", IN_UseItemUp );
1063
1064 Cmd_AddCommand( "+salute", IN_Button3Down ); //----(SA) salute
1065 Cmd_AddCommand( "-salute", IN_Button3Up );
1066
1067 Cmd_AddCommand( "+button4", IN_Button4Down );
1068 Cmd_AddCommand( "-button4", IN_Button4Up );
1069
1070 // Rafael Activate
1071 Cmd_AddCommand( "+activate", IN_ActivateDown );
1072 Cmd_AddCommand( "-activate", IN_ActivateUp );
1073 // done.
1074
1075 // Rafael Kick
1076 Cmd_AddCommand( "+kick", IN_KickDown );
1077 Cmd_AddCommand( "-kick", IN_KickUp );
1078 // done
1079
1080 Cmd_AddCommand( "+sprint", IN_SprintDown );
1081 Cmd_AddCommand( "-sprint", IN_SprintUp );
1082
1083
1084 // wolf buttons
1085 Cmd_AddCommand( "+attack2", IN_Wbutton0Down ); //----(SA) secondary firing
1086 Cmd_AddCommand( "-attack2", IN_Wbutton0Up );
1087 Cmd_AddCommand( "+zoom", IN_ZoomDown ); //
1088 Cmd_AddCommand( "-zoom", IN_ZoomUp );
1089 Cmd_AddCommand( "+quickgren", IN_QuickGrenDown ); //
1090 Cmd_AddCommand( "-quickgren", IN_QuickGrenUp );
1091 Cmd_AddCommand( "+reload", IN_ReloadDown ); //
1092 Cmd_AddCommand( "-reload", IN_ReloadUp );
1093 Cmd_AddCommand( "+leanleft", IN_LeanLeftDown );
1094 Cmd_AddCommand( "-leanleft", IN_LeanLeftUp );
1095 Cmd_AddCommand( "+leanright", IN_LeanRightDown );
1096 Cmd_AddCommand( "-leanright", IN_LeanRightUp );
1097 // JPW NERVE multiplayer buttons
1098 Cmd_AddCommand( "+dropweapon", IN_MP_DropWeaponDown ); // JPW NERVE drop two-handed weapon
1099 Cmd_AddCommand( "-dropweapon", IN_MP_DropWeaponUp );
1100 // jpw
1101 Cmd_AddCommand( "+wbutton7", IN_Wbutton7Down ); //
1102 Cmd_AddCommand( "-wbutton7", IN_Wbutton7Up );
1103 //----(SA) end
1104
1105 Cmd_AddCommand( "+mlook", IN_MLookDown );
1106 Cmd_AddCommand( "-mlook", IN_MLookUp );
1107
1108 #ifdef USE_VOIP
1109 Cmd_AddCommand( "+voiprecord", IN_VoipRecordDown );
1110 Cmd_AddCommand( "-voiprecord", IN_VoipRecordUp );
1111 #endif
1112
1113 // Cmd_AddCommand( "notebook", IN_Notebook );
1114 Cmd_AddCommand( "help",IN_Help );
1115
1116 cl_nodelta = Cvar_Get( "cl_nodelta", "0", 0 );
1117 cl_debugMove = Cvar_Get( "cl_debugMove", "0", 0 );
1118 }
1119
1120 /*
1121 ============
1122 CL_ShutdownInput
1123 ============
1124 */
CL_ShutdownInput(void)1125 void CL_ShutdownInput(void)
1126 {
1127 Cmd_RemoveCommand("centerview");
1128
1129 Cmd_RemoveCommand("+moveup");
1130 Cmd_RemoveCommand("-moveup");
1131 Cmd_RemoveCommand("+movedown");
1132 Cmd_RemoveCommand("-movedown");
1133 Cmd_RemoveCommand("+left");
1134 Cmd_RemoveCommand("-left");
1135 Cmd_RemoveCommand("+right");
1136 Cmd_RemoveCommand("-right");
1137 Cmd_RemoveCommand("+forward");
1138 Cmd_RemoveCommand("-forward");
1139 Cmd_RemoveCommand("+back");
1140 Cmd_RemoveCommand("-back");
1141 Cmd_RemoveCommand("+lookup");
1142 Cmd_RemoveCommand("-lookup");
1143 Cmd_RemoveCommand("+lookdown");
1144 Cmd_RemoveCommand("-lookdown");
1145 Cmd_RemoveCommand("+strafe");
1146 Cmd_RemoveCommand("-strafe");
1147 Cmd_RemoveCommand("+moveleft");
1148 Cmd_RemoveCommand("-moveleft");
1149 Cmd_RemoveCommand("+moveright");
1150 Cmd_RemoveCommand("-moveright");
1151 Cmd_RemoveCommand("+speed");
1152 Cmd_RemoveCommand("-speed");
1153
1154 Cmd_RemoveCommand("+attack");
1155 Cmd_RemoveCommand("-attack");
1156
1157 Cmd_RemoveCommand("+button1");
1158 Cmd_RemoveCommand("-button1");
1159
1160 Cmd_RemoveCommand("+useitem");
1161 Cmd_RemoveCommand("-useitem");
1162
1163 Cmd_RemoveCommand("+salute");
1164 Cmd_RemoveCommand("-salute");
1165
1166 Cmd_RemoveCommand("+button4");
1167 Cmd_RemoveCommand("-button4");
1168
1169 Cmd_RemoveCommand("+activate");
1170 Cmd_RemoveCommand("-activate");
1171
1172 Cmd_RemoveCommand("+kick");
1173 Cmd_RemoveCommand("-kick");
1174
1175 Cmd_RemoveCommand("+sprint");
1176 Cmd_RemoveCommand("-sprint");
1177
1178 Cmd_RemoveCommand("+attack2");
1179 Cmd_RemoveCommand("-attack2");
1180 Cmd_RemoveCommand("+zoom");
1181 Cmd_RemoveCommand("-zoom");
1182 Cmd_RemoveCommand("+quickgren");
1183 Cmd_RemoveCommand("-quickgren");
1184 Cmd_RemoveCommand("+reload");
1185 Cmd_RemoveCommand("-reload");
1186 Cmd_RemoveCommand("+leanleft");
1187 Cmd_RemoveCommand("-leanleft");
1188 Cmd_RemoveCommand("+leanright");
1189 Cmd_RemoveCommand("-leanright");
1190 Cmd_RemoveCommand("+dropweapon");
1191 Cmd_RemoveCommand("-dropweapon");
1192 Cmd_RemoveCommand("+wbutton7");
1193 Cmd_RemoveCommand("-wbutton7");
1194
1195 Cmd_RemoveCommand("+mlook");
1196 Cmd_RemoveCommand("-mlook");
1197
1198 #ifdef USE_VOIP
1199 Cmd_RemoveCommand("+voiprecord");
1200 Cmd_RemoveCommand("-voiprecord");
1201 #endif
1202
1203 Cmd_RemoveCommand("help");
1204 }
1205
1206 /*
1207 ============
1208 CL_ClearKeys
1209 ============
1210 */
CL_ClearKeys(void)1211 void CL_ClearKeys( void ) {
1212 memset( kb, 0, sizeof( kb ) );
1213 }
1214