|
|
1.1 ! root 1: /* ! 2: * Copyright (c) 1985 Regents of the University of California. ! 3: * All rights reserved. ! 4: * ! 5: * Redistribution and use in source and binary forms are permitted ! 6: * provided that the above copyright notice and this paragraph are ! 7: * duplicated in all such forms and that any documentation, ! 8: * advertising materials, and other materials related to such ! 9: * distribution and use acknowledge that the software was developed ! 10: * by the University of California, Berkeley. The name of the ! 11: * University may not be used to endorse or promote products derived ! 12: * from this software without specific prior written permission. ! 13: * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR ! 14: * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED ! 15: * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE. ! 16: */ ! 17: ! 18: #ifndef lint ! 19: static char sccsid[] = "@(#)shots.c 5.2 (Berkeley) 6/27/88"; ! 20: #endif /* not lint */ ! 21: ! 22: /* ! 23: * Hunt ! 24: * Copyright (c) 1985 Conrad C. Huang, Gregory S. Couch, Kenneth C.R.C. Arnold ! 25: * San Francisco, California ! 26: */ ! 27: ! 28: # include "hunt.h" ! 29: # include <signal.h> ! 30: ! 31: # define PLUS_DELTA(x, max) if (x < max) x++; else x-- ! 32: # define MINUS_DELTA(x, min) if (x > min) x--; else x++ ! 33: ! 34: /* ! 35: * moveshots: ! 36: * Move the shots already in the air, taking explosions into account ! 37: */ ! 38: moveshots() ! 39: { ! 40: register BULLET *bp, *next; ! 41: register PLAYER *pp; ! 42: register int x, y; ! 43: register BULLET *blist; ! 44: register int i; ! 45: ! 46: rollexpl(); ! 47: if (Bullets == NULL) ! 48: goto ret; ! 49: ! 50: /* ! 51: * First we move through the bullet list BULSPD times, looking ! 52: * for things we may have run into. If we do run into ! 53: * something, we set up the explosion and disappear, checking ! 54: * for damage to any player who got in the way. ! 55: */ ! 56: ! 57: blist = Bullets; ! 58: Bullets = NULL; ! 59: for (bp = blist; bp != NULL; bp = next) { ! 60: next = bp->b_next; ! 61: x = bp->b_x; ! 62: y = bp->b_y; ! 63: Maze[y][x] = bp->b_over; ! 64: for (pp = Player; pp < End_player; pp++) ! 65: check(pp, y, x); ! 66: # ifdef MONITOR ! 67: for (pp = Monitor; pp < End_monitor; pp++) ! 68: check(pp, y, x); ! 69: # endif MONITOR ! 70: ! 71: for (i = 0; i < BULSPD; i++) { ! 72: if (bp->b_expl) ! 73: break; ! 74: ! 75: x = bp->b_x; ! 76: y = bp->b_y; ! 77: ! 78: switch (bp->b_face) { ! 79: case LEFTS: ! 80: x--; ! 81: break; ! 82: case RIGHT: ! 83: x++; ! 84: break; ! 85: case ABOVE: ! 86: y--; ! 87: break; ! 88: case BELOW: ! 89: y++; ! 90: break; ! 91: } ! 92: ! 93: switch (Maze[y][x]) { ! 94: case SHOT: ! 95: if (rand_num(100) < 5) { ! 96: zapshot(Bullets, bp); ! 97: zapshot(next, bp); ! 98: } ! 99: break; ! 100: case GRENADE: ! 101: if (rand_num(100) < 10) { ! 102: zapshot(Bullets, bp); ! 103: zapshot(next, bp); ! 104: } ! 105: break; ! 106: # ifdef REFLECT ! 107: case WALL4: /* reflecting walls */ ! 108: switch (bp->b_face) { ! 109: case LEFTS: ! 110: bp->b_face = BELOW; ! 111: break; ! 112: case RIGHT: ! 113: bp->b_face = ABOVE; ! 114: break; ! 115: case ABOVE: ! 116: bp->b_face = RIGHT; ! 117: break; ! 118: case BELOW: ! 119: bp->b_face = LEFTS; ! 120: break; ! 121: } ! 122: Maze[y][x] = WALL5; ! 123: # ifdef MONITOR ! 124: for (pp = Monitor; pp < End_monitor; pp++) ! 125: check(pp, y, x); ! 126: # endif MONITOR ! 127: break; ! 128: case WALL5: ! 129: switch (bp->b_face) { ! 130: case LEFTS: ! 131: bp->b_face = ABOVE; ! 132: break; ! 133: case RIGHT: ! 134: bp->b_face = BELOW; ! 135: break; ! 136: case ABOVE: ! 137: bp->b_face = LEFTS; ! 138: break; ! 139: case BELOW: ! 140: bp->b_face = RIGHT; ! 141: break; ! 142: } ! 143: Maze[y][x] = WALL4; ! 144: # ifdef MONITOR ! 145: for (pp = Monitor; pp < End_monitor; pp++) ! 146: check(pp, y, x); ! 147: # endif MONITOR ! 148: break; ! 149: # endif REFLECT ! 150: # ifdef RANDOM ! 151: case DOOR: ! 152: switch (rand_num(4)) { ! 153: case 0: ! 154: bp->b_face = ABOVE; ! 155: break; ! 156: case 1: ! 157: bp->b_face = BELOW; ! 158: break; ! 159: case 2: ! 160: bp->b_face = LEFTS; ! 161: break; ! 162: case 3: ! 163: bp->b_face = RIGHT; ! 164: break; ! 165: } ! 166: break; ! 167: # endif RANDOM ! 168: case LEFTS: ! 169: case RIGHT: ! 170: case BELOW: ! 171: case ABOVE: ! 172: # ifdef FLY ! 173: case FLYER: ! 174: # endif FLY ! 175: /* ! 176: * give the person a chance to catch a ! 177: * grenade if s/he is facing it ! 178: */ ! 179: if (rand_num(100) < 10 ! 180: && opposite(bp->b_face, Maze[y][x])) { ! 181: if (bp->b_owner != NULL) ! 182: message(bp->b_owner, ! 183: "Your charge was absorbed!"); ! 184: pp = play_at(y, x); ! 185: pp->p_ammo += bp->b_charge; ! 186: (void) sprintf(Buf, ! 187: "Absorbed charge (good shield!)"); ! 188: message(pp, Buf); ! 189: free((char *) bp); ! 190: (void) sprintf(Buf, "%3d", pp->p_ammo); ! 191: cgoto(pp, STAT_AMMO_ROW, STAT_VALUE_COL); ! 192: outstr(pp, Buf, 3); ! 193: goto next_bullet; ! 194: } ! 195: /* FALLTHROUGH */ ! 196: # ifndef RANDOM ! 197: case DOOR: ! 198: # endif RANDOM ! 199: case WALL1: ! 200: case WALL2: ! 201: case WALL3: ! 202: bp->b_expl = TRUE; ! 203: break; ! 204: } ! 205: ! 206: bp->b_x = x; ! 207: bp->b_y = y; ! 208: } ! 209: ! 210: bp->b_next = Bullets; ! 211: Bullets = bp; ! 212: next_bullet: ! 213: ; ! 214: } ! 215: ! 216: blist = Bullets; ! 217: Bullets = NULL; ! 218: for (bp = blist; bp != NULL; bp = next) { ! 219: next = bp->b_next; ! 220: if (!bp->b_expl) { ! 221: save_bullet(bp); ! 222: # ifdef MONITOR ! 223: for (pp = Monitor; pp < End_monitor; pp++) ! 224: check(pp, bp->b_y, bp->b_x); ! 225: # endif MONITOR ! 226: continue; ! 227: } ! 228: ! 229: chkshot(bp); ! 230: free((char *) bp); ! 231: } ! 232: for (pp = Player; pp < End_player; pp++) ! 233: Maze[pp->p_y][pp->p_x] = pp->p_face; ! 234: ret: ! 235: for (pp = Player; pp < End_player; pp++) { ! 236: # ifdef FLY ! 237: if (pp->p_flying >= 0) { ! 238: Maze[pp->p_y][pp->p_x] = pp->p_over; ! 239: x = pp->p_x + pp->p_flyx; ! 240: y = pp->p_y + pp->p_flyy; ! 241: if (x < 1) { ! 242: x = 1 - x; ! 243: pp->p_flyx = -pp->p_flyx; ! 244: } ! 245: else if (x > WIDTH - 2) { ! 246: x = (WIDTH - 2) - (x - (WIDTH - 2)); ! 247: pp->p_flyx = -pp->p_flyx; ! 248: } ! 249: if (y < 1) { ! 250: y = 1 - y; ! 251: pp->p_flyy = -pp->p_flyy; ! 252: } ! 253: else if (y > HEIGHT - 2) { ! 254: y = (HEIGHT - 2) - (y - (HEIGHT - 2)); ! 255: pp->p_flyy = -pp->p_flyy; ! 256: } ! 257: again: switch (Maze[y][x]) { ! 258: case LEFTS: ! 259: case RIGHT: ! 260: case ABOVE: ! 261: case BELOW: ! 262: case FLYER: ! 263: switch (rand_num(4)) { ! 264: case 0: ! 265: PLUS_DELTA(x, WIDTH - 2); ! 266: break; ! 267: case 1: ! 268: MINUS_DELTA(x, 1); ! 269: break; ! 270: case 2: ! 271: PLUS_DELTA(y, HEIGHT - 2); ! 272: break; ! 273: case 3: ! 274: MINUS_DELTA(y, 1); ! 275: break; ! 276: } ! 277: goto again; ! 278: case WALL1: ! 279: case WALL2: ! 280: case WALL3: ! 281: # ifdef REFLECT ! 282: case WALL4: ! 283: case WALL5: ! 284: # endif REFLECT ! 285: # ifdef RANDOM ! 286: case DOOR: ! 287: # endif RANDOM ! 288: if (pp->p_flying == 0) ! 289: pp->p_flying++; ! 290: break; ! 291: case MINE: ! 292: checkdam(pp, NULL, NULL, MINDAM, MINE); ! 293: Maze[y][x] = SPACE; ! 294: break; ! 295: case GMINE: ! 296: checkdam(pp, NULL, NULL, MINDAM, GMINE); ! 297: checkdam(pp, NULL, NULL, MINDAM, GMINE); ! 298: Maze[y][x] = SPACE; ! 299: break; ! 300: } ! 301: pp->p_y = y; ! 302: pp->p_x = x; ! 303: pp->p_over = Maze[y][x]; ! 304: if (pp->p_flying-- == 0) { ! 305: checkdam(pp, NULL, NULL, ! 306: rand_num(pp->p_damage / 5), FALL); ! 307: rand_face(pp); ! 308: showstat(pp); ! 309: } ! 310: Maze[y][x] = pp->p_face; ! 311: showexpl(y, x, pp->p_face); ! 312: } ! 313: # endif FLY ! 314: sendcom(pp, REFRESH); /* Flush out the explosions */ ! 315: look(pp); ! 316: sendcom(pp, REFRESH); ! 317: } ! 318: # ifdef MONITOR ! 319: for (pp = Monitor; pp < End_monitor; pp++) ! 320: sendcom(pp, REFRESH); ! 321: # endif MONITOR ! 322: ! 323: # ifdef CONSTANT_MOVE ! 324: if (Bullets != NULL) { ! 325: bul_alarm(1); ! 326: return; ! 327: } ! 328: for (i = 0; i < EXPLEN; i++) ! 329: if (Expl[i] != NULL) { ! 330: bul_alarm(1); ! 331: return; ! 332: } ! 333: bul_alarm(0); ! 334: # endif CONSTANT_MOVE ! 335: ! 336: return; ! 337: } ! 338: ! 339: save_bullet(bp) ! 340: register BULLET *bp; ! 341: { ! 342: bp->b_over = Maze[bp->b_y][bp->b_x]; ! 343: switch (bp->b_over) { ! 344: case SHOT: ! 345: case GRENADE: ! 346: case SATCHEL: ! 347: case BOMB: ! 348: # ifdef OOZE ! 349: case SLIME: ! 350: # ifdef VOLCANO ! 351: case LAVA: ! 352: # endif VOLCANO ! 353: # endif OOZE ! 354: find_under(Bullets, bp); ! 355: break; ! 356: } ! 357: ! 358: switch (bp->b_over) { ! 359: case LEFTS: ! 360: case RIGHT: ! 361: case ABOVE: ! 362: case BELOW: ! 363: # ifdef FLY ! 364: case FLYER: ! 365: # endif FLY ! 366: mark_player(bp); ! 367: break; ! 368: ! 369: default: ! 370: Maze[bp->b_y][bp->b_x] = bp->b_type; ! 371: break; ! 372: } ! 373: ! 374: bp->b_next = Bullets; ! 375: Bullets = bp; ! 376: } ! 377: ! 378: /* ! 379: * chkshot ! 380: * Handle explosions ! 381: */ ! 382: chkshot(bp) ! 383: register BULLET *bp; ! 384: { ! 385: register int y, x; ! 386: register int dy, dx, absdy; ! 387: register int delta, damage; ! 388: register char expl; ! 389: register PLAYER *pp; ! 390: ! 391: switch (bp->b_type) { ! 392: case SHOT: ! 393: case MINE: ! 394: delta = 0; ! 395: break; ! 396: case GRENADE: ! 397: case GMINE: ! 398: delta = 1; ! 399: break; ! 400: case SATCHEL: ! 401: delta = 2; ! 402: break; ! 403: case BOMB: ! 404: delta = 3; ! 405: break; ! 406: # ifdef OOZE ! 407: case SLIME: ! 408: # ifdef VOLCANO ! 409: case LAVA: ! 410: # endif VOLCANO ! 411: chkslime(bp); ! 412: return; ! 413: # endif OOZE ! 414: } ! 415: for (y = bp->b_y - delta; y <= bp->b_y + delta; y++) { ! 416: if (y < 0 || y >= HEIGHT) ! 417: continue; ! 418: dy = y - bp->b_y; ! 419: absdy = (dy < 0) ? -dy : dy; ! 420: for (x = bp->b_x - delta; x <= bp->b_x + delta; x++) { ! 421: if (x < 0 || x >= WIDTH) ! 422: continue; ! 423: dx = x - bp->b_x; ! 424: if (dx == 0) ! 425: expl = (dy == 0) ? '*' : '|'; ! 426: else if (dy == 0) ! 427: expl = '-'; ! 428: else if (dx == dy) ! 429: expl = '\\'; ! 430: else if (dx == -dy) ! 431: expl = '/'; ! 432: else ! 433: expl = '*'; ! 434: showexpl(y, x, expl); ! 435: switch (Maze[y][x]) { ! 436: case LEFTS: ! 437: case RIGHT: ! 438: case ABOVE: ! 439: case BELOW: ! 440: # ifdef FLY ! 441: case FLYER: ! 442: # endif FLY ! 443: if (dx < 0) ! 444: dx = -dx; ! 445: if (absdy > dx) ! 446: damage = delta - absdy + 1; ! 447: else ! 448: damage = delta - dx + 1; ! 449: pp = play_at(y, x); ! 450: while (damage-- > 0) ! 451: checkdam(pp, bp->b_owner, bp->b_score, ! 452: MINDAM, bp->b_type); ! 453: break; ! 454: case GMINE: ! 455: case MINE: ! 456: add_shot((Maze[y][x] == GMINE) ? ! 457: GRENADE : SHOT, ! 458: y, x, LEFTS, ! 459: (Maze[y][x] == GMINE) ? ! 460: GRENREQ : BULREQ, ! 461: (PLAYER *) NULL, TRUE, SPACE); ! 462: Maze[y][x] = SPACE; ! 463: break; ! 464: } ! 465: } ! 466: } ! 467: } ! 468: ! 469: # ifdef OOZE ! 470: /* ! 471: * chkslime: ! 472: * handle slime shot exploding ! 473: */ ! 474: chkslime(bp) ! 475: register BULLET *bp; ! 476: { ! 477: register BULLET *nbp; ! 478: ! 479: switch (Maze[bp->b_y][bp->b_x]) { ! 480: case WALL1: ! 481: case WALL2: ! 482: case WALL3: ! 483: # ifdef REFLECT ! 484: case WALL4: ! 485: case WALL5: ! 486: # endif REFLECT ! 487: # ifdef RANDOM ! 488: case DOOR: ! 489: # endif RANDOM ! 490: switch (bp->b_face) { ! 491: case LEFTS: ! 492: bp->b_x++; ! 493: break; ! 494: case RIGHT: ! 495: bp->b_x--; ! 496: break; ! 497: case ABOVE: ! 498: bp->b_y++; ! 499: break; ! 500: case BELOW: ! 501: bp->b_y--; ! 502: break; ! 503: } ! 504: break; ! 505: } ! 506: nbp = (BULLET *) malloc(sizeof (BULLET)); ! 507: *nbp = *bp; ! 508: # ifdef VOLCANO ! 509: moveslime(nbp, nbp->b_type == SLIME ? SLIMESPEED : LAVASPEED); ! 510: # else VOLCANO ! 511: moveslime(nbp, SLIMESPEED); ! 512: # endif VOLCANO ! 513: } ! 514: ! 515: /* ! 516: * moveslime: ! 517: * move the given slime shot speed times and add it back if ! 518: * it hasn't fizzled yet ! 519: */ ! 520: moveslime(bp, speed) ! 521: register BULLET *bp; ! 522: register int speed; ! 523: { ! 524: register int i, j, dirmask, count; ! 525: register PLAYER *pp; ! 526: register BULLET *nbp; ! 527: ! 528: if (speed == 0) { ! 529: if (bp->b_charge <= 0) ! 530: free((char *) bp); ! 531: else ! 532: save_bullet(bp); ! 533: return; ! 534: } ! 535: ! 536: # ifdef VOLCANO ! 537: showexpl(bp->b_y, bp->b_x, bp->b_type == LAVA ? LAVA : '*'); ! 538: # else VOLCANO ! 539: showexpl(bp->b_y, bp->b_x, '*'); ! 540: # endif VOLCANO ! 541: switch (Maze[bp->b_y][bp->b_x]) { ! 542: case LEFTS: ! 543: case RIGHT: ! 544: case ABOVE: ! 545: case BELOW: ! 546: # ifdef FLY ! 547: case FLYER: ! 548: # endif FLY ! 549: pp = play_at(bp->b_y, bp->b_x); ! 550: message(pp, "You've been slimed."); ! 551: checkdam(pp, bp->b_owner, bp->b_score, MINDAM, bp->b_type); ! 552: break; ! 553: } ! 554: ! 555: if (--bp->b_charge <= 0) { ! 556: free((char *) bp); ! 557: return; ! 558: } ! 559: ! 560: dirmask = 0; ! 561: count = 0; ! 562: switch (bp->b_face) { ! 563: case LEFTS: ! 564: if (!iswall(bp->b_y, bp->b_x - 1)) ! 565: dirmask |= WEST, count++; ! 566: if (!iswall(bp->b_y - 1, bp->b_x)) ! 567: dirmask |= NORTH, count++; ! 568: if (!iswall(bp->b_y + 1, bp->b_x)) ! 569: dirmask |= SOUTH, count++; ! 570: if (dirmask == 0) ! 571: if (!iswall(bp->b_y, bp->b_x + 1)) ! 572: dirmask |= EAST, count++; ! 573: break; ! 574: case RIGHT: ! 575: if (!iswall(bp->b_y, bp->b_x + 1)) ! 576: dirmask |= EAST, count++; ! 577: if (!iswall(bp->b_y - 1, bp->b_x)) ! 578: dirmask |= NORTH, count++; ! 579: if (!iswall(bp->b_y + 1, bp->b_x)) ! 580: dirmask |= SOUTH, count++; ! 581: if (dirmask == 0) ! 582: if (!iswall(bp->b_y, bp->b_x - 1)) ! 583: dirmask |= WEST, count++; ! 584: break; ! 585: case ABOVE: ! 586: if (!iswall(bp->b_y - 1, bp->b_x)) ! 587: dirmask |= NORTH, count++; ! 588: if (!iswall(bp->b_y, bp->b_x - 1)) ! 589: dirmask |= WEST, count++; ! 590: if (!iswall(bp->b_y, bp->b_x + 1)) ! 591: dirmask |= EAST, count++; ! 592: if (dirmask == 0) ! 593: if (!iswall(bp->b_y + 1, bp->b_x)) ! 594: dirmask |= SOUTH, count++; ! 595: break; ! 596: case BELOW: ! 597: if (!iswall(bp->b_y + 1, bp->b_x)) ! 598: dirmask |= SOUTH, count++; ! 599: if (!iswall(bp->b_y, bp->b_x - 1)) ! 600: dirmask |= WEST, count++; ! 601: if (!iswall(bp->b_y, bp->b_x + 1)) ! 602: dirmask |= EAST, count++; ! 603: if (dirmask == 0) ! 604: if (!iswall(bp->b_y - 1, bp->b_x)) ! 605: dirmask |= NORTH, count++; ! 606: break; ! 607: } ! 608: if (count == 0) { ! 609: /* ! 610: * No place to go. Just sit here for a while and wait ! 611: * for adjacent squares to clear out. ! 612: */ ! 613: save_bullet(bp); ! 614: return; ! 615: } ! 616: if (bp->b_charge < count) { ! 617: /* Only bp->b_charge paths may be taken */ ! 618: while (count > bp->b_charge) { ! 619: if (dirmask & WEST) ! 620: dirmask &= ~WEST; ! 621: else if (dirmask & EAST) ! 622: dirmask &= ~EAST; ! 623: else if (dirmask & NORTH) ! 624: dirmask &= ~NORTH; ! 625: else if (dirmask & SOUTH) ! 626: dirmask &= ~SOUTH; ! 627: count--; ! 628: } ! 629: } ! 630: ! 631: i = bp->b_charge / count; ! 632: j = bp->b_charge % count; ! 633: if (dirmask & WEST) { ! 634: count--; ! 635: nbp = create_shot(bp->b_type, bp->b_y, bp->b_x - 1, LEFTS, ! 636: i, bp->b_owner, bp->b_score, TRUE, SPACE); ! 637: moveslime(nbp, speed - 1); ! 638: } ! 639: if (dirmask & EAST) { ! 640: count--; ! 641: nbp = create_shot(bp->b_type, bp->b_y, bp->b_x + 1, RIGHT, ! 642: (count < j) ? i + 1 : i, bp->b_owner, bp->b_score, ! 643: TRUE, SPACE); ! 644: moveslime(nbp, speed - 1); ! 645: } ! 646: if (dirmask & NORTH) { ! 647: count--; ! 648: nbp = create_shot(bp->b_type, bp->b_y - 1, bp->b_x, ABOVE, ! 649: (count < j) ? i + 1 : i, bp->b_owner, bp->b_score, ! 650: TRUE, SPACE); ! 651: moveslime(nbp, speed - 1); ! 652: } ! 653: if (dirmask & SOUTH) { ! 654: count--; ! 655: nbp = create_shot(bp->b_type, bp->b_y + 1, bp->b_x, BELOW, ! 656: (count < j) ? i + 1 : i, bp->b_owner, bp->b_score, ! 657: TRUE, SPACE); ! 658: moveslime(nbp, speed - 1); ! 659: } ! 660: ! 661: free((char *) bp); ! 662: } ! 663: ! 664: /* ! 665: * iswall: ! 666: * returns whether the given location is a wall ! 667: */ ! 668: iswall(y, x) ! 669: register int y, x; ! 670: { ! 671: if (y < 0 || x < 0 || y >= HEIGHT || x >= WIDTH) ! 672: return TRUE; ! 673: switch (Maze[y][x]) { ! 674: case WALL1: ! 675: case WALL2: ! 676: case WALL3: ! 677: # ifdef REFLECT ! 678: case WALL4: ! 679: case WALL5: ! 680: # endif REFLECT ! 681: # ifdef RANDOM ! 682: case DOOR: ! 683: # endif RANDOM ! 684: # ifdef VOLCANO ! 685: case LAVA: ! 686: # endif VOLCANO ! 687: return TRUE; ! 688: } ! 689: return FALSE; ! 690: } ! 691: # endif OOZE ! 692: ! 693: /* ! 694: * zapshot: ! 695: * Take a shot out of the air. ! 696: */ ! 697: zapshot(blist, obp) ! 698: register BULLET *blist, *obp; ! 699: { ! 700: register BULLET *bp; ! 701: register FLAG explode; ! 702: ! 703: explode = FALSE; ! 704: for (bp = blist; bp != NULL; bp = bp->b_next) { ! 705: if (bp->b_x != obp->b_x || bp->b_y != obp->b_y) ! 706: continue; ! 707: if (bp->b_face == obp->b_face) ! 708: continue; ! 709: explode = TRUE; ! 710: break; ! 711: } ! 712: if (!explode) ! 713: return; ! 714: explshot(blist, obp->b_y, obp->b_x); ! 715: } ! 716: ! 717: /* ! 718: * explshot - ! 719: * Make all shots at this location blow up ! 720: */ ! 721: explshot(blist, y, x) ! 722: register BULLET *blist; ! 723: register int y, x; ! 724: { ! 725: register BULLET *bp; ! 726: ! 727: for (bp = blist; bp != NULL; bp = bp->b_next) ! 728: if (bp->b_x == x && bp->b_y == y) { ! 729: bp->b_expl = TRUE; ! 730: if (bp->b_owner != NULL) ! 731: message(bp->b_owner, "Shot intercepted"); ! 732: } ! 733: } ! 734: ! 735: /* ! 736: * play_at: ! 737: * Return a pointer to the player at the given location ! 738: */ ! 739: PLAYER * ! 740: play_at(y, x) ! 741: register int y, x; ! 742: { ! 743: register PLAYER *pp; ! 744: ! 745: for (pp = Player; pp < End_player; pp++) ! 746: if (pp->p_x == x && pp->p_y == y) ! 747: return pp; ! 748: fprintf(stderr, "driver: couldn't find player at (%d,%d)\n", x, y); ! 749: abort(); ! 750: /* NOTREACHED */ ! 751: } ! 752: ! 753: /* ! 754: * opposite: ! 755: * Return TRUE if the bullet direction faces the opposite direction ! 756: * of the player in the maze ! 757: */ ! 758: opposite(face, dir) ! 759: int face; ! 760: char dir; ! 761: { ! 762: switch (face) { ! 763: case LEFTS: ! 764: return (dir == RIGHT); ! 765: case RIGHT: ! 766: return (dir == LEFTS); ! 767: case ABOVE: ! 768: return (dir == BELOW); ! 769: case BELOW: ! 770: return (dir == ABOVE); ! 771: default: ! 772: return FALSE; ! 773: } ! 774: } ! 775: ! 776: /* ! 777: * is_bullet: ! 778: * Is there a bullet at the given coordinates? If so, return ! 779: * a pointer to the bullet, otherwise return NULL ! 780: */ ! 781: BULLET * ! 782: is_bullet(y, x) ! 783: register int y, x; ! 784: { ! 785: register BULLET *bp; ! 786: ! 787: for (bp = Bullets; bp != NULL; bp = bp->b_next) ! 788: if (bp->b_y == y && bp->b_x == x) ! 789: return bp; ! 790: return NULL; ! 791: } ! 792: ! 793: /* ! 794: * fixshots: ! 795: * change the underlying character of the shots at a location ! 796: * to the given character. ! 797: */ ! 798: fixshots(y, x, over) ! 799: register int y, x; ! 800: char over; ! 801: { ! 802: register BULLET *bp; ! 803: ! 804: for (bp = Bullets; bp != NULL; bp = bp->b_next) ! 805: if (bp->b_y == y && bp->b_x == x) ! 806: bp->b_over = over; ! 807: } ! 808: ! 809: /* ! 810: * find_under: ! 811: * find the underlying character for a bullet when it lands ! 812: * on another bullet. ! 813: */ ! 814: find_under(blist, bp) ! 815: register BULLET *blist, *bp; ! 816: { ! 817: register BULLET *nbp; ! 818: ! 819: for (nbp = blist; nbp != NULL; nbp = nbp->b_next) ! 820: if (bp->b_y == nbp->b_y && bp->b_x == nbp->b_x) { ! 821: bp->b_over = nbp->b_over; ! 822: break; ! 823: } ! 824: } ! 825: ! 826: /* ! 827: * mark_player: ! 828: * mark a player as under a shot ! 829: */ ! 830: mark_player(bp) ! 831: register BULLET *bp; ! 832: { ! 833: register PLAYER *pp; ! 834: ! 835: for (pp = Player; pp < End_player; pp++) ! 836: if (pp->p_y == bp->b_y && pp->p_x == bp->b_x) { ! 837: pp->p_undershot = TRUE; ! 838: break; ! 839: } ! 840: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.