cg_consolecmds.c (14545B)
1 /* 2 =========================================================================== 3 Copyright (C) 1999-2005 Id Software, Inc. 4 5 This file is part of Quake III Arena source code. 6 7 Quake III Arena source code is free software; you can redistribute it 8 and/or modify it under the terms of the GNU General Public License as 9 published by the Free Software Foundation; either version 2 of the License, 10 or (at your option) any later version. 11 12 Quake III Arena source code is distributed in the hope that it will be 13 useful, but WITHOUT ANY WARRANTY; without even the implied warranty of 14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 15 GNU General Public License for more details. 16 17 You should have received a copy of the GNU General Public License 18 along with Foobar; if not, write to the Free Software 19 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA 20 =========================================================================== 21 */ 22 // 23 // cg_consolecmds.c -- text commands typed in at the local console, or 24 // executed by a key binding 25 26 #include "cg_local.h" 27 #include "../ui/ui_shared.h" 28 #ifdef MISSIONPACK 29 extern menuDef_t *menuScoreboard; 30 #endif 31 32 33 34 void CG_TargetCommand_f( void ) { 35 int targetNum; 36 char test[4]; 37 38 targetNum = CG_CrosshairPlayer(); 39 if (!targetNum ) { 40 return; 41 } 42 43 trap_Argv( 1, test, 4 ); 44 trap_SendConsoleCommand( va( "gc %i %i", targetNum, atoi( test ) ) ); 45 } 46 47 48 49 /* 50 ================= 51 CG_SizeUp_f 52 53 Keybinding command 54 ================= 55 */ 56 static void CG_SizeUp_f (void) { 57 trap_Cvar_Set("cg_viewsize", va("%i",(int)(cg_viewsize.integer+10))); 58 } 59 60 61 /* 62 ================= 63 CG_SizeDown_f 64 65 Keybinding command 66 ================= 67 */ 68 static void CG_SizeDown_f (void) { 69 trap_Cvar_Set("cg_viewsize", va("%i",(int)(cg_viewsize.integer-10))); 70 } 71 72 73 /* 74 ============= 75 CG_Viewpos_f 76 77 Debugging command to print the current position 78 ============= 79 */ 80 static void CG_Viewpos_f (void) { 81 CG_Printf ("(%i %i %i) : %i\n", (int)cg.refdef.vieworg[0], 82 (int)cg.refdef.vieworg[1], (int)cg.refdef.vieworg[2], 83 (int)cg.refdefViewAngles[YAW]); 84 } 85 86 87 static void CG_ScoresDown_f( void ) { 88 89 #ifdef MISSIONPACK 90 CG_BuildSpectatorString(); 91 #endif 92 if ( cg.scoresRequestTime + 2000 < cg.time ) { 93 // the scores are more than two seconds out of data, 94 // so request new ones 95 cg.scoresRequestTime = cg.time; 96 trap_SendClientCommand( "score" ); 97 98 // leave the current scores up if they were already 99 // displayed, but if this is the first hit, clear them out 100 if ( !cg.showScores ) { 101 cg.showScores = qtrue; 102 cg.numScores = 0; 103 } 104 } else { 105 // show the cached contents even if they just pressed if it 106 // is within two seconds 107 cg.showScores = qtrue; 108 } 109 } 110 111 static void CG_ScoresUp_f( void ) { 112 if ( cg.showScores ) { 113 cg.showScores = qfalse; 114 cg.scoreFadeTime = cg.time; 115 } 116 } 117 118 #ifdef MISSIONPACK 119 extern menuDef_t *menuScoreboard; 120 void Menu_Reset(); // FIXME: add to right include file 121 122 static void CG_LoadHud_f( void) { 123 char buff[1024]; 124 const char *hudSet; 125 memset(buff, 0, sizeof(buff)); 126 127 String_Init(); 128 Menu_Reset(); 129 130 trap_Cvar_VariableStringBuffer("cg_hudFiles", buff, sizeof(buff)); 131 hudSet = buff; 132 if (hudSet[0] == '\0') { 133 hudSet = "ui/hud.txt"; 134 } 135 136 CG_LoadMenus(hudSet); 137 menuScoreboard = NULL; 138 } 139 140 141 static void CG_scrollScoresDown_f( void) { 142 if (menuScoreboard && cg.scoreBoardShowing) { 143 Menu_ScrollFeeder(menuScoreboard, FEEDER_SCOREBOARD, qtrue); 144 Menu_ScrollFeeder(menuScoreboard, FEEDER_REDTEAM_LIST, qtrue); 145 Menu_ScrollFeeder(menuScoreboard, FEEDER_BLUETEAM_LIST, qtrue); 146 } 147 } 148 149 150 static void CG_scrollScoresUp_f( void) { 151 if (menuScoreboard && cg.scoreBoardShowing) { 152 Menu_ScrollFeeder(menuScoreboard, FEEDER_SCOREBOARD, qfalse); 153 Menu_ScrollFeeder(menuScoreboard, FEEDER_REDTEAM_LIST, qfalse); 154 Menu_ScrollFeeder(menuScoreboard, FEEDER_BLUETEAM_LIST, qfalse); 155 } 156 } 157 158 159 static void CG_spWin_f( void) { 160 trap_Cvar_Set("cg_cameraOrbit", "2"); 161 trap_Cvar_Set("cg_cameraOrbitDelay", "35"); 162 trap_Cvar_Set("cg_thirdPerson", "1"); 163 trap_Cvar_Set("cg_thirdPersonAngle", "0"); 164 trap_Cvar_Set("cg_thirdPersonRange", "100"); 165 CG_AddBufferedSound(cgs.media.winnerSound); 166 //trap_S_StartLocalSound(cgs.media.winnerSound, CHAN_ANNOUNCER); 167 CG_CenterPrint("YOU WIN!", SCREEN_HEIGHT * .30, 0); 168 } 169 170 static void CG_spLose_f( void) { 171 trap_Cvar_Set("cg_cameraOrbit", "2"); 172 trap_Cvar_Set("cg_cameraOrbitDelay", "35"); 173 trap_Cvar_Set("cg_thirdPerson", "1"); 174 trap_Cvar_Set("cg_thirdPersonAngle", "0"); 175 trap_Cvar_Set("cg_thirdPersonRange", "100"); 176 CG_AddBufferedSound(cgs.media.loserSound); 177 //trap_S_StartLocalSound(cgs.media.loserSound, CHAN_ANNOUNCER); 178 CG_CenterPrint("YOU LOSE...", SCREEN_HEIGHT * .30, 0); 179 } 180 181 #endif 182 183 static void CG_TellTarget_f( void ) { 184 int clientNum; 185 char command[128]; 186 char message[128]; 187 188 clientNum = CG_CrosshairPlayer(); 189 if ( clientNum == -1 ) { 190 return; 191 } 192 193 trap_Args( message, 128 ); 194 Com_sprintf( command, 128, "tell %i %s", clientNum, message ); 195 trap_SendClientCommand( command ); 196 } 197 198 static void CG_TellAttacker_f( void ) { 199 int clientNum; 200 char command[128]; 201 char message[128]; 202 203 clientNum = CG_LastAttacker(); 204 if ( clientNum == -1 ) { 205 return; 206 } 207 208 trap_Args( message, 128 ); 209 Com_sprintf( command, 128, "tell %i %s", clientNum, message ); 210 trap_SendClientCommand( command ); 211 } 212 213 static void CG_VoiceTellTarget_f( void ) { 214 int clientNum; 215 char command[128]; 216 char message[128]; 217 218 clientNum = CG_CrosshairPlayer(); 219 if ( clientNum == -1 ) { 220 return; 221 } 222 223 trap_Args( message, 128 ); 224 Com_sprintf( command, 128, "vtell %i %s", clientNum, message ); 225 trap_SendClientCommand( command ); 226 } 227 228 static void CG_VoiceTellAttacker_f( void ) { 229 int clientNum; 230 char command[128]; 231 char message[128]; 232 233 clientNum = CG_LastAttacker(); 234 if ( clientNum == -1 ) { 235 return; 236 } 237 238 trap_Args( message, 128 ); 239 Com_sprintf( command, 128, "vtell %i %s", clientNum, message ); 240 trap_SendClientCommand( command ); 241 } 242 243 #ifdef MISSIONPACK 244 static void CG_NextTeamMember_f( void ) { 245 CG_SelectNextPlayer(); 246 } 247 248 static void CG_PrevTeamMember_f( void ) { 249 CG_SelectPrevPlayer(); 250 } 251 252 // ASS U ME's enumeration order as far as task specific orders, OFFENSE is zero, CAMP is last 253 // 254 static void CG_NextOrder_f( void ) { 255 clientInfo_t *ci = cgs.clientinfo + cg.snap->ps.clientNum; 256 if (ci) { 257 if (!ci->teamLeader && sortedTeamPlayers[cg_currentSelectedPlayer.integer] != cg.snap->ps.clientNum) { 258 return; 259 } 260 } 261 if (cgs.currentOrder < TEAMTASK_CAMP) { 262 cgs.currentOrder++; 263 264 if (cgs.currentOrder == TEAMTASK_RETRIEVE) { 265 if (!CG_OtherTeamHasFlag()) { 266 cgs.currentOrder++; 267 } 268 } 269 270 if (cgs.currentOrder == TEAMTASK_ESCORT) { 271 if (!CG_YourTeamHasFlag()) { 272 cgs.currentOrder++; 273 } 274 } 275 276 } else { 277 cgs.currentOrder = TEAMTASK_OFFENSE; 278 } 279 cgs.orderPending = qtrue; 280 cgs.orderTime = cg.time + 3000; 281 } 282 283 284 static void CG_ConfirmOrder_f (void ) { 285 trap_SendConsoleCommand(va("cmd vtell %d %s\n", cgs.acceptLeader, VOICECHAT_YES)); 286 trap_SendConsoleCommand("+button5; wait; -button5"); 287 if (cg.time < cgs.acceptOrderTime) { 288 trap_SendClientCommand(va("teamtask %d\n", cgs.acceptTask)); 289 cgs.acceptOrderTime = 0; 290 } 291 } 292 293 static void CG_DenyOrder_f (void ) { 294 trap_SendConsoleCommand(va("cmd vtell %d %s\n", cgs.acceptLeader, VOICECHAT_NO)); 295 trap_SendConsoleCommand("+button6; wait; -button6"); 296 if (cg.time < cgs.acceptOrderTime) { 297 cgs.acceptOrderTime = 0; 298 } 299 } 300 301 static void CG_TaskOffense_f (void ) { 302 if (cgs.gametype == GT_CTF || cgs.gametype == GT_1FCTF) { 303 trap_SendConsoleCommand(va("cmd vsay_team %s\n", VOICECHAT_ONGETFLAG)); 304 } else { 305 trap_SendConsoleCommand(va("cmd vsay_team %s\n", VOICECHAT_ONOFFENSE)); 306 } 307 trap_SendClientCommand(va("teamtask %d\n", TEAMTASK_OFFENSE)); 308 } 309 310 static void CG_TaskDefense_f (void ) { 311 trap_SendConsoleCommand(va("cmd vsay_team %s\n", VOICECHAT_ONDEFENSE)); 312 trap_SendClientCommand(va("teamtask %d\n", TEAMTASK_DEFENSE)); 313 } 314 315 static void CG_TaskPatrol_f (void ) { 316 trap_SendConsoleCommand(va("cmd vsay_team %s\n", VOICECHAT_ONPATROL)); 317 trap_SendClientCommand(va("teamtask %d\n", TEAMTASK_PATROL)); 318 } 319 320 static void CG_TaskCamp_f (void ) { 321 trap_SendConsoleCommand(va("cmd vsay_team %s\n", VOICECHAT_ONCAMPING)); 322 trap_SendClientCommand(va("teamtask %d\n", TEAMTASK_CAMP)); 323 } 324 325 static void CG_TaskFollow_f (void ) { 326 trap_SendConsoleCommand(va("cmd vsay_team %s\n", VOICECHAT_ONFOLLOW)); 327 trap_SendClientCommand(va("teamtask %d\n", TEAMTASK_FOLLOW)); 328 } 329 330 static void CG_TaskRetrieve_f (void ) { 331 trap_SendConsoleCommand(va("cmd vsay_team %s\n", VOICECHAT_ONRETURNFLAG)); 332 trap_SendClientCommand(va("teamtask %d\n", TEAMTASK_RETRIEVE)); 333 } 334 335 static void CG_TaskEscort_f (void ) { 336 trap_SendConsoleCommand(va("cmd vsay_team %s\n", VOICECHAT_ONFOLLOWCARRIER)); 337 trap_SendClientCommand(va("teamtask %d\n", TEAMTASK_ESCORT)); 338 } 339 340 static void CG_TaskOwnFlag_f (void ) { 341 trap_SendConsoleCommand(va("cmd vsay_team %s\n", VOICECHAT_IHAVEFLAG)); 342 } 343 344 static void CG_TauntKillInsult_f (void ) { 345 trap_SendConsoleCommand("cmd vsay kill_insult\n"); 346 } 347 348 static void CG_TauntPraise_f (void ) { 349 trap_SendConsoleCommand("cmd vsay praise\n"); 350 } 351 352 static void CG_TauntTaunt_f (void ) { 353 trap_SendConsoleCommand("cmd vtaunt\n"); 354 } 355 356 static void CG_TauntDeathInsult_f (void ) { 357 trap_SendConsoleCommand("cmd vsay death_insult\n"); 358 } 359 360 static void CG_TauntGauntlet_f (void ) { 361 trap_SendConsoleCommand("cmd vsay kill_guantlet\n"); 362 } 363 364 static void CG_TaskSuicide_f (void ) { 365 int clientNum; 366 char command[128]; 367 368 clientNum = CG_CrosshairPlayer(); 369 if ( clientNum == -1 ) { 370 return; 371 } 372 373 Com_sprintf( command, 128, "tell %i suicide", clientNum ); 374 trap_SendClientCommand( command ); 375 } 376 377 378 379 /* 380 ================== 381 CG_TeamMenu_f 382 ================== 383 */ 384 /* 385 static void CG_TeamMenu_f( void ) { 386 if (trap_Key_GetCatcher() & KEYCATCH_CGAME) { 387 CG_EventHandling(CGAME_EVENT_NONE); 388 trap_Key_SetCatcher(0); 389 } else { 390 CG_EventHandling(CGAME_EVENT_TEAMMENU); 391 //trap_Key_SetCatcher(KEYCATCH_CGAME); 392 } 393 } 394 */ 395 396 /* 397 ================== 398 CG_EditHud_f 399 ================== 400 */ 401 /* 402 static void CG_EditHud_f( void ) { 403 //cls.keyCatchers ^= KEYCATCH_CGAME; 404 //VM_Call (cgvm, CG_EVENT_HANDLING, (cls.keyCatchers & KEYCATCH_CGAME) ? CGAME_EVENT_EDITHUD : CGAME_EVENT_NONE); 405 } 406 */ 407 408 #endif 409 410 /* 411 ================== 412 CG_StartOrbit_f 413 ================== 414 */ 415 416 static void CG_StartOrbit_f( void ) { 417 char var[MAX_TOKEN_CHARS]; 418 419 trap_Cvar_VariableStringBuffer( "developer", var, sizeof( var ) ); 420 if ( !atoi(var) ) { 421 return; 422 } 423 if (cg_cameraOrbit.value != 0) { 424 trap_Cvar_Set ("cg_cameraOrbit", "0"); 425 trap_Cvar_Set("cg_thirdPerson", "0"); 426 } else { 427 trap_Cvar_Set("cg_cameraOrbit", "5"); 428 trap_Cvar_Set("cg_thirdPerson", "1"); 429 trap_Cvar_Set("cg_thirdPersonAngle", "0"); 430 trap_Cvar_Set("cg_thirdPersonRange", "100"); 431 } 432 } 433 434 /* 435 static void CG_Camera_f( void ) { 436 char name[1024]; 437 trap_Argv( 1, name, sizeof(name)); 438 if (trap_loadCamera(name)) { 439 cg.cameraMode = qtrue; 440 trap_startCamera(cg.time); 441 } else { 442 CG_Printf ("Unable to load camera %s\n",name); 443 } 444 } 445 */ 446 447 448 typedef struct { 449 char *cmd; 450 void (*function)(void); 451 } consoleCommand_t; 452 453 static consoleCommand_t commands[] = { 454 { "testgun", CG_TestGun_f }, 455 { "testmodel", CG_TestModel_f }, 456 { "nextframe", CG_TestModelNextFrame_f }, 457 { "prevframe", CG_TestModelPrevFrame_f }, 458 { "nextskin", CG_TestModelNextSkin_f }, 459 { "prevskin", CG_TestModelPrevSkin_f }, 460 { "viewpos", CG_Viewpos_f }, 461 { "+scores", CG_ScoresDown_f }, 462 { "-scores", CG_ScoresUp_f }, 463 { "+zoom", CG_ZoomDown_f }, 464 { "-zoom", CG_ZoomUp_f }, 465 { "sizeup", CG_SizeUp_f }, 466 { "sizedown", CG_SizeDown_f }, 467 { "weapnext", CG_NextWeapon_f }, 468 { "weapprev", CG_PrevWeapon_f }, 469 { "weapon", CG_Weapon_f }, 470 { "tell_target", CG_TellTarget_f }, 471 { "tell_attacker", CG_TellAttacker_f }, 472 { "vtell_target", CG_VoiceTellTarget_f }, 473 { "vtell_attacker", CG_VoiceTellAttacker_f }, 474 { "tcmd", CG_TargetCommand_f }, 475 #ifdef MISSIONPACK 476 { "loadhud", CG_LoadHud_f }, 477 { "nextTeamMember", CG_NextTeamMember_f }, 478 { "prevTeamMember", CG_PrevTeamMember_f }, 479 { "nextOrder", CG_NextOrder_f }, 480 { "confirmOrder", CG_ConfirmOrder_f }, 481 { "denyOrder", CG_DenyOrder_f }, 482 { "taskOffense", CG_TaskOffense_f }, 483 { "taskDefense", CG_TaskDefense_f }, 484 { "taskPatrol", CG_TaskPatrol_f }, 485 { "taskCamp", CG_TaskCamp_f }, 486 { "taskFollow", CG_TaskFollow_f }, 487 { "taskRetrieve", CG_TaskRetrieve_f }, 488 { "taskEscort", CG_TaskEscort_f }, 489 { "taskSuicide", CG_TaskSuicide_f }, 490 { "taskOwnFlag", CG_TaskOwnFlag_f }, 491 { "tauntKillInsult", CG_TauntKillInsult_f }, 492 { "tauntPraise", CG_TauntPraise_f }, 493 { "tauntTaunt", CG_TauntTaunt_f }, 494 { "tauntDeathInsult", CG_TauntDeathInsult_f }, 495 { "tauntGauntlet", CG_TauntGauntlet_f }, 496 { "spWin", CG_spWin_f }, 497 { "spLose", CG_spLose_f }, 498 { "scoresDown", CG_scrollScoresDown_f }, 499 { "scoresUp", CG_scrollScoresUp_f }, 500 #endif 501 { "startOrbit", CG_StartOrbit_f }, 502 //{ "camera", CG_Camera_f }, 503 { "loaddeferred", CG_LoadDeferredPlayers } 504 }; 505 506 507 /* 508 ================= 509 CG_ConsoleCommand 510 511 The string has been tokenized and can be retrieved with 512 Cmd_Argc() / Cmd_Argv() 513 ================= 514 */ 515 qboolean CG_ConsoleCommand( void ) { 516 const char *cmd; 517 int i; 518 519 cmd = CG_Argv(0); 520 521 for ( i = 0 ; i < sizeof( commands ) / sizeof( commands[0] ) ; i++ ) { 522 if ( !Q_stricmp( cmd, commands[i].cmd ) ) { 523 commands[i].function(); 524 return qtrue; 525 } 526 } 527 528 return qfalse; 529 } 530 531 532 /* 533 ================= 534 CG_InitConsoleCommands 535 536 Let the client system know about all of our commands 537 so it can perform tab completion 538 ================= 539 */ 540 void CG_InitConsoleCommands( void ) { 541 int i; 542 543 for ( i = 0 ; i < sizeof( commands ) / sizeof( commands[0] ) ; i++ ) { 544 trap_AddCommand( commands[i].cmd ); 545 } 546 547 // 548 // the game server will interpret these commands, which will be automatically 549 // forwarded to the server after they are not recognized locally 550 // 551 trap_AddCommand ("kill"); 552 trap_AddCommand ("say"); 553 trap_AddCommand ("say_team"); 554 trap_AddCommand ("tell"); 555 trap_AddCommand ("vsay"); 556 trap_AddCommand ("vsay_team"); 557 trap_AddCommand ("vtell"); 558 trap_AddCommand ("vtaunt"); 559 trap_AddCommand ("vosay"); 560 trap_AddCommand ("vosay_team"); 561 trap_AddCommand ("votell"); 562 trap_AddCommand ("give"); 563 trap_AddCommand ("god"); 564 trap_AddCommand ("notarget"); 565 trap_AddCommand ("noclip"); 566 trap_AddCommand ("team"); 567 trap_AddCommand ("follow"); 568 trap_AddCommand ("levelshot"); 569 trap_AddCommand ("addbot"); 570 trap_AddCommand ("setviewpos"); 571 trap_AddCommand ("callvote"); 572 trap_AddCommand ("vote"); 573 trap_AddCommand ("callteamvote"); 574 trap_AddCommand ("teamvote"); 575 trap_AddCommand ("stats"); 576 trap_AddCommand ("teamtask"); 577 trap_AddCommand ("loaddefered"); // spelled wrong, but not changing for demo 578 }