|
|
1.1 ! root 1: /* ! 2: * zap.c ! 3: * ! 4: * This source herein may be modified and/or distributed by anybody who ! 5: * so desires, with the following restrictions: ! 6: * 1.) No portion of this notice shall be removed. ! 7: * 2.) Credit shall not be taken for the creation of this source. ! 8: * 3.) This code is not to be traded, sold, or used for personal ! 9: * gain or profit. ! 10: * ! 11: */ ! 12: ! 13: #ifndef lint ! 14: static char sccsid[] = "@(#)zap.c 5.1 (Berkeley) 11/25/87"; ! 15: #endif /* not lint */ ! 16: ! 17: #include "rogue.h" ! 18: ! 19: boolean wizard = 0; ! 20: ! 21: extern boolean being_held, score_only, detect_monster; ! 22: extern short cur_room; ! 23: ! 24: zapp() ! 25: { ! 26: short wch; ! 27: boolean first_miss = 1; ! 28: object *wand; ! 29: short dir, d, row, col; ! 30: object *monster; ! 31: ! 32: while (!is_direction(dir = rgetchar(), &d)) { ! 33: sound_bell(); ! 34: if (first_miss) { ! 35: message("direction? ", 0); ! 36: first_miss = 0; ! 37: } ! 38: } ! 39: check_message(); ! 40: if (dir == CANCEL) { ! 41: return; ! 42: } ! 43: if ((wch = pack_letter("zap with what?", WAND)) == CANCEL) { ! 44: return; ! 45: } ! 46: check_message(); ! 47: ! 48: if (!(wand = get_letter_object(wch))) { ! 49: message("no such item.", 0); ! 50: return; ! 51: } ! 52: if (wand->what_is != WAND) { ! 53: message("you can't zap with that", 0); ! 54: return; ! 55: } ! 56: if (wand->class <= 0) { ! 57: message("nothing happens", 0); ! 58: } else { ! 59: wand->class--; ! 60: row = rogue.row; col = rogue.col; ! 61: if ((wand->which_kind == COLD) || (wand->which_kind == FIRE)) { ! 62: bounce((short) wand->which_kind, d, row, col, 0); ! 63: } else { ! 64: monster = get_zapped_monster(d, &row, &col); ! 65: if (wand->which_kind == DRAIN_LIFE) { ! 66: wdrain_life(monster); ! 67: } else if (monster) { ! 68: wake_up(monster); ! 69: s_con_mon(monster); ! 70: zap_monster(monster, wand->which_kind); ! 71: relight(); ! 72: } ! 73: } ! 74: } ! 75: (void) reg_move(); ! 76: } ! 77: ! 78: object * ! 79: get_zapped_monster(dir, row, col) ! 80: short dir; ! 81: short *row, *col; ! 82: { ! 83: short orow, ocol; ! 84: ! 85: for (;;) { ! 86: orow = *row; ocol = *col; ! 87: get_dir_rc(dir, row, col, 0); ! 88: if (((*row == orow) && (*col == ocol)) || ! 89: (dungeon[*row][*col] & (HORWALL | VERTWALL)) || ! 90: (dungeon[*row][*col] == NOTHING)) { ! 91: return(0); ! 92: } ! 93: if (dungeon[*row][*col] & MONSTER) { ! 94: if (!imitating(*row, *col)) { ! 95: return(object_at(&level_monsters, *row, *col)); ! 96: } ! 97: } ! 98: } ! 99: } ! 100: ! 101: zap_monster(monster, kind) ! 102: object *monster; ! 103: unsigned short kind; ! 104: { ! 105: short row, col; ! 106: object *nm; ! 107: short tc; ! 108: ! 109: row = monster->row; ! 110: col = monster->col; ! 111: ! 112: switch(kind) { ! 113: case SLOW_MONSTER: ! 114: if (monster->m_flags & HASTED) { ! 115: monster->m_flags &= (~HASTED); ! 116: } else { ! 117: monster->slowed_toggle = 0; ! 118: monster->m_flags |= SLOWED; ! 119: } ! 120: break; ! 121: case HASTE_MONSTER: ! 122: if (monster->m_flags & SLOWED) { ! 123: monster->m_flags &= (~SLOWED); ! 124: } else { ! 125: monster->m_flags |= HASTED; ! 126: } ! 127: break; ! 128: case TELE_AWAY: ! 129: tele_away(monster); ! 130: break; ! 131: case INVISIBILITY: ! 132: monster->m_flags |= INVISIBLE; ! 133: break; ! 134: case POLYMORPH: ! 135: if (monster->m_flags & HOLDS) { ! 136: being_held = 0; ! 137: } ! 138: nm = monster->next_monster; ! 139: tc = monster->trail_char; ! 140: (void) gr_monster(monster, get_rand(0, MONSTERS-1)); ! 141: monster->row = row; ! 142: monster->col = col; ! 143: monster->next_monster = nm; ! 144: monster->trail_char = tc; ! 145: if (!(monster->m_flags & IMITATES)) { ! 146: wake_up(monster); ! 147: } ! 148: break; ! 149: case MAGIC_MISSILE: ! 150: rogue_hit(monster, 1); ! 151: break; ! 152: case CANCELLATION: ! 153: if (monster->m_flags & HOLDS) { ! 154: being_held = 0; ! 155: } ! 156: if (monster->m_flags & STEALS_ITEM) { ! 157: monster->drop_percent = 0; ! 158: } ! 159: monster->m_flags &= (~(FLIES | FLITS | SPECIAL_HIT | INVISIBLE | ! 160: FLAMES | IMITATES | CONFUSES | SEEKS_GOLD | HOLDS)); ! 161: break; ! 162: case DO_NOTHING: ! 163: message("nothing happens", 0); ! 164: break; ! 165: } ! 166: } ! 167: ! 168: tele_away(monster) ! 169: object *monster; ! 170: { ! 171: short row, col; ! 172: ! 173: if (monster->m_flags & HOLDS) { ! 174: being_held = 0; ! 175: } ! 176: gr_row_col(&row, &col, (FLOOR | TUNNEL | STAIRS | OBJECT)); ! 177: mvaddch(monster->row, monster->col, monster->trail_char); ! 178: dungeon[monster->row][monster->col] &= ~MONSTER; ! 179: monster->row = row; monster->col = col; ! 180: dungeon[row][col] |= MONSTER; ! 181: monster->trail_char = mvinch(row, col); ! 182: if (detect_monster || rogue_can_see(row, col)) { ! 183: mvaddch(row, col, gmc(monster)); ! 184: } ! 185: } ! 186: ! 187: wizardize() ! 188: { ! 189: char buf[100]; ! 190: ! 191: if (wizard) { ! 192: wizard = 0; ! 193: message("not wizard anymore", 0); ! 194: } else { ! 195: if (get_input_line("wizard's password:", "", buf, "", 0, 0)) { ! 196: (void) xxx(1); ! 197: xxxx(buf, strlen(buf)); ! 198: if (!strncmp(buf, "\247\104\126\272\115\243\027", 7)) { ! 199: wizard = 1; ! 200: score_only = 1; ! 201: message("Welcome, mighty wizard!", 0); ! 202: } else { ! 203: message("sorry", 0); ! 204: } ! 205: } ! 206: } ! 207: } ! 208: ! 209: wdrain_life(monster) ! 210: object *monster; ! 211: { ! 212: short hp; ! 213: object *lmon, *nm; ! 214: ! 215: hp = rogue.hp_current / 3; ! 216: rogue.hp_current = (rogue.hp_current + 1) / 2; ! 217: ! 218: if (cur_room >= 0) { ! 219: lmon = level_monsters.next_monster; ! 220: while (lmon) { ! 221: nm = lmon->next_monster; ! 222: if (get_room_number(lmon->row, lmon->col) == cur_room) { ! 223: wake_up(lmon); ! 224: (void) mon_damage(lmon, hp); ! 225: } ! 226: lmon = nm; ! 227: } ! 228: } else { ! 229: if (monster) { ! 230: wake_up(monster); ! 231: (void) mon_damage(monster, hp); ! 232: } ! 233: } ! 234: print_stats(STAT_HP); ! 235: relight(); ! 236: } ! 237: ! 238: bounce(ball, dir, row, col, r) ! 239: short ball, dir, row, col, r; ! 240: { ! 241: short orow, ocol; ! 242: char buf[DCOLS], *s; ! 243: short i, ch, new_dir = -1, damage; ! 244: static short btime; ! 245: ! 246: if (++r == 1) { ! 247: btime = get_rand(3, 6); ! 248: } else if (r > btime) { ! 249: return; ! 250: } ! 251: ! 252: if (ball == FIRE) { ! 253: s = "fire"; ! 254: } else { ! 255: s = "ice"; ! 256: } ! 257: if (r > 1) { ! 258: sprintf(buf, "the %s bounces", s); ! 259: message(buf, 0); ! 260: } ! 261: orow = row; ! 262: ocol = col; ! 263: do { ! 264: ch = mvinch(orow, ocol); ! 265: standout(); ! 266: mvaddch(orow, ocol, ch); ! 267: get_dir_rc(dir, &orow, &ocol, 1); ! 268: } while (!( (ocol <= 0) || ! 269: (ocol >= DCOLS-1) || ! 270: (dungeon[orow][ocol] == NOTHING) || ! 271: (dungeon[orow][ocol] & MONSTER) || ! 272: (dungeon[orow][ocol] & (HORWALL | VERTWALL)) || ! 273: ((orow == rogue.row) && (ocol == rogue.col)))); ! 274: standend(); ! 275: refresh(); ! 276: do { ! 277: orow = row; ! 278: ocol = col; ! 279: ch = mvinch(row, col); ! 280: mvaddch(row, col, ch); ! 281: get_dir_rc(dir, &row, &col, 1); ! 282: } while (!( (col <= 0) || ! 283: (col >= DCOLS-1) || ! 284: (dungeon[row][col] == NOTHING) || ! 285: (dungeon[row][col] & MONSTER) || ! 286: (dungeon[row][col] & (HORWALL | VERTWALL)) || ! 287: ((row == rogue.row) && (col == rogue.col)))); ! 288: ! 289: if (dungeon[row][col] & MONSTER) { ! 290: object *monster; ! 291: ! 292: monster = object_at(&level_monsters, row, col); ! 293: ! 294: wake_up(monster); ! 295: if (rand_percent(33)) { ! 296: sprintf(buf, "the %s misses the %s", s, mon_name(monster)); ! 297: message(buf, 0); ! 298: goto ND; ! 299: } ! 300: if (ball == FIRE) { ! 301: if (!(monster->m_flags & RUSTS)) { ! 302: if (monster->m_flags & FREEZES) { ! 303: damage = monster->hp_to_kill; ! 304: } else if (monster->m_flags & FLAMES) { ! 305: damage = (monster->hp_to_kill / 10) + 1; ! 306: } else { ! 307: damage = get_rand((rogue.hp_current / 3), rogue.hp_max); ! 308: } ! 309: } else { ! 310: damage = (monster->hp_to_kill / 2) + 1; ! 311: } ! 312: sprintf(buf, "the %s hits the %s", s, mon_name(monster)); ! 313: message(buf, 0); ! 314: (void) mon_damage(monster, damage); ! 315: } else { ! 316: damage = -1; ! 317: if (!(monster->m_flags & FREEZES)) { ! 318: if (rand_percent(33)) { ! 319: message("the monster is frozen", 0); ! 320: monster->m_flags |= (ASLEEP | NAPPING); ! 321: monster->nap_length = get_rand(3, 6); ! 322: } else { ! 323: damage = rogue.hp_current / 4; ! 324: } ! 325: } else { ! 326: damage = -2; ! 327: } ! 328: if (damage != -1) { ! 329: sprintf(buf, "the %s hits the %s", s, mon_name(monster)); ! 330: message(buf, 0); ! 331: (void) mon_damage(monster, damage); ! 332: } ! 333: } ! 334: } else if ((row == rogue.row) && (col == rogue.col)) { ! 335: if (rand_percent(10 + (3 * get_armor_class(rogue.armor)))) { ! 336: sprintf(buf, "the %s misses", s); ! 337: message(buf, 0); ! 338: goto ND; ! 339: } else { ! 340: damage = get_rand(3, (3 * rogue.exp)); ! 341: if (ball == FIRE) { ! 342: damage = (damage * 3) / 2; ! 343: damage -= get_armor_class(rogue.armor); ! 344: } ! 345: sprintf(buf, "the %s hits", s); ! 346: rogue_damage(damage, (object *) 0, ! 347: ((ball == FIRE) ? KFIRE : HYPOTHERMIA)); ! 348: message(buf, 0); ! 349: } ! 350: } else { ! 351: short nrow, ncol; ! 352: ! 353: ND: for (i = 0; i < 10; i++) { ! 354: dir = get_rand(0, DIRS-1); ! 355: nrow = orow; ! 356: ncol = ocol; ! 357: get_dir_rc(dir, &nrow, &ncol, 1); ! 358: if (((ncol >= 0) && (ncol <= DCOLS-1)) && ! 359: (dungeon[nrow][ncol] != NOTHING) && ! 360: (!(dungeon[nrow][ncol] & (VERTWALL | HORWALL)))) { ! 361: new_dir = dir; ! 362: break; ! 363: } ! 364: } ! 365: if (new_dir != -1) { ! 366: bounce(ball, new_dir, orow, ocol, r); ! 367: } ! 368: } ! 369: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.