1 // 2 // Copyright(C) 1993-1996 Id Software, Inc. 3 // Copyright(C) 2005-2014 Simon Howard 4 // 5 // This program is free software; you can redistribute it and/or 6 // modify it under the terms of the GNU General Public License 7 // as published by the Free Software Foundation; either version 2 8 // of the License, or (at your option) any later version. 9 // 10 // This program is distributed in the hope that it will be useful, 11 // but WITHOUT ANY WARRANTY; without even the implied warranty of 12 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 // GNU General Public License for more details. 14 // 15 // DESCRIPTION: 16 // Intermission screens. 17 // 18 19 // haleyjd 08/23/2010: There is no intermission in Strife 20 #if 0 21 #include <stdio.h> 22 23 #include "z_zone.h" 24 25 #include "m_random.h" 26 27 #include "deh_main.h" 28 #include "i_swap.h" 29 #include "i_system.h" 30 31 #include "w_wad.h" 32 33 #include "g_game.h" 34 35 #include "r_local.h" 36 #include "s_sound.h" 37 38 #include "doomstat.h" 39 40 // Data. 41 #include "sounds.h" 42 43 // Needs access to LFB. 44 #include "v_video.h" 45 46 #include "wi_stuff.h" 47 48 // 49 // Data needed to add patches to full screen intermission pics. 50 // Patches are statistics messages, and animations. 51 // Loads of by-pixel layout and placement, offsets etc. 52 // 53 54 55 // 56 // Different vetween registered DOOM (1994) and 57 // Ultimate DOOM - Final edition (retail, 1995?). 58 // This is supposedly ignored for commercial 59 // release (aka DOOM II), which had 34 maps 60 // in one episode. So there. 61 #define NUMEPISODES 4 62 #define NUMMAPS 9 63 64 65 // in tics 66 //U #define PAUSELEN (TICRATE*2) 67 //U #define SCORESTEP 100 68 //U #define ANIMPERIOD 32 69 // pixel distance from "(YOU)" to "PLAYER N" 70 //U #define STARDIST 10 71 //U #define WK 1 72 73 74 // GLOBAL LOCATIONS 75 #define WI_TITLEY 2 76 #define WI_SPACINGY 33 77 78 // SINGPLE-PLAYER STUFF 79 #define SP_STATSX 50 80 #define SP_STATSY 50 81 82 #define SP_TIMEX 16 83 #define SP_TIMEY (SCREENHEIGHT-32) 84 85 86 // NET GAME STUFF 87 #define NG_STATSY 50 88 #define NG_STATSX (32 + SHORT(star->width)/2 + 32*!dofrags) 89 90 #define NG_SPACINGX 64 91 92 93 // DEATHMATCH STUFF 94 #define DM_MATRIXX 42 95 #define DM_MATRIXY 68 96 97 #define DM_SPACINGX 40 98 99 #define DM_TOTALSX 269 100 101 #define DM_KILLERSX 10 102 #define DM_KILLERSY 100 103 #define DM_VICTIMSX 5 104 #define DM_VICTIMSY 50 105 106 107 108 109 typedef enum 110 { 111 ANIM_ALWAYS, 112 ANIM_RANDOM, 113 ANIM_LEVEL 114 115 } animenum_t; 116 117 typedef struct 118 { 119 int x; 120 int y; 121 122 } point_t; 123 124 125 // 126 // Animation. 127 // There is another anim_t used in p_spec. 128 // 129 typedef struct 130 { 131 animenum_t type; 132 133 // period in tics between animations 134 int period; 135 136 // number of animation frames 137 int nanims; 138 139 // location of animation 140 point_t loc; 141 142 // ALWAYS: n/a, 143 // RANDOM: period deviation (<256), 144 // LEVEL: level 145 int data1; 146 147 // ALWAYS: n/a, 148 // RANDOM: random base period, 149 // LEVEL: n/a 150 int data2; 151 152 // actual graphics for frames of animations 153 patch_t* p[3]; 154 155 // following must be initialized to zero before use! 156 157 // next value of bcnt (used in conjunction with period) 158 int nexttic; 159 160 // last drawn animation frame 161 int lastdrawn; 162 163 // next frame number to animate 164 int ctr; 165 166 // used by RANDOM and LEVEL when animating 167 int state; 168 169 } anim_t; 170 171 172 static point_t lnodes[NUMEPISODES][NUMMAPS] = 173 { 174 // Episode 0 World Map 175 { 176 { 185, 164 }, // location of level 0 (CJ) 177 { 148, 143 }, // location of level 1 (CJ) 178 { 69, 122 }, // location of level 2 (CJ) 179 { 209, 102 }, // location of level 3 (CJ) 180 { 116, 89 }, // location of level 4 (CJ) 181 { 166, 55 }, // location of level 5 (CJ) 182 { 71, 56 }, // location of level 6 (CJ) 183 { 135, 29 }, // location of level 7 (CJ) 184 { 71, 24 } // location of level 8 (CJ) 185 }, 186 187 // Episode 1 World Map should go here 188 { 189 { 254, 25 }, // location of level 0 (CJ) 190 { 97, 50 }, // location of level 1 (CJ) 191 { 188, 64 }, // location of level 2 (CJ) 192 { 128, 78 }, // location of level 3 (CJ) 193 { 214, 92 }, // location of level 4 (CJ) 194 { 133, 130 }, // location of level 5 (CJ) 195 { 208, 136 }, // location of level 6 (CJ) 196 { 148, 140 }, // location of level 7 (CJ) 197 { 235, 158 } // location of level 8 (CJ) 198 }, 199 200 // Episode 2 World Map should go here 201 { 202 { 156, 168 }, // location of level 0 (CJ) 203 { 48, 154 }, // location of level 1 (CJ) 204 { 174, 95 }, // location of level 2 (CJ) 205 { 265, 75 }, // location of level 3 (CJ) 206 { 130, 48 }, // location of level 4 (CJ) 207 { 279, 23 }, // location of level 5 (CJ) 208 { 198, 48 }, // location of level 6 (CJ) 209 { 140, 25 }, // location of level 7 (CJ) 210 { 281, 136 } // location of level 8 (CJ) 211 } 212 213 }; 214 215 216 // 217 // Animation locations for episode 0 (1). 218 // Using patches saves a lot of space, 219 // as they replace 320x200 full screen frames. 220 // 221 222 #define ANIM(type, period, nanims, x, y, nexttic) \ 223 { (type), (period), (nanims), { (x), (y) }, (nexttic), \ 224 0, { NULL, NULL, NULL }, 0, 0, 0, 0 } 225 226 227 static anim_t epsd0animinfo[] = 228 { 229 ANIM(ANIM_ALWAYS, TICRATE/3, 3, 224, 104, 0), 230 ANIM(ANIM_ALWAYS, TICRATE/3, 3, 184, 160, 0), 231 ANIM(ANIM_ALWAYS, TICRATE/3, 3, 112, 136, 0), 232 ANIM(ANIM_ALWAYS, TICRATE/3, 3, 72, 112, 0), 233 ANIM(ANIM_ALWAYS, TICRATE/3, 3, 88, 96, 0), 234 ANIM(ANIM_ALWAYS, TICRATE/3, 3, 64, 48, 0), 235 ANIM(ANIM_ALWAYS, TICRATE/3, 3, 192, 40, 0), 236 ANIM(ANIM_ALWAYS, TICRATE/3, 3, 136, 16, 0), 237 ANIM(ANIM_ALWAYS, TICRATE/3, 3, 80, 16, 0), 238 ANIM(ANIM_ALWAYS, TICRATE/3, 3, 64, 24, 0), 239 }; 240 241 static anim_t epsd1animinfo[] = 242 { 243 ANIM(ANIM_LEVEL, TICRATE/3, 1, 128, 136, 1), 244 ANIM(ANIM_LEVEL, TICRATE/3, 1, 128, 136, 2), 245 ANIM(ANIM_LEVEL, TICRATE/3, 1, 128, 136, 3), 246 ANIM(ANIM_LEVEL, TICRATE/3, 1, 128, 136, 4), 247 ANIM(ANIM_LEVEL, TICRATE/3, 1, 128, 136, 5), 248 ANIM(ANIM_LEVEL, TICRATE/3, 1, 128, 136, 6), 249 ANIM(ANIM_LEVEL, TICRATE/3, 1, 128, 136, 7), 250 ANIM(ANIM_LEVEL, TICRATE/3, 3, 192, 144, 8), 251 ANIM(ANIM_LEVEL, TICRATE/3, 1, 128, 136, 8), 252 }; 253 254 static anim_t epsd2animinfo[] = 255 { 256 ANIM(ANIM_ALWAYS, TICRATE/3, 3, 104, 168, 0), 257 ANIM(ANIM_ALWAYS, TICRATE/3, 3, 40, 136, 0), 258 ANIM(ANIM_ALWAYS, TICRATE/3, 3, 160, 96, 0), 259 ANIM(ANIM_ALWAYS, TICRATE/3, 3, 104, 80, 0), 260 ANIM(ANIM_ALWAYS, TICRATE/3, 3, 120, 32, 0), 261 ANIM(ANIM_ALWAYS, TICRATE/4, 3, 40, 0, 0), 262 }; 263 264 static int NUMANIMS[NUMEPISODES] = 265 { 266 arrlen(epsd0animinfo), 267 arrlen(epsd1animinfo), 268 arrlen(epsd2animinfo), 269 }; 270 271 static anim_t *anims[NUMEPISODES] = 272 { 273 epsd0animinfo, 274 epsd1animinfo, 275 epsd2animinfo 276 }; 277 278 279 // 280 // GENERAL DATA 281 // 282 283 // 284 // Locally used stuff. 285 // 286 287 // States for single-player 288 #define SP_KILLS 0 289 #define SP_ITEMS 2 290 #define SP_SECRET 4 291 #define SP_FRAGS 6 292 #define SP_TIME 8 293 #define SP_PAR ST_TIME 294 295 #define SP_PAUSE 1 296 297 // in seconds 298 #define SHOWNEXTLOCDELAY 4 299 //#define SHOWLASTLOCDELAY SHOWNEXTLOCDELAY 300 301 302 // used to accelerate or skip a stage 303 static int acceleratestage; 304 305 // wbs->pnum 306 static int me; 307 308 // specifies current state 309 static stateenum_t state; 310 311 // contains information passed into intermission 312 static wbstartstruct_t* wbs; 313 314 static wbplayerstruct_t* plrs; // wbs->plyr[] 315 316 // used for general timing 317 static int cnt; 318 319 // used for timing of background animation 320 static int bcnt; 321 322 // signals to refresh everything for one frame 323 static int firstrefresh; 324 325 static int cnt_kills[MAXPLAYERS]; 326 static int cnt_items[MAXPLAYERS]; 327 static int cnt_secret[MAXPLAYERS]; 328 static int cnt_time; 329 static int cnt_par; 330 static int cnt_pause; 331 332 // # of commercial levels 333 static int NUMCMAPS; 334 335 336 // 337 // GRAPHICS 338 // 339 340 // You Are Here graphic 341 static patch_t* yah[3] = { NULL, NULL, NULL }; 342 343 // splat 344 static patch_t* splat[2] = { NULL, NULL }; 345 346 // %, : graphics 347 static patch_t* percent; 348 static patch_t* colon; 349 350 // 0-9 graphic 351 static patch_t* num[10]; 352 353 // minus sign 354 static patch_t* wiminus; 355 356 // "Finished!" graphics 357 static patch_t* finished; 358 359 // "Entering" graphic 360 static patch_t* entering; 361 362 // "secret" 363 static patch_t* sp_secret; 364 365 // "Kills", "Scrt", "Items", "Frags" 366 static patch_t* kills; 367 static patch_t* secret; 368 static patch_t* items; 369 static patch_t* frags; 370 371 // Time sucks. 372 static patch_t* timepatch; 373 static patch_t* par; 374 static patch_t* sucks; 375 376 // "killers", "victims" 377 static patch_t* killers; 378 static patch_t* victims; 379 380 // "Total", your face, your dead face 381 static patch_t* total; 382 static patch_t* star; 383 static patch_t* bstar; 384 385 // "red P[1..MAXPLAYERS]" 386 static patch_t* p[MAXPLAYERS]; 387 388 // "gray P[1..MAXPLAYERS]" 389 static patch_t* bp[MAXPLAYERS]; 390 391 // Name graphics of each level (centered) 392 static patch_t** lnames; 393 394 // Buffer storing the backdrop 395 static patch_t *background; 396 397 // 398 // CODE 399 // 400 401 // slam background 402 void WI_slamBackground(void) 403 { 404 V_DrawPatch(0, 0, background); 405 } 406 407 // The ticker is used to detect keys 408 // because of timing issues in netgames. 409 boolean WI_Responder(event_t* ev) 410 { 411 return false; 412 } 413 414 415 // Draws "<Levelname> Finished!" 416 void WI_drawLF(void) 417 { 418 int y = WI_TITLEY; 419 420 if (gamemode != commercial || wbs->last < NUMCMAPS) 421 { 422 // draw <LevelName> 423 V_DrawPatch((SCREENWIDTH - SHORT(lnames[wbs->last]->width))/2, 424 y, lnames[wbs->last]); 425 426 // draw "Finished!" 427 y += (5*SHORT(lnames[wbs->last]->height))/4; 428 429 V_DrawPatch((SCREENWIDTH - SHORT(finished->width)) / 2, y, finished); 430 } 431 else if (wbs->last == NUMCMAPS) 432 { 433 // MAP33 - nothing is displayed! 434 } 435 else if (wbs->last > NUMCMAPS) 436 { 437 // > MAP33. Doom bombs out here with a Bad V_DrawPatch error. 438 // I'm pretty sure that doom2.exe is just reading into random 439 // bits of memory at this point, but let's try to be accurate 440 // anyway. This deliberately triggers a V_DrawPatch error. 441 442 patch_t tmp = { SCREENWIDTH, SCREENHEIGHT, 1, 1, 443 { 0, 0, 0, 0, 0, 0, 0, 0 } }; 444 445 V_DrawPatch(0, y, &tmp); 446 } 447 } 448 449 450 451 // Draws "Entering <LevelName>" 452 void WI_drawEL(void) 453 { 454 int y = WI_TITLEY; 455 456 // draw "Entering" 457 V_DrawPatch((SCREENWIDTH - SHORT(entering->width))/2, 458 y, 459 entering); 460 461 // draw level 462 y += (5*SHORT(lnames[wbs->next]->height))/4; 463 464 V_DrawPatch((SCREENWIDTH - SHORT(lnames[wbs->next]->width))/2, 465 y, 466 lnames[wbs->next]); 467 468 } 469 470 void 471 WI_drawOnLnode 472 ( int n, 473 patch_t* c[] ) 474 { 475 476 int i; 477 int left; 478 int top; 479 int right; 480 int bottom; 481 boolean fits = false; 482 483 i = 0; 484 do 485 { 486 left = lnodes[wbs->epsd][n].x - SHORT(c[i]->leftoffset); 487 top = lnodes[wbs->epsd][n].y - SHORT(c[i]->topoffset); 488 right = left + SHORT(c[i]->width); 489 bottom = top + SHORT(c[i]->height); 490 491 if (left >= 0 492 && right < SCREENWIDTH 493 && top >= 0 494 && bottom < SCREENHEIGHT) 495 { 496 fits = true; 497 } 498 else 499 { 500 i++; 501 } 502 } while (!fits && i!=2 && c[i] != NULL); 503 504 if (fits && i<2) 505 { 506 V_DrawPatch(lnodes[wbs->epsd][n].x, 507 lnodes[wbs->epsd][n].y, 508 c[i]); 509 } 510 else 511 { 512 // DEBUG 513 printf("Could not place patch on level %d", n+1); 514 } 515 } 516 517 518 519 void WI_initAnimatedBack(void) 520 { 521 int i; 522 anim_t* a; 523 524 if (gamemode == commercial) 525 return; 526 527 if (wbs->epsd > 2) 528 return; 529 530 for (i=0;i<NUMANIMS[wbs->epsd];i++) 531 { 532 a = &anims[wbs->epsd][i]; 533 534 // init variables 535 a->ctr = -1; 536 537 // specify the next time to draw it 538 if (a->type == ANIM_ALWAYS) 539 a->nexttic = bcnt + 1 + (M_Random()%a->period); 540 else if (a->type == ANIM_RANDOM) 541 a->nexttic = bcnt + 1 + a->data2+(M_Random()%a->data1); 542 else if (a->type == ANIM_LEVEL) 543 a->nexttic = bcnt + 1; 544 } 545 546 } 547 548 void WI_updateAnimatedBack(void) 549 { 550 int i; 551 anim_t* a; 552 553 if (gamemode == commercial) 554 return; 555 556 if (wbs->epsd > 2) 557 return; 558 559 for (i=0;i<NUMANIMS[wbs->epsd];i++) 560 { 561 a = &anims[wbs->epsd][i]; 562 563 if (bcnt == a->nexttic) 564 { 565 switch (a->type) 566 { 567 case ANIM_ALWAYS: 568 if (++a->ctr >= a->nanims) a->ctr = 0; 569 a->nexttic = bcnt + a->period; 570 break; 571 572 case ANIM_RANDOM: 573 a->ctr++; 574 if (a->ctr == a->nanims) 575 { 576 a->ctr = -1; 577 a->nexttic = bcnt+a->data2+(M_Random()%a->data1); 578 } 579 else a->nexttic = bcnt + a->period; 580 break; 581 582 case ANIM_LEVEL: 583 // gawd-awful hack for level anims 584 if (!(state == StatCount && i == 7) 585 && wbs->next == a->data1) 586 { 587 a->ctr++; 588 if (a->ctr == a->nanims) a->ctr--; 589 a->nexttic = bcnt + a->period; 590 } 591 break; 592 } 593 } 594 595 } 596 597 } 598 599 void WI_drawAnimatedBack(void) 600 { 601 int i; 602 anim_t* a; 603 604 if (gamemode == commercial) 605 return; 606 607 if (wbs->epsd > 2) 608 return; 609 610 for (i=0 ; i<NUMANIMS[wbs->epsd] ; i++) 611 { 612 a = &anims[wbs->epsd][i]; 613 614 if (a->ctr >= 0) 615 V_DrawPatch(a->loc.x, a->loc.y, a->p[a->ctr]); 616 } 617 618 } 619 620 // 621 // Draws a number. 622 // If digits > 0, then use that many digits minimum, 623 // otherwise only use as many as necessary. 624 // Returns new x position. 625 // 626 627 int 628 WI_drawNum 629 ( int x, 630 int y, 631 int n, 632 int digits ) 633 { 634 635 int fontwidth = SHORT(num[0]->width); 636 int neg; 637 int temp; 638 639 if (digits < 0) 640 { 641 if (!n) 642 { 643 // make variable-length zeros 1 digit long 644 digits = 1; 645 } 646 else 647 { 648 // figure out # of digits in # 649 digits = 0; 650 temp = n; 651 652 while (temp) 653 { 654 temp /= 10; 655 digits++; 656 } 657 } 658 } 659 660 neg = n < 0; 661 if (neg) 662 n = -n; 663 664 // if non-number, do not draw it 665 if (n == 1994) 666 return 0; 667 668 // draw the new number 669 while (digits--) 670 { 671 x -= fontwidth; 672 V_DrawPatch(x, y, num[ n % 10 ]); 673 n /= 10; 674 } 675 676 // draw a minus sign if necessary 677 if (neg) 678 V_DrawPatch(x-=8, y, wiminus); 679 680 return x; 681 682 } 683 684 void 685 WI_drawPercent 686 ( int x, 687 int y, 688 int p ) 689 { 690 if (p < 0) 691 return; 692 693 V_DrawPatch(x, y, percent); 694 WI_drawNum(x, y, p, -1); 695 } 696 697 698 699 // 700 // Display level completion time and par, 701 // or "sucks" message if overflow. 702 // 703 void 704 WI_drawTime 705 ( int x, 706 int y, 707 int t ) 708 { 709 710 int div; 711 int n; 712 713 if (t<0) 714 return; 715 716 if (t <= 61*59) 717 { 718 div = 1; 719 720 do 721 { 722 n = (t / div) % 60; 723 x = WI_drawNum(x, y, n, 2) - SHORT(colon->width); 724 div *= 60; 725 726 // draw 727 if (div==60 || t / div) 728 V_DrawPatch(x, y, colon); 729 730 } while (t / div); 731 } 732 else 733 { 734 // "sucks" 735 V_DrawPatch(x - SHORT(sucks->width), y, sucks); 736 } 737 } 738 739 740 void WI_End(void) 741 { 742 void WI_unloadData(void); 743 WI_unloadData(); 744 } 745 746 void WI_initNoState(void) 747 { 748 state = NoState; 749 acceleratestage = 0; 750 cnt = 10; 751 } 752 753 void WI_updateNoState(void) { 754 755 WI_updateAnimatedBack(); 756 757 if (!--cnt) 758 { 759 // Don't call WI_End yet. G_WorldDone doesnt immediately 760 // change gamestate, so WI_Drawer is still going to get 761 // run until that happens. If we do that after WI_End 762 // (which unloads all the graphics), we're in trouble. 763 //WI_End(); 764 G_WorldDone(); 765 } 766 767 } 768 769 static boolean snl_pointeron = false; 770 771 772 void WI_initShowNextLoc(void) 773 { 774 state = ShowNextLoc; 775 acceleratestage = 0; 776 cnt = SHOWNEXTLOCDELAY * TICRATE; 777 778 WI_initAnimatedBack(); 779 } 780 781 void WI_updateShowNextLoc(void) 782 { 783 WI_updateAnimatedBack(); 784 785 if (!--cnt || acceleratestage) 786 WI_initNoState(); 787 else 788 snl_pointeron = (cnt & 31) < 20; 789 } 790 791 void WI_drawShowNextLoc(void) 792 { 793 794 int i; 795 int last; 796 797 WI_slamBackground(); 798 799 // draw animated background 800 WI_drawAnimatedBack(); 801 802 if ( gamemode != commercial) 803 { 804 if (wbs->epsd > 2) 805 { 806 WI_drawEL(); 807 return; 808 } 809 810 last = (wbs->last == 8) ? wbs->next - 1 : wbs->last; 811 812 // draw a splat on taken cities. 813 for (i=0 ; i<=last ; i++) 814 WI_drawOnLnode(i, splat); 815 816 // splat the secret level? 817 if (wbs->didsecret) 818 WI_drawOnLnode(8, splat); 819 820 // draw flashing ptr 821 if (snl_pointeron) 822 WI_drawOnLnode(wbs->next, yah); 823 } 824 825 // draws which level you are entering.. 826 if ( (gamemode != commercial) 827 || wbs->next != 30) 828 WI_drawEL(); 829 830 } 831 832 void WI_drawNoState(void) 833 { 834 snl_pointeron = true; 835 WI_drawShowNextLoc(); 836 } 837 838 int WI_fragSum(int playernum) 839 { 840 int i; 841 int frags = 0; 842 843 for (i=0 ; i<MAXPLAYERS ; i++) 844 { 845 if (playeringame[i] 846 && i!=playernum) 847 { 848 frags += plrs[playernum].frags[i]; 849 } 850 } 851 852 853 // JDC hack - negative frags. 854 frags -= plrs[playernum].frags[playernum]; 855 // UNUSED if (frags < 0) 856 // frags = 0; 857 858 return frags; 859 } 860 861 862 863 static int dm_state; 864 static int dm_frags[MAXPLAYERS][MAXPLAYERS]; 865 static int dm_totals[MAXPLAYERS]; 866 867 868 869 void WI_initDeathmatchStats(void) 870 { 871 872 int i; 873 int j; 874 875 state = StatCount; 876 acceleratestage = 0; 877 dm_state = 1; 878 879 cnt_pause = TICRATE; 880 881 for (i=0 ; i<MAXPLAYERS ; i++) 882 { 883 if (playeringame[i]) 884 { 885 for (j=0 ; j<MAXPLAYERS ; j++) 886 if (playeringame[j]) 887 dm_frags[i][j] = 0; 888 889 dm_totals[i] = 0; 890 } 891 } 892 893 WI_initAnimatedBack(); 894 } 895 896 897 898 void WI_updateDeathmatchStats(void) 899 { 900 901 int i; 902 int j; 903 904 boolean stillticking; 905 906 WI_updateAnimatedBack(); 907 908 if (acceleratestage && dm_state != 4) 909 { 910 acceleratestage = 0; 911 912 for (i=0 ; i<MAXPLAYERS ; i++) 913 { 914 if (playeringame[i]) 915 { 916 for (j=0 ; j<MAXPLAYERS ; j++) 917 if (playeringame[j]) 918 dm_frags[i][j] = plrs[i].frags[j]; 919 920 dm_totals[i] = WI_fragSum(i); 921 } 922 } 923 924 925 S_StartSound(0, sfx_barexp); 926 dm_state = 4; 927 } 928 929 930 if (dm_state == 2) 931 { 932 if (!(bcnt&3)) 933 S_StartSound(0, sfx_pistol); 934 935 stillticking = false; 936 937 for (i=0 ; i<MAXPLAYERS ; i++) 938 { 939 if (playeringame[i]) 940 { 941 for (j=0 ; j<MAXPLAYERS ; j++) 942 { 943 if (playeringame[j] 944 && dm_frags[i][j] != plrs[i].frags[j]) 945 { 946 if (plrs[i].frags[j] < 0) 947 dm_frags[i][j]--; 948 else 949 dm_frags[i][j]++; 950 951 if (dm_frags[i][j] > 99) 952 dm_frags[i][j] = 99; 953 954 if (dm_frags[i][j] < -99) 955 dm_frags[i][j] = -99; 956 957 stillticking = true; 958 } 959 } 960 dm_totals[i] = WI_fragSum(i); 961 962 if (dm_totals[i] > 99) 963 dm_totals[i] = 99; 964 965 if (dm_totals[i] < -99) 966 dm_totals[i] = -99; 967 } 968 969 } 970 if (!stillticking) 971 { 972 S_StartSound(0, sfx_barexp); 973 dm_state++; 974 } 975 976 } 977 else if (dm_state == 4) 978 { 979 if (acceleratestage) 980 { 981 S_StartSound(0, sfx_slop); 982 983 if ( gamemode == commercial) 984 WI_initNoState(); 985 else 986 WI_initShowNextLoc(); 987 } 988 } 989 else if (dm_state & 1) 990 { 991 if (!--cnt_pause) 992 { 993 dm_state++; 994 cnt_pause = TICRATE; 995 } 996 } 997 } 998 999 1000 1001 void WI_drawDeathmatchStats(void) 1002 { 1003 1004 int i; 1005 int j; 1006 int x; 1007 int y; 1008 int w; 1009 1010 int lh; // line height 1011 1012 lh = WI_SPACINGY; 1013 1014 WI_slamBackground(); 1015 1016 // draw animated background 1017 WI_drawAnimatedBack(); 1018 WI_drawLF(); 1019 1020 // draw stat titles (top line) 1021 V_DrawPatch(DM_TOTALSX-SHORT(total->width)/2, 1022 DM_MATRIXY-WI_SPACINGY+10, 1023 total); 1024 1025 V_DrawPatch(DM_KILLERSX, DM_KILLERSY, killers); 1026 V_DrawPatch(DM_VICTIMSX, DM_VICTIMSY, victims); 1027 1028 // draw P? 1029 x = DM_MATRIXX + DM_SPACINGX; 1030 y = DM_MATRIXY; 1031 1032 for (i=0 ; i<MAXPLAYERS ; i++) 1033 { 1034 if (playeringame[i]) 1035 { 1036 V_DrawPatch(x-SHORT(p[i]->width)/2, 1037 DM_MATRIXY - WI_SPACINGY, 1038 p[i]); 1039 1040 V_DrawPatch(DM_MATRIXX-SHORT(p[i]->width)/2, 1041 y, 1042 p[i]); 1043 1044 if (i == me) 1045 { 1046 V_DrawPatch(x-SHORT(p[i]->width)/2, 1047 DM_MATRIXY - WI_SPACINGY, 1048 bstar); 1049 1050 V_DrawPatch(DM_MATRIXX-SHORT(p[i]->width)/2, 1051 y, 1052 star); 1053 } 1054 } 1055 else 1056 { 1057 // V_DrawPatch(x-SHORT(bp[i]->width)/2, 1058 // DM_MATRIXY - WI_SPACINGY, bp[i]); 1059 // V_DrawPatch(DM_MATRIXX-SHORT(bp[i]->width)/2, 1060 // y, bp[i]); 1061 } 1062 x += DM_SPACINGX; 1063 y += WI_SPACINGY; 1064 } 1065 1066 // draw stats 1067 y = DM_MATRIXY+10; 1068 w = SHORT(num[0]->width); 1069 1070 for (i=0 ; i<MAXPLAYERS ; i++) 1071 { 1072 x = DM_MATRIXX + DM_SPACINGX; 1073 1074 if (playeringame[i]) 1075 { 1076 for (j=0 ; j<MAXPLAYERS ; j++) 1077 { 1078 if (playeringame[j]) 1079 WI_drawNum(x+w, y, dm_frags[i][j], 2); 1080 1081 x += DM_SPACINGX; 1082 } 1083 WI_drawNum(DM_TOTALSX+w, y, dm_totals[i], 2); 1084 } 1085 y += WI_SPACINGY; 1086 } 1087 } 1088 1089 static int cnt_frags[MAXPLAYERS]; 1090 static int dofrags; 1091 static int ng_state; 1092 1093 void WI_initNetgameStats(void) 1094 { 1095 1096 int i; 1097 1098 state = StatCount; 1099 acceleratestage = 0; 1100 ng_state = 1; 1101 1102 cnt_pause = TICRATE; 1103 1104 for (i=0 ; i<MAXPLAYERS ; i++) 1105 { 1106 if (!playeringame[i]) 1107 continue; 1108 1109 cnt_kills[i] = cnt_items[i] = cnt_secret[i] = cnt_frags[i] = 0; 1110 1111 dofrags += WI_fragSum(i); 1112 } 1113 1114 dofrags = !!dofrags; 1115 1116 WI_initAnimatedBack(); 1117 } 1118 1119 1120 1121 void WI_updateNetgameStats(void) 1122 { 1123 1124 int i; 1125 int fsum; 1126 1127 boolean stillticking; 1128 1129 WI_updateAnimatedBack(); 1130 1131 if (acceleratestage && ng_state != 10) 1132 { 1133 acceleratestage = 0; 1134 1135 for (i=0 ; i<MAXPLAYERS ; i++) 1136 { 1137 if (!playeringame[i]) 1138 continue; 1139 1140 cnt_kills[i] = (plrs[i].skills * 100) / wbs->maxkills; 1141 cnt_items[i] = (plrs[i].sitems * 100) / wbs->maxitems; 1142 cnt_secret[i] = (plrs[i].ssecret * 100) / wbs->maxsecret; 1143 1144 if (dofrags) 1145 cnt_frags[i] = WI_fragSum(i); 1146 } 1147 S_StartSound(0, sfx_barexp); 1148 ng_state = 10; 1149 } 1150 1151 if (ng_state == 2) 1152 { 1153 if (!(bcnt&3)) 1154 S_StartSound(0, sfx_pistol); 1155 1156 stillticking = false; 1157 1158 for (i=0 ; i<MAXPLAYERS ; i++) 1159 { 1160 if (!playeringame[i]) 1161 continue; 1162 1163 cnt_kills[i] += 2; 1164 1165 if (cnt_kills[i] >= (plrs[i].skills * 100) / wbs->maxkills) 1166 cnt_kills[i] = (plrs[i].skills * 100) / wbs->maxkills; 1167 else 1168 stillticking = true; 1169 } 1170 1171 if (!stillticking) 1172 { 1173 S_StartSound(0, sfx_barexp); 1174 ng_state++; 1175 } 1176 } 1177 else if (ng_state == 4) 1178 { 1179 if (!(bcnt&3)) 1180 S_StartSound(0, sfx_pistol); 1181 1182 stillticking = false; 1183 1184 for (i=0 ; i<MAXPLAYERS ; i++) 1185 { 1186 if (!playeringame[i]) 1187 continue; 1188 1189 cnt_items[i] += 2; 1190 if (cnt_items[i] >= (plrs[i].sitems * 100) / wbs->maxitems) 1191 cnt_items[i] = (plrs[i].sitems * 100) / wbs->maxitems; 1192 else 1193 stillticking = true; 1194 } 1195 if (!stillticking) 1196 { 1197 S_StartSound(0, sfx_barexp); 1198 ng_state++; 1199 } 1200 } 1201 else if (ng_state == 6) 1202 { 1203 if (!(bcnt&3)) 1204 S_StartSound(0, sfx_pistol); 1205 1206 stillticking = false; 1207 1208 for (i=0 ; i<MAXPLAYERS ; i++) 1209 { 1210 if (!playeringame[i]) 1211 continue; 1212 1213 cnt_secret[i] += 2; 1214 1215 if (cnt_secret[i] >= (plrs[i].ssecret * 100) / wbs->maxsecret) 1216 cnt_secret[i] = (plrs[i].ssecret * 100) / wbs->maxsecret; 1217 else 1218 stillticking = true; 1219 } 1220 1221 if (!stillticking) 1222 { 1223 S_StartSound(0, sfx_barexp); 1224 ng_state += 1 + 2*!dofrags; 1225 } 1226 } 1227 else if (ng_state == 8) 1228 { 1229 if (!(bcnt&3)) 1230 S_StartSound(0, sfx_pistol); 1231 1232 stillticking = false; 1233 1234 for (i=0 ; i<MAXPLAYERS ; i++) 1235 { 1236 if (!playeringame[i]) 1237 continue; 1238 1239 cnt_frags[i] += 1; 1240 1241 if (cnt_frags[i] >= (fsum = WI_fragSum(i))) 1242 cnt_frags[i] = fsum; 1243 else 1244 stillticking = true; 1245 } 1246 1247 if (!stillticking) 1248 { 1249 S_StartSound(0, sfx_pldeth); 1250 ng_state++; 1251 } 1252 } 1253 else if (ng_state == 10) 1254 { 1255 if (acceleratestage) 1256 { 1257 S_StartSound(0, sfx_sgcock); 1258 if ( gamemode == commercial ) 1259 WI_initNoState(); 1260 else 1261 WI_initShowNextLoc(); 1262 } 1263 } 1264 else if (ng_state & 1) 1265 { 1266 if (!--cnt_pause) 1267 { 1268 ng_state++; 1269 cnt_pause = TICRATE; 1270 } 1271 } 1272 } 1273 1274 1275 1276 void WI_drawNetgameStats(void) 1277 { 1278 int i; 1279 int x; 1280 int y; 1281 int pwidth = SHORT(percent->width); 1282 1283 WI_slamBackground(); 1284 1285 // draw animated background 1286 WI_drawAnimatedBack(); 1287 1288 WI_drawLF(); 1289 1290 // draw stat titles (top line) 1291 V_DrawPatch(NG_STATSX+NG_SPACINGX-SHORT(kills->width), 1292 NG_STATSY, kills); 1293 1294 V_DrawPatch(NG_STATSX+2*NG_SPACINGX-SHORT(items->width), 1295 NG_STATSY, items); 1296 1297 V_DrawPatch(NG_STATSX+3*NG_SPACINGX-SHORT(secret->width), 1298 NG_STATSY, secret); 1299 1300 if (dofrags) 1301 V_DrawPatch(NG_STATSX+4*NG_SPACINGX-SHORT(frags->width), 1302 NG_STATSY, frags); 1303 1304 // draw stats 1305 y = NG_STATSY + SHORT(kills->height); 1306 1307 for (i=0 ; i<MAXPLAYERS ; i++) 1308 { 1309 if (!playeringame[i]) 1310 continue; 1311 1312 x = NG_STATSX; 1313 V_DrawPatch(x-SHORT(p[i]->width), y, p[i]); 1314 1315 if (i == me) 1316 V_DrawPatch(x-SHORT(p[i]->width), y, star); 1317 1318 x += NG_SPACINGX; 1319 WI_drawPercent(x-pwidth, y+10, cnt_kills[i]); x += NG_SPACINGX; 1320 WI_drawPercent(x-pwidth, y+10, cnt_items[i]); x += NG_SPACINGX; 1321 WI_drawPercent(x-pwidth, y+10, cnt_secret[i]); x += NG_SPACINGX; 1322 1323 if (dofrags) 1324 WI_drawNum(x, y+10, cnt_frags[i], -1); 1325 1326 y += WI_SPACINGY; 1327 } 1328 1329 } 1330 1331 static int sp_state; 1332 1333 void WI_initStats(void) 1334 { 1335 state = StatCount; 1336 acceleratestage = 0; 1337 sp_state = 1; 1338 cnt_kills[0] = cnt_items[0] = cnt_secret[0] = -1; 1339 cnt_time = cnt_par = -1; 1340 cnt_pause = TICRATE; 1341 1342 WI_initAnimatedBack(); 1343 } 1344 1345 void WI_updateStats(void) 1346 { 1347 1348 WI_updateAnimatedBack(); 1349 1350 if (acceleratestage && sp_state != 10) 1351 { 1352 acceleratestage = 0; 1353 cnt_kills[0] = (plrs[me].skills * 100) / wbs->maxkills; 1354 cnt_items[0] = (plrs[me].sitems * 100) / wbs->maxitems; 1355 cnt_secret[0] = (plrs[me].ssecret * 100) / wbs->maxsecret; 1356 cnt_time = plrs[me].stime / TICRATE; 1357 cnt_par = wbs->partime / TICRATE; 1358 S_StartSound(0, sfx_barexp); 1359 sp_state = 10; 1360 } 1361 1362 if (sp_state == 2) 1363 { 1364 cnt_kills[0] += 2; 1365 1366 if (!(bcnt&3)) 1367 S_StartSound(0, sfx_pistol); 1368 1369 if (cnt_kills[0] >= (plrs[me].skills * 100) / wbs->maxkills) 1370 { 1371 cnt_kills[0] = (plrs[me].skills * 100) / wbs->maxkills; 1372 S_StartSound(0, sfx_barexp); 1373 sp_state++; 1374 } 1375 } 1376 else if (sp_state == 4) 1377 { 1378 cnt_items[0] += 2; 1379 1380 if (!(bcnt&3)) 1381 S_StartSound(0, sfx_pistol); 1382 1383 if (cnt_items[0] >= (plrs[me].sitems * 100) / wbs->maxitems) 1384 { 1385 cnt_items[0] = (plrs[me].sitems * 100) / wbs->maxitems; 1386 S_StartSound(0, sfx_barexp); 1387 sp_state++; 1388 } 1389 } 1390 else if (sp_state == 6) 1391 { 1392 cnt_secret[0] += 2; 1393 1394 if (!(bcnt&3)) 1395 S_StartSound(0, sfx_pistol); 1396 1397 if (cnt_secret[0] >= (plrs[me].ssecret * 100) / wbs->maxsecret) 1398 { 1399 cnt_secret[0] = (plrs[me].ssecret * 100) / wbs->maxsecret; 1400 S_StartSound(0, sfx_barexp); 1401 sp_state++; 1402 } 1403 } 1404 1405 else if (sp_state == 8) 1406 { 1407 if (!(bcnt&3)) 1408 S_StartSound(0, sfx_pistol); 1409 1410 cnt_time += 3; 1411 1412 if (cnt_time >= plrs[me].stime / TICRATE) 1413 cnt_time = plrs[me].stime / TICRATE; 1414 1415 cnt_par += 3; 1416 1417 if (cnt_par >= wbs->partime / TICRATE) 1418 { 1419 cnt_par = wbs->partime / TICRATE; 1420 1421 if (cnt_time >= plrs[me].stime / TICRATE) 1422 { 1423 S_StartSound(0, sfx_barexp); 1424 sp_state++; 1425 } 1426 } 1427 } 1428 else if (sp_state == 10) 1429 { 1430 if (acceleratestage) 1431 { 1432 S_StartSound(0, sfx_sgcock); 1433 1434 if (gamemode == commercial) 1435 WI_initNoState(); 1436 else 1437 WI_initShowNextLoc(); 1438 } 1439 } 1440 else if (sp_state & 1) 1441 { 1442 if (!--cnt_pause) 1443 { 1444 sp_state++; 1445 cnt_pause = TICRATE; 1446 } 1447 } 1448 1449 } 1450 1451 void WI_drawStats(void) 1452 { 1453 // line height 1454 int lh; 1455 1456 lh = (3*SHORT(num[0]->height))/2; 1457 1458 WI_slamBackground(); 1459 1460 // draw animated background 1461 WI_drawAnimatedBack(); 1462 1463 WI_drawLF(); 1464 1465 V_DrawPatch(SP_STATSX, SP_STATSY, kills); 1466 WI_drawPercent(SCREENWIDTH - SP_STATSX, SP_STATSY, cnt_kills[0]); 1467 1468 V_DrawPatch(SP_STATSX, SP_STATSY+lh, items); 1469 WI_drawPercent(SCREENWIDTH - SP_STATSX, SP_STATSY+lh, cnt_items[0]); 1470 1471 V_DrawPatch(SP_STATSX, SP_STATSY+2*lh, sp_secret); 1472 WI_drawPercent(SCREENWIDTH - SP_STATSX, SP_STATSY+2*lh, cnt_secret[0]); 1473 1474 V_DrawPatch(SP_TIMEX, SP_TIMEY, timepatch); 1475 WI_drawTime(SCREENWIDTH/2 - SP_TIMEX, SP_TIMEY, cnt_time); 1476 1477 if (wbs->epsd < 3) 1478 { 1479 V_DrawPatch(SCREENWIDTH/2 + SP_TIMEX, SP_TIMEY, par); 1480 WI_drawTime(SCREENWIDTH - SP_TIMEX, SP_TIMEY, cnt_par); 1481 } 1482 1483 } 1484 1485 void WI_checkForAccelerate(void) 1486 { 1487 int i; 1488 player_t *player; 1489 1490 // check for button presses to skip delays 1491 for (i=0, player = players ; i<MAXPLAYERS ; i++, player++) 1492 { 1493 if (playeringame[i]) 1494 { 1495 if (player->cmd.buttons & BT_ATTACK) 1496 { 1497 if (!player->attackdown) 1498 acceleratestage = 1; 1499 player->attackdown = true; 1500 } 1501 else 1502 player->attackdown = false; 1503 if (player->cmd.buttons & BT_USE) 1504 { 1505 if (!player->usedown) 1506 acceleratestage = 1; 1507 player->usedown = true; 1508 } 1509 else 1510 player->usedown = false; 1511 } 1512 } 1513 } 1514 1515 1516 1517 // Updates stuff each tick 1518 void WI_Ticker(void) 1519 { 1520 // counter for general background animation 1521 bcnt++; 1522 1523 if (bcnt == 1) 1524 { 1525 // intermission music 1526 if ( gamemode == commercial ) 1527 S_ChangeMusic(mus_dm2int, true); 1528 else 1529 S_ChangeMusic(mus_inter, true); 1530 } 1531 1532 WI_checkForAccelerate(); 1533 1534 switch (state) 1535 { 1536 case StatCount: 1537 if (deathmatch) WI_updateDeathmatchStats(); 1538 else if (netgame) WI_updateNetgameStats(); 1539 else WI_updateStats(); 1540 break; 1541 1542 case ShowNextLoc: 1543 WI_updateShowNextLoc(); 1544 break; 1545 1546 case NoState: 1547 WI_updateNoState(); 1548 break; 1549 } 1550 1551 } 1552 1553 typedef void (*load_callback_t)(char *lumpname, patch_t **variable); 1554 1555 // Common load/unload function. Iterates over all the graphics 1556 // lumps to be loaded/unloaded into memory. 1557 1558 static void WI_loadUnloadData(load_callback_t callback) 1559 { 1560 int i, j; 1561 char name[9]; 1562 anim_t *a; 1563 1564 if (gamemode == commercial) 1565 { 1566 for (i=0 ; i<NUMCMAPS ; i++) 1567 { 1568 DEH_snprintf(name, 9, "CWILV%2.2d", i); 1569 callback(name, &lnames[i]); 1570 } 1571 } 1572 else 1573 { 1574 for (i=0 ; i<NUMMAPS ; i++) 1575 { 1576 DEH_snprintf(name, 9, "WILV%d%d", wbs->epsd, i); 1577 callback(name, &lnames[i]); 1578 } 1579 1580 // you are here 1581 callback(DEH_String("WIURH0"), &yah[0]); 1582 1583 // you are here (alt.) 1584 callback(DEH_String("WIURH1"), &yah[1]); 1585 1586 // splat 1587 callback(DEH_String("WISPLAT"), &splat[0]); 1588 1589 if (wbs->epsd < 3) 1590 { 1591 for (j=0;j<NUMANIMS[wbs->epsd];j++) 1592 { 1593 a = &anims[wbs->epsd][j]; 1594 for (i=0;i<a->nanims;i++) 1595 { 1596 // MONDO HACK! 1597 if (wbs->epsd != 1 || j != 8) 1598 { 1599 // animations 1600 DEH_snprintf(name, 9, "WIA%d%.2d%.2d", wbs->epsd, j, i); 1601 callback(name, &a->p[i]); 1602 } 1603 else 1604 { 1605 // HACK ALERT! 1606 a->p[i] = anims[1][4].p[i]; 1607 } 1608 } 1609 } 1610 } 1611 } 1612 1613 // More hacks on minus sign. 1614 callback(DEH_String("WIMINUS"), &wiminus); 1615 1616 for (i=0;i<10;i++) 1617 { 1618 // numbers 0-9 1619 DEH_snprintf(name, 9, "WINUM%d", i); 1620 callback(name, &num[i]); 1621 } 1622 1623 // percent sign 1624 callback(DEH_String("WIPCNT"), &percent); 1625 1626 // "finished" 1627 callback(DEH_String("WIF"), &finished); 1628 1629 // "entering" 1630 callback(DEH_String("WIENTER"), &entering); 1631 1632 // "kills" 1633 callback(DEH_String("WIOSTK"), &kills); 1634 1635 // "scrt" 1636 callback(DEH_String("WIOSTS"), &secret); 1637 1638 // "secret" 1639 callback(DEH_String("WISCRT2"), &sp_secret); 1640 1641 // french wad uses WIOBJ (?) 1642 if (W_CheckNumForName(DEH_String("WIOBJ")) >= 0) 1643 { 1644 // "items" 1645 if (netgame && !deathmatch) 1646 callback(DEH_String("WIOBJ"), &items); 1647 else 1648 callback(DEH_String("WIOSTI"), &items); 1649 } else { 1650 callback(DEH_String("WIOSTI"), &items); 1651 } 1652 1653 // "frgs" 1654 callback(DEH_String("WIFRGS"), &frags); 1655 1656 // ":" 1657 callback(DEH_String("WICOLON"), &colon); 1658 1659 // "time" 1660 callback(DEH_String("WITIME"), &timepatch); 1661 1662 // "sucks" 1663 callback(DEH_String("WISUCKS"), &sucks); 1664 1665 // "par" 1666 callback(DEH_String("WIPAR"), &par); 1667 1668 // "killers" (vertical) 1669 callback(DEH_String("WIKILRS"), &killers); 1670 1671 // "victims" (horiz) 1672 callback(DEH_String("WIVCTMS"), &victims); 1673 1674 // "total" 1675 callback(DEH_String("WIMSTT"), &total); 1676 1677 for (i=0 ; i<MAXPLAYERS ; i++) 1678 { 1679 // "1,2,3,4" 1680 DEH_snprintf(name, 9, "STPB%d", i); 1681 callback(name, &p[i]); 1682 1683 // "1,2,3,4" 1684 DEH_snprintf(name, 9, "WIBP%d", i+1); 1685 callback(name, &bp[i]); 1686 } 1687 1688 // Background image 1689 1690 if (gamemode == commercial) 1691 { 1692 M_StringCopy(name, DEH_String("INTERPIC"), sizeof(name)); 1693 name[8] = '\0'; 1694 } 1695 else if (gamemode == retail && wbs->epsd == 3) 1696 { 1697 M_StringCopy(name, DEH_String("INTERPIC"), sizeof(name)); 1698 name[8] = '\0'; 1699 } 1700 else 1701 { 1702 DEH_snprintf(name, 9, "WIMAP%d", wbs->epsd); 1703 } 1704 1705 // Draw backdrop and save to a temporary buffer 1706 1707 callback(name, &background); 1708 } 1709 1710 static void WI_loadCallback(char *name, patch_t **variable) 1711 { 1712 *variable = W_CacheLumpName(name, PU_STATIC); 1713 } 1714 1715 void WI_loadData(void) 1716 { 1717 if (gamemode == commercial) 1718 { 1719 NUMCMAPS = 32; 1720 lnames = (patch_t **) Z_Malloc(sizeof(patch_t*) * NUMCMAPS, 1721 PU_STATIC, NULL); 1722 } 1723 else 1724 { 1725 lnames = (patch_t **) Z_Malloc(sizeof(patch_t*) * NUMMAPS, 1726 PU_STATIC, NULL); 1727 } 1728 1729 WI_loadUnloadData(WI_loadCallback); 1730 1731 // These two graphics are special cased because we're sharing 1732 // them with the status bar code 1733 1734 // your face 1735 star = W_CacheLumpName(DEH_String("STFST01"), PU_STATIC); 1736 1737 // dead face 1738 bstar = W_CacheLumpName(DEH_String("STFDEAD0"), PU_STATIC); 1739 } 1740 1741 static void WI_unloadCallback(char *name, patch_t **variable) 1742 { 1743 W_ReleaseLumpName(name); 1744 *variable = NULL; 1745 } 1746 1747 void WI_unloadData(void) 1748 { 1749 WI_loadUnloadData(WI_unloadCallback); 1750 1751 // We do not free these lumps as they are shared with the status 1752 // bar code. 1753 1754 // W_ReleaseLumpName("STFST01"); 1755 // W_ReleaseLumpName("STFDEAD0"); 1756 } 1757 1758 void WI_Drawer (void) 1759 { 1760 switch (state) 1761 { 1762 case StatCount: 1763 if (deathmatch) 1764 WI_drawDeathmatchStats(); 1765 else if (netgame) 1766 WI_drawNetgameStats(); 1767 else 1768 WI_drawStats(); 1769 break; 1770 1771 case ShowNextLoc: 1772 WI_drawShowNextLoc(); 1773 break; 1774 1775 case NoState: 1776 WI_drawNoState(); 1777 break; 1778 } 1779 } 1780 1781 1782 void WI_initVariables(wbstartstruct_t* wbstartstruct) 1783 { 1784 1785 wbs = wbstartstruct; 1786 1787 #ifdef RANGECHECKING 1788 if (gamemode != commercial) 1789 { 1790 if ( gamemode == retail ) 1791 RNGCHECK(wbs->epsd, 0, 3); 1792 else 1793 RNGCHECK(wbs->epsd, 0, 2); 1794 } 1795 else 1796 { 1797 RNGCHECK(wbs->last, 0, 8); 1798 RNGCHECK(wbs->next, 0, 8); 1799 } 1800 RNGCHECK(wbs->pnum, 0, MAXPLAYERS); 1801 RNGCHECK(wbs->pnum, 0, MAXPLAYERS); 1802 #endif 1803 1804 acceleratestage = 0; 1805 cnt = bcnt = 0; 1806 firstrefresh = 1; 1807 me = wbs->pnum; 1808 plrs = wbs->plyr; 1809 1810 if (!wbs->maxkills) 1811 wbs->maxkills = 1; 1812 1813 if (!wbs->maxitems) 1814 wbs->maxitems = 1; 1815 1816 if (!wbs->maxsecret) 1817 wbs->maxsecret = 1; 1818 1819 if ( gamemode != retail ) 1820 if (wbs->epsd > 2) 1821 wbs->epsd -= 3; 1822 } 1823 1824 void WI_Start(wbstartstruct_t* wbstartstruct) 1825 { 1826 WI_initVariables(wbstartstruct); 1827 WI_loadData(); 1828 1829 if (deathmatch) 1830 WI_initDeathmatchStats(); 1831 else if (netgame) 1832 WI_initNetgameStats(); 1833 else 1834 WI_initStats(); 1835 } 1836 #endif 1837