00001
00002 #include "q_shared.h"
00003 #include "bg_public.h"
00004 #include "bg_local.h"
00005 #include "w_saber.h"
00006
00007 extern stringID_table_t animTable [MAX_ANIMATIONS+1];
00008
00009
00010 #include "../namespace_begin.h"
00011 extern int trap_FS_FOpenFile( const char *qpath, fileHandle_t *f, fsMode_t mode );
00012 extern void trap_FS_Read( void *buffer, int len, fileHandle_t f );
00013 extern void trap_FS_Write( const void *buffer, int len, fileHandle_t f );
00014 extern void trap_FS_FCloseFile( fileHandle_t f );
00015 extern int trap_FS_GetFileList( const char *path, const char *extension, char *listbuf, int bufsize );
00016 extern qhandle_t trap_R_RegisterSkin( const char *name );
00017 #include "../namespace_end.h"
00018
00019
00020 #ifdef QAGAME
00021 extern int G_SoundIndex( const char *name );
00022 #elif defined CGAME
00023 #include "../namespace_begin.h"
00024 sfxHandle_t trap_S_RegisterSound( const char *sample);
00025 qhandle_t trap_R_RegisterShader( const char *name );
00026 int trap_FX_RegisterEffect(const char *file);
00027 #include "../namespace_end.h"
00028 #endif
00029
00030 #include "../namespace_begin.h"
00031
00032 int BG_SoundIndex(char *sound)
00033 {
00034 #ifdef QAGAME
00035 return G_SoundIndex(sound);
00036 #elif defined CGAME
00037 return trap_S_RegisterSound(sound);
00038 #endif
00039 }
00040
00041 extern stringID_table_t FPTable[];
00042
00043 #define MAX_SABER_DATA_SIZE 0x80000
00044 static char SaberParms[MAX_SABER_DATA_SIZE];
00045
00046 stringID_table_t SaberTable[] =
00047 {
00048 ENUM2STRING(SABER_NONE),
00049 ENUM2STRING(SABER_SINGLE),
00050 ENUM2STRING(SABER_STAFF),
00051 ENUM2STRING(SABER_BROAD),
00052 ENUM2STRING(SABER_PRONG),
00053 ENUM2STRING(SABER_DAGGER),
00054 ENUM2STRING(SABER_ARC),
00055 ENUM2STRING(SABER_SAI),
00056 ENUM2STRING(SABER_CLAW),
00057 ENUM2STRING(SABER_LANCE),
00058 ENUM2STRING(SABER_STAR),
00059 ENUM2STRING(SABER_TRIDENT),
00060 "", -1
00061 };
00062
00063 stringID_table_t SaberMoveTable[] =
00064 {
00065 ENUM2STRING(LS_NONE),
00066
00067 ENUM2STRING(LS_A_TL2BR),
00068 ENUM2STRING(LS_A_L2R),
00069 ENUM2STRING(LS_A_BL2TR),
00070 ENUM2STRING(LS_A_BR2TL),
00071 ENUM2STRING(LS_A_R2L),
00072 ENUM2STRING(LS_A_TR2BL),
00073 ENUM2STRING(LS_A_T2B),
00074 ENUM2STRING(LS_A_BACKSTAB),
00075 ENUM2STRING(LS_A_BACK),
00076 ENUM2STRING(LS_A_BACK_CR),
00077 ENUM2STRING(LS_ROLL_STAB),
00078 ENUM2STRING(LS_A_LUNGE),
00079 ENUM2STRING(LS_A_JUMP_T__B_),
00080 ENUM2STRING(LS_A_FLIP_STAB),
00081 ENUM2STRING(LS_A_FLIP_SLASH),
00082 ENUM2STRING(LS_JUMPATTACK_DUAL),
00083 ENUM2STRING(LS_JUMPATTACK_ARIAL_LEFT),
00084 ENUM2STRING(LS_JUMPATTACK_ARIAL_RIGHT),
00085 ENUM2STRING(LS_JUMPATTACK_CART_LEFT),
00086 ENUM2STRING(LS_JUMPATTACK_CART_RIGHT),
00087 ENUM2STRING(LS_JUMPATTACK_STAFF_LEFT),
00088 ENUM2STRING(LS_JUMPATTACK_STAFF_RIGHT),
00089 ENUM2STRING(LS_BUTTERFLY_LEFT),
00090 ENUM2STRING(LS_BUTTERFLY_RIGHT),
00091 ENUM2STRING(LS_A_BACKFLIP_ATK),
00092 ENUM2STRING(LS_SPINATTACK_DUAL),
00093 ENUM2STRING(LS_SPINATTACK),
00094 ENUM2STRING(LS_LEAP_ATTACK),
00095 ENUM2STRING(LS_SWOOP_ATTACK_RIGHT),
00096 ENUM2STRING(LS_SWOOP_ATTACK_LEFT),
00097 ENUM2STRING(LS_TAUNTAUN_ATTACK_RIGHT),
00098 ENUM2STRING(LS_TAUNTAUN_ATTACK_LEFT),
00099 ENUM2STRING(LS_KICK_F),
00100 ENUM2STRING(LS_KICK_B),
00101 ENUM2STRING(LS_KICK_R),
00102 ENUM2STRING(LS_KICK_L),
00103 ENUM2STRING(LS_KICK_S),
00104 ENUM2STRING(LS_KICK_BF),
00105 ENUM2STRING(LS_KICK_RL),
00106 ENUM2STRING(LS_KICK_F_AIR),
00107 ENUM2STRING(LS_KICK_B_AIR),
00108 ENUM2STRING(LS_KICK_R_AIR),
00109 ENUM2STRING(LS_KICK_L_AIR),
00110 ENUM2STRING(LS_STABDOWN),
00111 ENUM2STRING(LS_STABDOWN_STAFF),
00112 ENUM2STRING(LS_STABDOWN_DUAL),
00113 ENUM2STRING(LS_DUAL_SPIN_PROTECT),
00114 ENUM2STRING(LS_STAFF_SOULCAL),
00115 ENUM2STRING(LS_A1_SPECIAL),
00116 ENUM2STRING(LS_A2_SPECIAL),
00117 ENUM2STRING(LS_A3_SPECIAL),
00118 ENUM2STRING(LS_UPSIDE_DOWN_ATTACK),
00119 ENUM2STRING(LS_PULL_ATTACK_STAB),
00120 ENUM2STRING(LS_PULL_ATTACK_SWING),
00121 ENUM2STRING(LS_SPINATTACK_ALORA),
00122 ENUM2STRING(LS_DUAL_FB),
00123 ENUM2STRING(LS_DUAL_LR),
00124 ENUM2STRING(LS_HILT_BASH),
00125 "", -1
00126 };
00127
00128
00129 qboolean BG_ParseLiteral( const char **data, const char *string )
00130 {
00131 const char *token;
00132
00133 token = COM_ParseExt( data, qtrue );
00134 if ( token[0] == 0 )
00135 {
00136 Com_Printf( "unexpected EOF\n" );
00137 return qtrue;
00138 }
00139
00140 if ( Q_stricmp( token, string ) )
00141 {
00142 Com_Printf( "required string '%s' missing\n", string );
00143 return qtrue;
00144 }
00145
00146 return qfalse;
00147 }
00148
00149 saber_colors_t TranslateSaberColor( const char *name )
00150 {
00151 if ( !Q_stricmp( name, "red" ) )
00152 {
00153 return SABER_RED;
00154 }
00155 if ( !Q_stricmp( name, "orange" ) )
00156 {
00157 return SABER_ORANGE;
00158 }
00159 if ( !Q_stricmp( name, "yellow" ) )
00160 {
00161 return SABER_YELLOW;
00162 }
00163 if ( !Q_stricmp( name, "green" ) )
00164 {
00165 return SABER_GREEN;
00166 }
00167 if ( !Q_stricmp( name, "blue" ) )
00168 {
00169 return SABER_BLUE;
00170 }
00171 if ( !Q_stricmp( name, "purple" ) )
00172 {
00173 return SABER_PURPLE;
00174 }
00175 if ( !Q_stricmp( name, "random" ) )
00176 {
00177 return ((saber_colors_t)(Q_irand( SABER_ORANGE, SABER_PURPLE )));
00178 }
00179 return SABER_BLUE;
00180 }
00181
00182 saber_styles_t TranslateSaberStyle( const char *name )
00183 {
00184 if ( !Q_stricmp( name, "fast" ) )
00185 {
00186 return SS_FAST;
00187 }
00188 if ( !Q_stricmp( name, "medium" ) )
00189 {
00190 return SS_MEDIUM;
00191 }
00192 if ( !Q_stricmp( name, "strong" ) )
00193 {
00194 return SS_STRONG;
00195 }
00196 if ( !Q_stricmp( name, "desann" ) )
00197 {
00198 return SS_DESANN;
00199 }
00200 if ( !Q_stricmp( name, "tavion" ) )
00201 {
00202 return SS_TAVION;
00203 }
00204 if ( !Q_stricmp( name, "dual" ) )
00205 {
00206 return SS_DUAL;
00207 }
00208 if ( !Q_stricmp( name, "staff" ) )
00209 {
00210 return SS_STAFF;
00211 }
00212 return SS_NONE;
00213 }
00214
00215 qboolean WP_SaberBladeUseSecondBladeStyle( saberInfo_t *saber, int bladeNum )
00216 {
00217 if ( saber )
00218 {
00219 if ( saber->bladeStyle2Start > 0 )
00220 {
00221 if ( bladeNum >= saber->bladeStyle2Start )
00222 {
00223 return qtrue;
00224 }
00225 }
00226 }
00227 return qfalse;
00228 }
00229
00230 qboolean WP_SaberBladeDoTransitionDamage( saberInfo_t *saber, int bladeNum )
00231 {
00232 if ( !WP_SaberBladeUseSecondBladeStyle( saber, bladeNum )
00233 && (saber->saberFlags2&SFL2_TRANSITION_DAMAGE) )
00234 {
00235 return qtrue;
00236 }
00237 else if ( WP_SaberBladeUseSecondBladeStyle( saber, bladeNum )
00238 && (saber->saberFlags2&SFL2_TRANSITION_DAMAGE2) )
00239 {
00240 return qtrue;
00241 }
00242 return qfalse;
00243 }
00244
00245 qboolean WP_UseFirstValidSaberStyle( saberInfo_t *saber1, saberInfo_t *saber2, int saberHolstered, int *saberAnimLevel )
00246 {
00247 qboolean styleInvalid = qfalse;
00248 qboolean saber1Active;
00249 qboolean saber2Active;
00250 qboolean dualSabers = qfalse;
00251 int validStyles = 0, styleNum;
00252
00253 if ( saber2 && saber2->model && saber2->model[0] )
00254 {
00255 dualSabers = qtrue;
00256 }
00257
00258 if ( dualSabers )
00259 {
00260 if ( saberHolstered > 1 )
00261 {
00262 saber1Active = saber2Active = qfalse;
00263 }
00264 else if ( saberHolstered > 0 )
00265 {
00266 saber1Active = qtrue;
00267 saber2Active = qfalse;
00268 }
00269 else
00270 {
00271 saber1Active = saber2Active = qtrue;
00272 }
00273 }
00274 else
00275 {
00276 saber2Active = qfalse;
00277 if ( !saber1
00278 || !saber1->model
00279 || !saber1->model[0] )
00280 {
00281 saber1Active = qfalse;
00282 }
00283 else if ( saber1->numBlades > 1 )
00284 {
00285 if ( saberHolstered > 1 )
00286 {
00287 saber1Active = qfalse;
00288 }
00289 else
00290 {
00291 saber1Active = qtrue;
00292 }
00293 }
00294 else
00295 {
00296 if ( saberHolstered )
00297 {
00298 saber1Active = qfalse;
00299 }
00300 else
00301 {
00302 saber1Active = qtrue;
00303 }
00304 }
00305 }
00306
00307
00308 for ( styleNum = SS_NONE+1; styleNum < SS_NUM_SABER_STYLES; styleNum++ )
00309 {
00310 validStyles |= (1<<styleNum);
00311 }
00312
00313 if ( saber1Active
00314 && saber1
00315 && saber1->model
00316 && saber1->model[0]
00317 && saber1->stylesForbidden )
00318 {
00319 if ( (saber1->stylesForbidden&(1<<*saberAnimLevel)) )
00320 {
00321 styleInvalid = qtrue;
00322 validStyles &= ~saber1->stylesForbidden;
00323 }
00324 }
00325 if ( dualSabers )
00326 {
00327 if ( saber2Active
00328 && saber2->stylesForbidden )
00329 {
00330 if ( (saber2->stylesForbidden&(1<<*saberAnimLevel)) )
00331 {
00332 styleInvalid = qtrue;
00333
00334 validStyles &= ~saber2->stylesForbidden;
00335 }
00336 }
00337 }
00338 if ( styleInvalid && validStyles )
00339 {
00340 int styleNum;
00341 for ( styleNum = SS_FAST; styleNum < SS_NUM_SABER_STYLES; styleNum++ )
00342 {
00343 if ( (validStyles&(1<<styleNum)) )
00344 {
00345 *saberAnimLevel = styleNum;
00346 return qtrue;
00347 }
00348 }
00349 }
00350 return qfalse;
00351 }
00352
00353 qboolean WP_SaberStyleValidForSaber( saberInfo_t *saber1, saberInfo_t *saber2, int saberHolstered, int saberAnimLevel )
00354 {
00355 qboolean saber1Active;
00356 qboolean saber2Active;
00357 qboolean dualSabers = qfalse;
00358
00359 if ( saber2 && saber2->model && saber2->model[0] )
00360 {
00361 dualSabers = qtrue;
00362 }
00363
00364 if ( dualSabers )
00365 {
00366 if ( saberHolstered > 1 )
00367 {
00368 saber1Active = saber2Active = qfalse;
00369 }
00370 else if ( saberHolstered > 0 )
00371 {
00372 saber1Active = qtrue;
00373 saber2Active = qfalse;
00374 }
00375 else
00376 {
00377 saber1Active = saber2Active = qtrue;
00378 }
00379 }
00380 else
00381 {
00382 saber2Active = qfalse;
00383 if ( !saber1
00384 || !saber1->model
00385 || !saber1->model[0] )
00386 {
00387 saber1Active = qfalse;
00388 }
00389 else if ( saber1->numBlades > 1 )
00390 {
00391 if ( saberHolstered > 1 )
00392 {
00393 saber1Active = qfalse;
00394 }
00395 else
00396 {
00397 saber1Active = qtrue;
00398 }
00399 }
00400 else
00401 {
00402 if ( saberHolstered )
00403 {
00404 saber1Active = qfalse;
00405 }
00406 else
00407 {
00408 saber1Active = qtrue;
00409 }
00410 }
00411 }
00412
00413 if ( saber1Active
00414 && saber1
00415 && saber1->model
00416 && saber1->model[0]
00417 && saber1->stylesForbidden )
00418 {
00419 if ( (saber1->stylesForbidden&(1<<saberAnimLevel)) )
00420 {
00421 return qfalse;
00422 }
00423 }
00424 if ( dualSabers
00425 && saber2Active
00426 && saber2
00427 && saber2->model
00428 && saber2->model[0] )
00429 {
00430 if ( saber2->stylesForbidden )
00431 {
00432 if ( (saber2->stylesForbidden&(1<<saberAnimLevel)) )
00433 {
00434 return qfalse;
00435 }
00436 }
00437
00438 if ( saberAnimLevel != SS_DUAL )
00439 {
00440 if ( saberAnimLevel != SS_TAVION )
00441 {
00442 return qfalse;
00443 }
00444 else
00445 {
00446 if ( saber1Active
00447 && saber1
00448 && saber1->model
00449 && saber1->model[0]
00450 && (saber1->stylesLearned&(1<<SS_TAVION)) )
00451 {
00452 }
00453 else if ( (saber2->stylesLearned&(1<<SS_TAVION)) )
00454 {
00455 }
00456 else
00457 {
00458 return qfalse;
00459 }
00460 }
00461 }
00462 }
00463 return qtrue;
00464 }
00465
00466 qboolean WP_SaberCanTurnOffSomeBlades( saberInfo_t *saber )
00467 {
00468 if ( saber->bladeStyle2Start > 0
00469 && saber->numBlades > saber->bladeStyle2Start )
00470 {
00471 if ( (saber->saberFlags2&SFL2_NO_MANUAL_DEACTIVATE)
00472 && (saber->saberFlags2&SFL2_NO_MANUAL_DEACTIVATE2) )
00473 {
00474 return qfalse;
00475 }
00476 }
00477 else
00478 {
00479 if ( (saber->saberFlags2&SFL2_NO_MANUAL_DEACTIVATE) )
00480 {
00481 return qfalse;
00482 }
00483 }
00484
00485 return qtrue;
00486 }
00487
00488 void WP_SaberSetDefaults( saberInfo_t *saber )
00489 {
00490 int i;
00491
00492
00493 for ( i = 0; i < MAX_BLADES; i++ )
00494 {
00495 saber->blade[i].color = SABER_RED;
00496 saber->blade[i].radius = SABER_RADIUS_STANDARD;
00497 saber->blade[i].lengthMax = 32;
00498 }
00499
00500 strcpy(saber->name, "default");
00501 strcpy(saber->fullName, "lightsaber");
00502 strcpy(saber->model, "models/weapons2/saber_reborn/saber_w.glm");
00503 saber->skin = 0;
00504 saber->soundOn = BG_SoundIndex( "sound/weapons/saber/enemy_saber_on.wav" );
00505 saber->soundLoop = BG_SoundIndex( "sound/weapons/saber/saberhum3.wav" );
00506 saber->soundOff = BG_SoundIndex( "sound/weapons/saber/enemy_saber_off.wav" );
00507 saber->numBlades = 1;
00508 saber->type = SABER_SINGLE;
00509 saber->stylesLearned = 0;
00510 saber->stylesForbidden = 0;
00511 saber->maxChain = 0;
00512 saber->forceRestrictions = 0;
00513 saber->lockBonus = 0;
00514 saber->parryBonus = 0;
00515 saber->breakParryBonus = 0;
00516 saber->breakParryBonus2 = 0;
00517 saber->disarmBonus = 0;
00518 saber->disarmBonus2 = 0;
00519 saber->singleBladeStyle = SS_NONE;
00520
00521
00522
00523
00524 saber->saberFlags = 0;
00525 saber->saberFlags2 = 0;
00526
00527 saber->spinSound = 0;
00528 saber->swingSound[0] = 0;
00529 saber->swingSound[1] = 0;
00530 saber->swingSound[2] = 0;
00531
00532
00533 saber->moveSpeedScale = 1.0f;
00534 saber->animSpeedScale = 1.0f;
00535
00536 saber->kataMove = LS_INVALID;
00537 saber->lungeAtkMove = LS_INVALID;
00538 saber->jumpAtkUpMove = LS_INVALID;
00539 saber->jumpAtkFwdMove = LS_INVALID;
00540 saber->jumpAtkBackMove = LS_INVALID;
00541 saber->jumpAtkRightMove = LS_INVALID;
00542 saber->jumpAtkLeftMove = LS_INVALID;
00543 saber->readyAnim = -1;
00544 saber->drawAnim = -1;
00545 saber->putawayAnim = -1;
00546 saber->tauntAnim = -1;
00547 saber->bowAnim = -1;
00548 saber->meditateAnim = -1;
00549 saber->flourishAnim = -1;
00550 saber->gloatAnim = -1;
00551
00552
00553 saber->bladeStyle2Start = 0;
00554
00555
00556
00557
00558
00559 saber->trailStyle = 0;
00560 saber->g2MarksShader = 0;
00561 saber->g2WeaponMarkShader = 0;
00562
00563
00564 saber->hitSound[0] = 0;
00565 saber->hitSound[1] = 0;
00566 saber->hitSound[2] = 0;
00567 saber->blockSound[0] = 0;
00568 saber->blockSound[1] = 0;
00569 saber->blockSound[2] = 0;
00570 saber->bounceSound[0] = 0;
00571 saber->bounceSound[1] = 0;
00572 saber->bounceSound[2] = 0;
00573 saber->blockEffect = 0;
00574 saber->hitPersonEffect = 0;
00575 saber->hitOtherEffect = 0;
00576 saber->bladeEffect = 0;
00577
00578
00579 saber->knockbackScale = 0;
00580 saber->damageScale = 1.0f;
00581 saber->splashRadius = 0.0f;
00582 saber->splashDamage = 0;
00583 saber->splashKnockback = 0.0f;
00584
00585
00586
00587 saber->trailStyle2 = 0;
00588 saber->g2MarksShader2 = 0;
00589 saber->g2WeaponMarkShader2 = 0;
00590
00591
00592 saber->hit2Sound[0] = 0;
00593 saber->hit2Sound[1] = 0;
00594 saber->hit2Sound[2] = 0;
00595 saber->block2Sound[0] = 0;
00596 saber->block2Sound[1] = 0;
00597 saber->block2Sound[2] = 0;
00598 saber->bounce2Sound[0] = 0;
00599 saber->bounce2Sound[1] = 0;
00600 saber->bounce2Sound[2] = 0;
00601 saber->blockEffect2 = 0;
00602 saber->hitPersonEffect2 = 0;
00603 saber->hitOtherEffect2 = 0;
00604 saber->bladeEffect2 = 0;
00605
00606
00607 saber->knockbackScale2 = 0;
00608 saber->damageScale2 = 1.0f;
00609 saber->splashRadius2 = 0.0f;
00610 saber->splashDamage2 = 0;
00611 saber->splashKnockback2 = 0.0f;
00612
00613 }
00614
00615 #define DEFAULT_SABER "Kyle"
00616
00617 qboolean WP_SaberParseParms( const char *SaberName, saberInfo_t *saber )
00618 {
00619 const char *token;
00620 const char *value;
00621 const char *p;
00622 char useSaber[1024];
00623 float f;
00624 int n;
00625 qboolean triedDefault = qfalse;
00626 int saberMove = LS_INVALID;
00627 int anim = -1;
00628
00629 if ( !saber )
00630 {
00631 return qfalse;
00632 }
00633
00634
00635 WP_SaberSetDefaults( saber );
00636
00637 if ( !SaberName || !SaberName[0] )
00638 {
00639 strcpy(useSaber, DEFAULT_SABER);
00640 triedDefault = qtrue;
00641 }
00642 else
00643 {
00644 strcpy(useSaber, SaberName);
00645 }
00646
00647
00648 p = SaberParms;
00649 COM_BeginParseSession("saberinfo");
00650
00651
00652 while ( p )
00653 {
00654 token = COM_ParseExt( &p, qtrue );
00655 if ( token[0] == 0 )
00656 {
00657 if (!triedDefault)
00658 {
00659 p = SaberParms;
00660 COM_BeginParseSession("saberinfo");
00661 strcpy(useSaber, DEFAULT_SABER);
00662 triedDefault = qtrue;
00663 }
00664 else
00665 {
00666 return qfalse;
00667 }
00668 }
00669
00670 if ( !Q_stricmp( token, useSaber ) )
00671 {
00672 break;
00673 }
00674
00675 SkipBracedSection( &p );
00676 }
00677 if ( !p )
00678 {
00679 return qfalse;
00680 }
00681
00682
00683 strcpy(saber->name, useSaber);
00684
00685 if ( BG_ParseLiteral( &p, "{" ) )
00686 {
00687 return qfalse;
00688 }
00689
00690
00691 while ( 1 )
00692 {
00693 token = COM_ParseExt( &p, qtrue );
00694 if ( !token[0] )
00695 {
00696 Com_Printf( S_COLOR_RED"ERROR: unexpected EOF while parsing '%s'\n", useSaber );
00697 return qfalse;
00698 }
00699
00700 if ( !Q_stricmp( token, "}" ) )
00701 {
00702 break;
00703 }
00704
00705
00706 if ( !Q_stricmp( token, "name" ) )
00707 {
00708 if ( COM_ParseString( &p, &value ) )
00709 {
00710 continue;
00711 }
00712 strcpy(saber->fullName, value);
00713 continue;
00714 }
00715
00716
00717 if ( !Q_stricmp( token, "saberType" ) )
00718 {
00719 int saberType;
00720
00721 if ( COM_ParseString( &p, &value ) )
00722 {
00723 continue;
00724 }
00725 saberType = GetIDForString( SaberTable, value );
00726 if ( saberType >= SABER_SINGLE && saberType <= NUM_SABERS )
00727 {
00728 saber->type = (saberType_t)saberType;
00729 }
00730 continue;
00731 }
00732
00733
00734 if ( !Q_stricmp( token, "saberModel" ) )
00735 {
00736 if ( COM_ParseString( &p, &value ) )
00737 {
00738 continue;
00739 }
00740 strcpy(saber->model, value);
00741 continue;
00742 }
00743
00744 if ( !Q_stricmp( token, "customSkin" ) )
00745 {
00746 if ( COM_ParseString( &p, &value ) )
00747 {
00748 continue;
00749 }
00750 saber->skin = trap_R_RegisterSkin(value);
00751 continue;
00752 }
00753
00754
00755 if ( !Q_stricmp( token, "soundOn" ) )
00756 {
00757 if ( COM_ParseString( &p, &value ) )
00758 {
00759 continue;
00760 }
00761 saber->soundOn = BG_SoundIndex( (char *)value );
00762 continue;
00763 }
00764
00765
00766 if ( !Q_stricmp( token, "soundLoop" ) )
00767 {
00768 if ( COM_ParseString( &p, &value ) )
00769 {
00770 continue;
00771 }
00772 saber->soundLoop = BG_SoundIndex( (char *)value );
00773 continue;
00774 }
00775
00776
00777 if ( !Q_stricmp( token, "soundOff" ) )
00778 {
00779 if ( COM_ParseString( &p, &value ) )
00780 {
00781 continue;
00782 }
00783 saber->soundOff = BG_SoundIndex( (char *)value );
00784 continue;
00785 }
00786
00787 if ( !Q_stricmp( token, "numBlades" ) )
00788 {
00789 if ( COM_ParseInt( &p, &n ) )
00790 {
00791 SkipRestOfLine( &p );
00792 continue;
00793 }
00794 if ( n < 1 || n > MAX_BLADES )
00795 {
00796 Com_Error(ERR_DROP, "WP_SaberParseParms: saber %s has illegal number of blades (%d) max: %d", useSaber, n, MAX_BLADES );
00797 continue;
00798 }
00799 saber->numBlades = n;
00800 continue;
00801 }
00802
00803
00804 if ( !Q_stricmpn( token, "saberColor", 10 ) )
00805 {
00806 if (strlen(token)==10)
00807 {
00808 n = -1;
00809 }
00810 else if (strlen(token)==11)
00811 {
00812 n = atoi(&token[10])-1;
00813 if (n > 7 || n < 1 )
00814 {
00815 Com_Printf( S_COLOR_YELLOW"WARNING: bad saberColor '%s' in %s\n", token, useSaber );
00816 continue;
00817 }
00818 }
00819 else
00820 {
00821 Com_Printf( S_COLOR_YELLOW"WARNING: bad saberColor '%s' in %s\n", token, useSaber );
00822 continue;
00823 }
00824
00825 if ( COM_ParseString( &p, &value ) )
00826 {
00827 continue;
00828 }
00829
00830 if (n==-1)
00831 {
00832 saber_colors_t color = TranslateSaberColor( value );
00833 for ( n = 0; n < MAX_BLADES; n++ )
00834 {
00835 saber->blade[n].color = color;
00836 }
00837 } else
00838 {
00839 saber->blade[n].color = TranslateSaberColor( value );
00840 }
00841 continue;
00842 }
00843
00844
00845 if ( !Q_stricmpn( token, "saberLength", 11 ) )
00846 {
00847 if (strlen(token)==11)
00848 {
00849 n = -1;
00850 }
00851 else if (strlen(token)==12)
00852 {
00853 n = atoi(&token[11])-1;
00854 if (n > 7 || n < 1 )
00855 {
00856 Com_Printf( S_COLOR_YELLOW"WARNING: bad saberLength '%s' in %s\n", token, useSaber );
00857 continue;
00858 }
00859 }
00860 else
00861 {
00862 Com_Printf( S_COLOR_YELLOW"WARNING: bad saberLength '%s' in %s\n", token, useSaber );
00863 continue;
00864 }
00865
00866 if ( COM_ParseFloat( &p, &f ) )
00867 {
00868 SkipRestOfLine( &p );
00869 continue;
00870 }
00871
00872 if ( f < 4.0f )
00873 {
00874 f = 4.0f;
00875 }
00876
00877 if (n==-1)
00878 {
00879 for ( n = 0; n < MAX_BLADES; n++ )
00880 {
00881 saber->blade[n].lengthMax = f;
00882 }
00883 }
00884 else
00885 {
00886 saber->blade[n].lengthMax = f;
00887 }
00888 continue;
00889 }
00890
00891
00892 if ( !Q_stricmpn( token, "saberRadius", 11 ) )
00893 {
00894 if (strlen(token)==11)
00895 {
00896 n = -1;
00897 }
00898 else if (strlen(token)==12)
00899 {
00900 n = atoi(&token[11])-1;
00901 if (n > 7 || n < 1 )
00902 {
00903 Com_Printf( S_COLOR_YELLOW"WARNING: bad saberRadius '%s' in %s\n", token, useSaber );
00904 continue;
00905 }
00906 }
00907 else
00908 {
00909 Com_Printf( S_COLOR_YELLOW"WARNING: bad saberRadius '%s' in %s\n", token, useSaber );
00910 continue;
00911 }
00912
00913 if ( COM_ParseFloat( &p, &f ) )
00914 {
00915 SkipRestOfLine( &p );
00916 continue;
00917 }
00918
00919 if ( f < 0.25f )
00920 {
00921 f = 0.25f;
00922 }
00923 if (n==-1)
00924 {
00925 for ( n = 0; n < MAX_BLADES; n++ )
00926 {
00927 saber->blade[n].radius = f;
00928 }
00929 }
00930 else
00931 {
00932 saber->blade[n].radius = f;
00933 }
00934 continue;
00935 }
00936
00937
00938 if ( !Q_stricmp( token, "saberStyle" ) )
00939 {
00940 int style, styleNum;
00941 if ( COM_ParseString( &p, &value ) )
00942 {
00943 continue;
00944 }
00945
00946 style = TranslateSaberStyle( value );
00947
00948 saber->stylesLearned = (1<<style);
00949
00950 saber->stylesForbidden = 0;
00951 for ( styleNum = SS_NONE+1; styleNum < SS_NUM_SABER_STYLES; styleNum++ )
00952 {
00953 if ( styleNum != style )
00954 {
00955 saber->stylesForbidden |= (1<<styleNum);
00956 }
00957 }
00958 continue;
00959 }
00960
00961
00962 if ( !Q_stricmp( token, "saberStyleLearned" ) )
00963 {
00964 if ( COM_ParseString( &p, &value ) )
00965 {
00966 continue;
00967 }
00968 saber->stylesLearned |= (1<<TranslateSaberStyle( value ));
00969 continue;
00970 }
00971
00972
00973 if ( !Q_stricmp( token, "saberStyleForbidden" ) )
00974 {
00975 if ( COM_ParseString( &p, &value ) )
00976 {
00977 continue;
00978 }
00979 saber->stylesForbidden |= (1<<TranslateSaberStyle( value ));
00980 continue;
00981 }
00982
00983
00984 if ( !Q_stricmp( token, "maxChain" ) )
00985 {
00986 if ( COM_ParseInt( &p, &n ) )
00987 {
00988 SkipRestOfLine( &p );
00989 continue;
00990 }
00991 saber->maxChain = n;
00992 continue;
00993 }
00994
00995
00996 if ( !Q_stricmp( token, "lockable" ) )
00997 {
00998 if ( COM_ParseInt( &p, &n ) )
00999 {
01000 SkipRestOfLine( &p );
01001 continue;
01002 }
01003 if ( n == 0 )
01004 {
01005 saber->saberFlags |= SFL_NOT_LOCKABLE;
01006 }
01007 continue;
01008 }
01009
01010
01011 if ( !Q_stricmp( token, "throwable" ) )
01012 {
01013 if ( COM_ParseInt( &p, &n ) )
01014 {
01015 SkipRestOfLine( &p );
01016 continue;
01017 }
01018 if ( n == 0 )
01019 {
01020 saber->saberFlags |= SFL_NOT_THROWABLE;
01021 }
01022 continue;
01023 }
01024
01025
01026 if ( !Q_stricmp( token, "disarmable" ) )
01027 {
01028 if ( COM_ParseInt( &p, &n ) )
01029 {
01030 SkipRestOfLine( &p );
01031 continue;
01032 }
01033 if ( n == 0 )
01034 {
01035 saber->saberFlags |= SFL_NOT_DISARMABLE;
01036 }
01037 continue;
01038 }
01039
01040
01041 if ( !Q_stricmp( token, "blocking" ) )
01042 {
01043 if ( COM_ParseInt( &p, &n ) )
01044 {
01045 SkipRestOfLine( &p );
01046 continue;
01047 }
01048 if ( n == 0 )
01049 {
01050 saber->saberFlags |= SFL_NOT_ACTIVE_BLOCKING;
01051 }
01052 continue;
01053 }
01054
01055
01056 if ( !Q_stricmp( token, "twoHanded" ) )
01057 {
01058 if ( COM_ParseInt( &p, &n ) )
01059 {
01060 SkipRestOfLine( &p );
01061 continue;
01062 }
01063 if ( n )
01064 {
01065 saber->saberFlags |= SFL_TWO_HANDED;
01066 }
01067 continue;
01068 }
01069
01070
01071 if ( !Q_stricmp( token, "forceRestrict" ) )
01072 {
01073 int fp;
01074
01075 if ( COM_ParseString( &p, &value ) )
01076 {
01077 continue;
01078 }
01079 fp = GetIDForString( FPTable, value );
01080 if ( fp >= FP_FIRST && fp < NUM_FORCE_POWERS )
01081 {
01082 saber->forceRestrictions |= (1<<fp);
01083 }
01084 continue;
01085 }
01086
01087
01088 if ( !Q_stricmp( token, "lockBonus" ) )
01089 {
01090 if ( COM_ParseInt( &p, &n ) )
01091 {
01092 SkipRestOfLine( &p );
01093 continue;
01094 }
01095 saber->lockBonus = n;
01096 continue;
01097 }
01098
01099
01100 if ( !Q_stricmp( token, "parryBonus" ) )
01101 {
01102 if ( COM_ParseInt( &p, &n ) )
01103 {
01104 SkipRestOfLine( &p );
01105 continue;
01106 }
01107 saber->parryBonus = n;
01108 continue;
01109 }
01110
01111
01112 if ( !Q_stricmp( token, "breakParryBonus" ) )
01113 {
01114 if ( COM_ParseInt( &p, &n ) )
01115 {
01116 SkipRestOfLine( &p );
01117 continue;
01118 }
01119 saber->breakParryBonus = n;
01120 continue;
01121 }
01122
01123
01124 if ( !Q_stricmp( token, "breakParryBonus2" ) )
01125 {
01126 if ( COM_ParseInt( &p, &n ) )
01127 {
01128 SkipRestOfLine( &p );
01129 continue;
01130 }
01131 saber->breakParryBonus2 = n;
01132 continue;
01133 }
01134
01135
01136 if ( !Q_stricmp( token, "disarmBonus" ) )
01137 {
01138 if ( COM_ParseInt( &p, &n ) )
01139 {
01140 SkipRestOfLine( &p );
01141 continue;
01142 }
01143 saber->disarmBonus = n;
01144 continue;
01145 }
01146
01147
01148 if ( !Q_stricmp( token, "disarmBonus2" ) )
01149 {
01150 if ( COM_ParseInt( &p, &n ) )
01151 {
01152 SkipRestOfLine( &p );
01153 continue;
01154 }
01155 saber->disarmBonus2 = n;
01156 continue;
01157 }
01158
01159
01160 if ( !Q_stricmp( token, "singleBladeStyle" ) )
01161 {
01162 if ( COM_ParseString( &p, &value ) )
01163 {
01164 continue;
01165 }
01166 saber->singleBladeStyle = TranslateSaberStyle( value );
01167 continue;
01168 }
01169
01170
01171 if ( !Q_stricmp( token, "singleBladeThrowable" ) )
01172 {
01173 if ( COM_ParseInt( &p, &n ) )
01174 {
01175 SkipRestOfLine( &p );
01176 continue;
01177 }
01178 if ( n )
01179 {
01180 saber->saberFlags |= SFL_SINGLE_BLADE_THROWABLE;
01181 }
01182 continue;
01183 }
01184
01185
01186 if ( !Q_stricmp( token, "brokenSaber1" ) )
01187 {
01188 if ( COM_ParseString( &p, &value ) )
01189 {
01190 continue;
01191 }
01192
01193 continue;
01194 }
01195
01196
01197 if ( !Q_stricmp( token, "brokenSaber2" ) )
01198 {
01199 if ( COM_ParseString( &p, &value ) )
01200 {
01201 continue;
01202 }
01203
01204 continue;
01205 }
01206
01207
01208 if ( !Q_stricmp( token, "returnDamage" ) )
01209 {
01210 if ( COM_ParseInt( &p, &n ) )
01211 {
01212 SkipRestOfLine( &p );
01213 continue;
01214 }
01215 if ( n )
01216 {
01217 saber->saberFlags |= SFL_RETURN_DAMAGE;
01218 }
01219 continue;
01220 }
01221
01222
01223 if ( !Q_stricmp( token, "spinSound" ) )
01224 {
01225 if ( COM_ParseString( &p, &value ) )
01226 {
01227 continue;
01228 }
01229 saber->spinSound = BG_SoundIndex( (char *)value );
01230 continue;
01231 }
01232
01233
01234 if ( !Q_stricmp( token, "swingSound1" ) )
01235 {
01236 if ( COM_ParseString( &p, &value ) )
01237 {
01238 continue;
01239 }
01240 saber->swingSound[0] = BG_SoundIndex( (char *)value );
01241 continue;
01242 }
01243
01244
01245 if ( !Q_stricmp( token, "swingSound2" ) )
01246 {
01247 if ( COM_ParseString( &p, &value ) )
01248 {
01249 continue;
01250 }
01251 saber->swingSound[1] = BG_SoundIndex( (char *)value );
01252 continue;
01253 }
01254
01255
01256 if ( !Q_stricmp( token, "swingSound3" ) )
01257 {
01258 if ( COM_ParseString( &p, &value ) )
01259 {
01260 continue;
01261 }
01262 saber->swingSound[2] = BG_SoundIndex( (char *)value );
01263 continue;
01264 }
01265
01266
01267 if ( !Q_stricmp( token, "moveSpeedScale" ) )
01268 {
01269 if ( COM_ParseFloat( &p, &f ) )
01270 {
01271 SkipRestOfLine( &p );
01272 continue;
01273 }
01274 saber->moveSpeedScale = f;
01275 continue;
01276 }
01277
01278
01279 if ( !Q_stricmp( token, "animSpeedScale" ) )
01280 {
01281 if ( COM_ParseFloat( &p, &f ) )
01282 {
01283 SkipRestOfLine( &p );
01284 continue;
01285 }
01286 saber->animSpeedScale = f;
01287 continue;
01288 }
01289
01290
01291 if ( !Q_stricmp( token, "bounceOnWalls" ) )
01292 {
01293 if ( COM_ParseInt( &p, &n ) )
01294 {
01295 SkipRestOfLine( &p );
01296 continue;
01297 }
01298 if ( n )
01299 {
01300 saber->saberFlags |= SFL_BOUNCE_ON_WALLS;
01301 }
01302 continue;
01303 }
01304
01305
01306 if ( !Q_stricmp( token, "boltToWrist" ) )
01307 {
01308 if ( COM_ParseInt( &p, &n ) )
01309 {
01310 SkipRestOfLine( &p );
01311 continue;
01312 }
01313 if ( n )
01314 {
01315 saber->saberFlags |= SFL_BOLT_TO_WRIST;
01316 }
01317 continue;
01318 }
01319
01320
01321 if ( !Q_stricmp( token, "kataMove" ) )
01322 {
01323 if ( COM_ParseString( &p, &value ) )
01324 {
01325 continue;
01326 }
01327 saberMove = GetIDForString( SaberMoveTable, value );
01328 if ( saberMove >= LS_INVALID && saberMove < LS_MOVE_MAX )
01329 {
01330 saber->kataMove = saberMove;
01331 }
01332 continue;
01333 }
01334
01335 if ( !Q_stricmp( token, "lungeAtkMove" ) )
01336 {
01337 if ( COM_ParseString( &p, &value ) )
01338 {
01339 continue;
01340 }
01341 saberMove = GetIDForString( SaberMoveTable, value );
01342 if ( saberMove >= LS_INVALID && saberMove < LS_MOVE_MAX )
01343 {
01344 saber->lungeAtkMove = saberMove;
01345 }
01346 continue;
01347 }
01348
01349 if ( !Q_stricmp( token, "jumpAtkUpMove" ) )
01350 {
01351 if ( COM_ParseString( &p, &value ) )
01352 {
01353 continue;
01354 }
01355 saberMove = GetIDForString( SaberMoveTable, value );
01356 if ( saberMove >= LS_INVALID && saberMove < LS_MOVE_MAX )
01357 {
01358 saber->jumpAtkUpMove = saberMove;
01359 }
01360 continue;
01361 }
01362
01363