1 1.11 dholland /* $NetBSD: hack.read.c,v 1.11 2011/08/06 20:29:37 dholland Exp $ */ 2 1.4 christos 3 1.2 mycroft /* 4 1.8 jsm * Copyright (c) 1985, Stichting Centrum voor Wiskunde en Informatica, 5 1.8 jsm * Amsterdam 6 1.8 jsm * All rights reserved. 7 1.8 jsm * 8 1.8 jsm * Redistribution and use in source and binary forms, with or without 9 1.8 jsm * modification, are permitted provided that the following conditions are 10 1.8 jsm * met: 11 1.8 jsm * 12 1.8 jsm * - Redistributions of source code must retain the above copyright notice, 13 1.8 jsm * this list of conditions and the following disclaimer. 14 1.8 jsm * 15 1.8 jsm * - Redistributions in binary form must reproduce the above copyright 16 1.8 jsm * notice, this list of conditions and the following disclaimer in the 17 1.8 jsm * documentation and/or other materials provided with the distribution. 18 1.8 jsm * 19 1.8 jsm * - Neither the name of the Stichting Centrum voor Wiskunde en 20 1.8 jsm * Informatica, nor the names of its contributors may be used to endorse or 21 1.8 jsm * promote products derived from this software without specific prior 22 1.8 jsm * written permission. 23 1.8 jsm * 24 1.8 jsm * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS 25 1.8 jsm * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 26 1.8 jsm * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A 27 1.8 jsm * PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER 28 1.8 jsm * OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 29 1.8 jsm * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 30 1.8 jsm * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 31 1.8 jsm * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 32 1.8 jsm * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 33 1.8 jsm * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 34 1.8 jsm * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 35 1.8 jsm */ 36 1.8 jsm 37 1.8 jsm /* 38 1.8 jsm * Copyright (c) 1982 Jay Fenlason <hack (at) gnu.org> 39 1.8 jsm * All rights reserved. 40 1.8 jsm * 41 1.8 jsm * Redistribution and use in source and binary forms, with or without 42 1.8 jsm * modification, are permitted provided that the following conditions 43 1.8 jsm * are met: 44 1.8 jsm * 1. Redistributions of source code must retain the above copyright 45 1.8 jsm * notice, this list of conditions and the following disclaimer. 46 1.8 jsm * 2. Redistributions in binary form must reproduce the above copyright 47 1.8 jsm * notice, this list of conditions and the following disclaimer in the 48 1.8 jsm * documentation and/or other materials provided with the distribution. 49 1.8 jsm * 3. The name of the author may not be used to endorse or promote products 50 1.8 jsm * derived from this software without specific prior written permission. 51 1.8 jsm * 52 1.8 jsm * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, 53 1.8 jsm * INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY 54 1.8 jsm * AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL 55 1.8 jsm * THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 56 1.8 jsm * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 57 1.8 jsm * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; 58 1.8 jsm * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, 59 1.8 jsm * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR 60 1.8 jsm * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF 61 1.8 jsm * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 62 1.2 mycroft */ 63 1.2 mycroft 64 1.4 christos #include <sys/cdefs.h> 65 1.2 mycroft #ifndef lint 66 1.11 dholland __RCSID("$NetBSD: hack.read.c,v 1.11 2011/08/06 20:29:37 dholland Exp $"); 67 1.4 christos #endif /* not lint */ 68 1.1 cgd 69 1.4 christos #include <stdlib.h> 70 1.1 cgd #include "hack.h" 71 1.4 christos #include "extern.h" 72 1.1 cgd 73 1.10 dholland static int identify(struct obj *); 74 1.10 dholland static int monstersym(int); 75 1.10 dholland 76 1.4 christos int 77 1.9 dholland doread(void) 78 1.4 christos { 79 1.4 christos struct obj *scroll; 80 1.4 christos boolean confused = (Confusion != 0); 81 1.4 christos boolean known = FALSE; 82 1.1 cgd 83 1.1 cgd scroll = getobj("?", "read"); 84 1.4 christos if (!scroll) 85 1.4 christos return (0); 86 1.4 christos if (!scroll->dknown && Blind) { 87 1.4 christos pline("Being blind, you cannot read the formula on the scroll."); 88 1.4 christos return (0); 89 1.1 cgd } 90 1.4 christos if (Blind) 91 1.4 christos pline("As you pronounce the formula on it, the scroll disappears."); 92 1.1 cgd else 93 1.4 christos pline("As you read the scroll, it disappears."); 94 1.4 christos if (confused) 95 1.4 christos pline("Being confused, you mispronounce the magic words ... "); 96 1.1 cgd 97 1.4 christos switch (scroll->otyp) { 98 1.1 cgd #ifdef MAIL 99 1.1 cgd case SCR_MAIL: 100 1.4 christos readmail( /* scroll */ ); 101 1.1 cgd break; 102 1.4 christos #endif /* MAIL */ 103 1.1 cgd case SCR_ENCHANT_ARMOR: 104 1.4 christos { 105 1.4 christos struct obj *otmp = some_armor(); 106 1.4 christos if (!otmp) { 107 1.4 christos strange_feeling(scroll, "Your skin glows then fades."); 108 1.4 christos return (1); 109 1.4 christos } 110 1.4 christos if (confused) { 111 1.4 christos pline("Your %s glows silver for a moment.", 112 1.4 christos objects[otmp->otyp].oc_name); 113 1.4 christos otmp->rustfree = 1; 114 1.4 christos break; 115 1.4 christos } 116 1.4 christos if (otmp->spe > 3 && rn2(otmp->spe)) { 117 1.4 christos pline("Your %s glows violently green for a while, then evaporates.", 118 1.4 christos objects[otmp->otyp].oc_name); 119 1.4 christos useup(otmp); 120 1.4 christos break; 121 1.4 christos } 122 1.4 christos pline("Your %s glows green for a moment.", 123 1.4 christos objects[otmp->otyp].oc_name); 124 1.4 christos otmp->cursed = 0; 125 1.4 christos otmp->spe++; 126 1.1 cgd break; 127 1.1 cgd } 128 1.1 cgd case SCR_DESTROY_ARMOR: 129 1.4 christos if (confused) { 130 1.4 christos struct obj *otmp = some_armor(); 131 1.4 christos if (!otmp) { 132 1.4 christos strange_feeling(scroll, "Your bones itch."); 133 1.4 christos return (1); 134 1.1 cgd } 135 1.1 cgd pline("Your %s glows purple for a moment.", 136 1.4 christos objects[otmp->otyp].oc_name); 137 1.1 cgd otmp->rustfree = 0; 138 1.1 cgd break; 139 1.1 cgd } 140 1.4 christos if (uarm) { 141 1.4 christos pline("Your armor turns to dust and falls to the floor!"); 142 1.4 christos useup(uarm); 143 1.4 christos } else if (uarmh) { 144 1.4 christos pline("Your helmet turns to dust and is blown away!"); 145 1.4 christos useup(uarmh); 146 1.4 christos } else if (uarmg) { 147 1.1 cgd pline("Your gloves vanish!"); 148 1.1 cgd useup(uarmg); 149 1.1 cgd selftouch("You"); 150 1.1 cgd } else { 151 1.4 christos strange_feeling(scroll, "Your skin itches."); 152 1.4 christos return (1); 153 1.1 cgd } 154 1.1 cgd break; 155 1.1 cgd case SCR_CONFUSE_MONSTER: 156 1.4 christos if (confused) { 157 1.1 cgd pline("Your hands begin to glow purple."); 158 1.1 cgd Confusion += rnd(100); 159 1.1 cgd } else { 160 1.1 cgd pline("Your hands begin to glow blue."); 161 1.1 cgd u.umconf = 1; 162 1.1 cgd } 163 1.1 cgd break; 164 1.1 cgd case SCR_SCARE_MONSTER: 165 1.4 christos { 166 1.4 christos int ct = 0; 167 1.4 christos struct monst *mtmp; 168 1.4 christos 169 1.4 christos for (mtmp = fmon; mtmp; mtmp = mtmp->nmon) 170 1.4 christos if (cansee(mtmp->mx, mtmp->my)) { 171 1.4 christos if (confused) 172 1.4 christos mtmp->mflee = mtmp->mfroz = 173 1.4 christos mtmp->msleep = 0; 174 1.4 christos else 175 1.4 christos mtmp->mflee = 1; 176 1.4 christos ct++; 177 1.4 christos } 178 1.4 christos if (!ct) { 179 1.4 christos if (confused) 180 1.4 christos pline("You hear sad wailing in the distance."); 181 1.1 cgd else 182 1.4 christos pline("You hear maniacal laughter in the distance."); 183 1.1 cgd } 184 1.4 christos break; 185 1.1 cgd } 186 1.1 cgd case SCR_BLANK_PAPER: 187 1.4 christos if (confused) 188 1.4 christos pline("You see strange patterns on this scroll."); 189 1.1 cgd else 190 1.4 christos pline("This scroll seems to be blank."); 191 1.1 cgd break; 192 1.1 cgd case SCR_REMOVE_CURSE: 193 1.4 christos { 194 1.4 christos struct obj *obj; 195 1.4 christos if (confused) 196 1.4 christos pline("You feel like you need some help."); 197 1.4 christos else 198 1.4 christos pline("You feel like someone is helping you."); 199 1.4 christos for (obj = invent; obj; obj = obj->nobj) 200 1.4 christos if (obj->owornmask) 201 1.4 christos obj->cursed = confused; 202 1.4 christos if (Punished && !confused) { 203 1.4 christos Punished = 0; 204 1.4 christos freeobj(uchain); 205 1.4 christos unpobj(uchain); 206 1.11 dholland free(uchain); 207 1.4 christos uball->spe = 0; 208 1.4 christos uball->owornmask &= ~W_BALL; 209 1.4 christos uchain = uball = (struct obj *) 0; 210 1.4 christos } 211 1.4 christos break; 212 1.1 cgd } 213 1.1 cgd case SCR_CREATE_MONSTER: 214 1.4 christos { 215 1.4 christos int cnt = 1; 216 1.1 cgd 217 1.4 christos if (!rn2(73)) 218 1.4 christos cnt += rnd(4); 219 1.4 christos if (confused) 220 1.4 christos cnt += 12; 221 1.4 christos while (cnt--) 222 1.4 christos (void) makemon(confused ? PM_ACID_BLOB : 223 1.4 christos (struct permonst *) 0, u.ux, u.uy); 224 1.4 christos break; 225 1.4 christos } 226 1.1 cgd case SCR_ENCHANT_WEAPON: 227 1.4 christos if (uwep && confused) { 228 1.1 cgd pline("Your %s glows silver for a moment.", 229 1.4 christos objects[uwep->otyp].oc_name); 230 1.1 cgd uwep->rustfree = 1; 231 1.4 christos } else if (!chwepon(scroll, 1)) /* tests for !uwep */ 232 1.4 christos return (1); 233 1.1 cgd break; 234 1.1 cgd case SCR_DAMAGE_WEAPON: 235 1.4 christos if (uwep && confused) { 236 1.1 cgd pline("Your %s glows purple for a moment.", 237 1.4 christos objects[uwep->otyp].oc_name); 238 1.1 cgd uwep->rustfree = 0; 239 1.4 christos } else if (!chwepon(scroll, -1)) /* tests for !uwep */ 240 1.4 christos return (1); 241 1.1 cgd break; 242 1.1 cgd case SCR_TAMING: 243 1.4 christos { 244 1.4 christos int i, j; 245 1.4 christos int bd = confused ? 5 : 1; 246 1.4 christos struct monst *mtmp; 247 1.4 christos 248 1.4 christos for (i = -bd; i <= bd; i++) 249 1.4 christos for (j = -bd; j <= bd; j++) 250 1.4 christos if ((mtmp = m_at(u.ux + i, u.uy + j)) != NULL) 251 1.4 christos (void) tamedog(mtmp, (struct obj *) 0); 252 1.4 christos break; 253 1.4 christos } 254 1.1 cgd case SCR_GENOCIDE: 255 1.4 christos { 256 1.4 christos char buf[BUFSZ]; 257 1.4 christos struct monst *mtmp, *mtmp2; 258 1.1 cgd 259 1.4 christos pline("You have found a scroll of genocide!"); 260 1.4 christos known = TRUE; 261 1.4 christos if (confused) 262 1.4 christos *buf = u.usym; 263 1.4 christos else 264 1.4 christos do { 265 1.4 christos pline("What monster do you want to genocide (Type the letter)? "); 266 1.4 christos getlin(buf); 267 1.4 christos } while (strlen(buf) != 1 || !monstersym(*buf)); 268 1.4 christos if (!strchr(fut_geno, *buf)) 269 1.4 christos charcat(fut_geno, *buf); 270 1.4 christos if (!strchr(genocided, *buf)) 271 1.4 christos charcat(genocided, *buf); 272 1.4 christos else { 273 1.4 christos pline("Such monsters do not exist in this world."); 274 1.4 christos break; 275 1.4 christos } 276 1.4 christos for (mtmp = fmon; mtmp; mtmp = mtmp2) { 277 1.4 christos mtmp2 = mtmp->nmon; 278 1.4 christos if (mtmp->data->mlet == *buf) 279 1.4 christos mondead(mtmp); 280 1.4 christos } 281 1.4 christos pline("Wiped out all %c's.", *buf); 282 1.4 christos if (*buf == u.usym) { 283 1.4 christos killer = "scroll of genocide"; 284 1.4 christos u.uhp = -1; 285 1.4 christos } 286 1.1 cgd break; 287 1.1 cgd } 288 1.1 cgd case SCR_LIGHT: 289 1.4 christos if (!Blind) 290 1.4 christos known = TRUE; 291 1.1 cgd litroom(!confused); 292 1.1 cgd break; 293 1.1 cgd case SCR_TELEPORTATION: 294 1.4 christos if (confused) 295 1.1 cgd level_tele(); 296 1.1 cgd else { 297 1.1 cgd #ifdef QUEST 298 1.4 christos int oux = u.ux, ouy = u.uy; 299 1.1 cgd tele(); 300 1.4 christos if (dist(oux, ouy) > 100) 301 1.4 christos known = TRUE; 302 1.4 christos #else /* QUEST */ 303 1.4 christos int uroom = inroom(u.ux, u.uy); 304 1.1 cgd tele(); 305 1.4 christos if (uroom != inroom(u.ux, u.uy)) 306 1.4 christos known = TRUE; 307 1.4 christos #endif /* QUEST */ 308 1.1 cgd } 309 1.1 cgd break; 310 1.1 cgd case SCR_GOLD_DETECTION: 311 1.4 christos /* 312 1.4 christos * Unfortunately this code has become slightly less elegant, 313 1.4 christos * now that gold and traps no longer are of the same type. 314 1.4 christos */ 315 1.4 christos if (confused) { 316 1.4 christos struct trap *ttmp; 317 1.4 christos 318 1.4 christos if (!ftrap) { 319 1.4 christos strange_feeling(scroll, "Your toes stop itching."); 320 1.4 christos return (1); 321 1.4 christos } else { 322 1.4 christos for (ttmp = ftrap; ttmp; ttmp = ttmp->ntrap) 323 1.4 christos if (ttmp->tx != u.ux || ttmp->ty != u.uy) 324 1.4 christos goto outtrapmap; 325 1.4 christos /* 326 1.4 christos * only under me - no separate display 327 1.4 christos * required 328 1.4 christos */ 329 1.4 christos pline("Your toes itch!"); 330 1.4 christos break; 331 1.1 cgd outtrapmap: 332 1.4 christos cls(); 333 1.4 christos for (ttmp = ftrap; ttmp; ttmp = ttmp->ntrap) 334 1.4 christos at(ttmp->tx, ttmp->ty, '$'); 335 1.4 christos prme(); 336 1.4 christos pline("You feel very greedy!"); 337 1.4 christos } 338 1.1 cgd } else { 339 1.4 christos struct gold *gtmp; 340 1.4 christos 341 1.4 christos if (!fgold) { 342 1.4 christos strange_feeling(scroll, "You feel materially poor."); 343 1.4 christos return (1); 344 1.4 christos } else { 345 1.4 christos known = TRUE; 346 1.4 christos for (gtmp = fgold; gtmp; gtmp = gtmp->ngold) 347 1.4 christos if (gtmp->gx != u.ux || gtmp->gy != u.uy) 348 1.4 christos goto outgoldmap; 349 1.4 christos /* 350 1.4 christos * only under me - no separate display 351 1.4 christos * required 352 1.4 christos */ 353 1.4 christos pline("You notice some gold between your feet."); 354 1.4 christos break; 355 1.1 cgd outgoldmap: 356 1.4 christos cls(); 357 1.4 christos for (gtmp = fgold; gtmp; gtmp = gtmp->ngold) 358 1.4 christos at(gtmp->gx, gtmp->gy, '$'); 359 1.4 christos prme(); 360 1.4 christos pline("You feel very greedy, and sense gold!"); 361 1.4 christos } 362 1.1 cgd } 363 1.1 cgd /* common sequel */ 364 1.1 cgd more(); 365 1.1 cgd docrt(); 366 1.1 cgd break; 367 1.1 cgd case SCR_FOOD_DETECTION: 368 1.4 christos { 369 1.4 christos int ct = 0, ctu = 0; 370 1.4 christos struct obj *obj; 371 1.4 christos char foodsym = confused ? POTION_SYM : FOOD_SYM; 372 1.4 christos 373 1.4 christos for (obj = fobj; obj; obj = obj->nobj) 374 1.4 christos if (obj->olet == FOOD_SYM) { 375 1.4 christos if (obj->ox == u.ux && obj->oy == u.uy) 376 1.4 christos ctu++; 377 1.4 christos else 378 1.4 christos ct++; 379 1.4 christos } 380 1.4 christos if (!ct && !ctu) { 381 1.4 christos strange_feeling(scroll, "Your nose twitches."); 382 1.4 christos return (1); 383 1.4 christos } else if (!ct) { 384 1.4 christos known = TRUE; 385 1.4 christos pline("You smell %s close nearby.", 386 1.4 christos confused ? "something" : "food"); 387 1.4 christos 388 1.4 christos } else { 389 1.4 christos known = TRUE; 390 1.4 christos cls(); 391 1.4 christos for (obj = fobj; obj; obj = obj->nobj) 392 1.4 christos if (obj->olet == foodsym) 393 1.4 christos at(obj->ox, obj->oy, FOOD_SYM); 394 1.4 christos prme(); 395 1.4 christos pline("Your nose tingles and you smell %s!", 396 1.4 christos confused ? "something" : "food"); 397 1.4 christos more(); 398 1.4 christos docrt(); 399 1.4 christos } 400 1.4 christos break; 401 1.1 cgd } 402 1.1 cgd case SCR_IDENTIFY: 403 1.1 cgd /* known = TRUE; */ 404 1.4 christos if (confused) 405 1.1 cgd pline("You identify this as an identify scroll."); 406 1.1 cgd else 407 1.1 cgd pline("This is an identify scroll."); 408 1.1 cgd useup(scroll); 409 1.1 cgd objects[SCR_IDENTIFY].oc_name_known = 1; 410 1.4 christos if (!confused) 411 1.4 christos while ( 412 1.4 christos !ggetobj("identify", identify, rn2(5) ? 1 : rn2(5)) 413 1.4 christos && invent 414 1.4 christos ); 415 1.4 christos return (1); 416 1.1 cgd case SCR_MAGIC_MAPPING: 417 1.4 christos { 418 1.4 christos struct rm *lev; 419 1.4 christos int num, zx, zy; 420 1.1 cgd 421 1.4 christos known = TRUE; 422 1.4 christos pline("On this scroll %s a map!", 423 1.4 christos confused ? "was" : "is"); 424 1.4 christos for (zy = 0; zy < ROWNO; zy++) 425 1.4 christos for (zx = 0; zx < COLNO; zx++) { 426 1.4 christos if (confused && rn2(7)) 427 1.4 christos continue; 428 1.4 christos lev = &(levl[zx][zy]); 429 1.4 christos if ((num = lev->typ) == 0) 430 1.4 christos continue; 431 1.4 christos if (num == SCORR) { 432 1.4 christos lev->typ = CORR; 433 1.4 christos lev->scrsym = CORR_SYM; 434 1.4 christos } else if (num == SDOOR) { 435 1.4 christos lev->typ = DOOR; 436 1.4 christos lev->scrsym = '+'; 437 1.4 christos /* do sth in doors ? */ 438 1.4 christos } else if (lev->seen) 439 1.4 christos continue; 440 1.1 cgd #ifndef QUEST 441 1.4 christos if (num != ROOM) 442 1.4 christos #endif /* QUEST */ 443 1.4 christos { 444 1.4 christos lev->seen = lev->new = 1; 445 1.4 christos if (lev->scrsym == ' ' || !lev->scrsym) 446 1.4 christos newsym(zx, zy); 447 1.4 christos else 448 1.4 christos on_scr(zx, zy); 449 1.4 christos } 450 1.1 cgd } 451 1.4 christos break; 452 1.4 christos } 453 1.1 cgd case SCR_AMNESIA: 454 1.4 christos { 455 1.4 christos int zx, zy; 456 1.1 cgd 457 1.4 christos known = TRUE; 458 1.4 christos for (zx = 0; zx < COLNO; zx++) 459 1.4 christos for (zy = 0; zy < ROWNO; zy++) 460 1.4 christos if (!confused || rn2(7)) 461 1.4 christos if (!cansee(zx, zy)) 462 1.4 christos levl[zx][zy].seen = 0; 463 1.4 christos docrt(); 464 1.4 christos pline("Thinking of Maud you forget everything else."); 465 1.4 christos break; 466 1.4 christos } 467 1.1 cgd case SCR_FIRE: 468 1.4 christos { 469 1.4 christos int num = 0; 470 1.4 christos struct monst *mtmp; 471 1.1 cgd 472 1.4 christos known = TRUE; 473 1.4 christos if (confused) { 474 1.4 christos pline("The scroll catches fire and you burn your hands."); 475 1.4 christos losehp(1, "scroll of fire"); 476 1.4 christos } else { 477 1.4 christos pline("The scroll erupts in a tower of flame!"); 478 1.4 christos if (Fire_resistance) 479 1.4 christos pline("You are uninjured."); 480 1.4 christos else { 481 1.4 christos num = rnd(6); 482 1.4 christos u.uhpmax -= num; 483 1.4 christos losehp(num, "scroll of fire"); 484 1.4 christos } 485 1.4 christos } 486 1.4 christos num = (2 * num + 1) / 3; 487 1.4 christos for (mtmp = fmon; mtmp; mtmp = mtmp->nmon) { 488 1.4 christos if (dist(mtmp->mx, mtmp->my) < 3) { 489 1.4 christos mtmp->mhp -= num; 490 1.4 christos if (strchr("FY", mtmp->data->mlet)) 491 1.4 christos mtmp->mhp -= 3 * num; /* this might well kill 492 1.4 christos * 'F's */ 493 1.4 christos if (mtmp->mhp < 1) { 494 1.4 christos killed(mtmp); 495 1.4 christos break; /* primitive */ 496 1.4 christos } 497 1.4 christos } 498 1.1 cgd } 499 1.4 christos break; 500 1.1 cgd } 501 1.1 cgd case SCR_PUNISHMENT: 502 1.1 cgd known = TRUE; 503 1.4 christos if (confused) { 504 1.1 cgd pline("You feel guilty."); 505 1.1 cgd break; 506 1.1 cgd } 507 1.1 cgd pline("You are being punished for your misbehaviour!"); 508 1.4 christos if (Punished) { 509 1.1 cgd pline("Your iron ball gets heavier."); 510 1.1 cgd uball->owt += 15; 511 1.1 cgd break; 512 1.1 cgd } 513 1.1 cgd Punished = INTRINSIC; 514 1.1 cgd setworn(mkobj_at(CHAIN_SYM, u.ux, u.uy), W_CHAIN); 515 1.1 cgd setworn(mkobj_at(BALL_SYM, u.ux, u.uy), W_BALL); 516 1.4 christos uball->spe = 1; /* special ball (see save) */ 517 1.1 cgd break; 518 1.1 cgd default: 519 1.1 cgd impossible("What weird language is this written in? (%u)", 520 1.4 christos scroll->otyp); 521 1.1 cgd } 522 1.4 christos if (!objects[scroll->otyp].oc_name_known) { 523 1.4 christos if (known && !confused) { 524 1.1 cgd objects[scroll->otyp].oc_name_known = 1; 525 1.4 christos more_experienced(0, 10); 526 1.4 christos } else if (!objects[scroll->otyp].oc_uname) 527 1.1 cgd docall(scroll); 528 1.1 cgd } 529 1.1 cgd useup(scroll); 530 1.4 christos return (1); 531 1.1 cgd } 532 1.1 cgd 533 1.10 dholland static int 534 1.9 dholland identify(struct obj *otmp) /* also called by newmail() */ 535 1.1 cgd { 536 1.1 cgd objects[otmp->otyp].oc_name_known = 1; 537 1.1 cgd otmp->known = otmp->dknown = 1; 538 1.1 cgd prinv(otmp); 539 1.4 christos return (1); 540 1.1 cgd } 541 1.1 cgd 542 1.4 christos void 543 1.9 dholland litroom(boolean on) 544 1.1 cgd { 545 1.4 christos #ifndef QUEST 546 1.4 christos int num, zx, zy; 547 1.4 christos #endif 548 1.1 cgd 549 1.1 cgd /* first produce the text (provided he is not blind) */ 550 1.4 christos if (Blind) 551 1.4 christos goto do_it; 552 1.4 christos if (!on) { 553 1.4 christos if (u.uswallow || !xdnstair || levl[u.ux][u.uy].typ == CORR || 554 1.1 cgd !levl[u.ux][u.uy].lit) { 555 1.1 cgd pline("It seems even darker in here than before."); 556 1.1 cgd return; 557 1.1 cgd } else 558 1.1 cgd pline("It suddenly becomes dark in here."); 559 1.1 cgd } else { 560 1.4 christos if (u.uswallow) { 561 1.1 cgd pline("%s's stomach is lit.", Monnam(u.ustuck)); 562 1.1 cgd return; 563 1.1 cgd } 564 1.4 christos if (!xdnstair) { 565 1.1 cgd pline("Nothing Happens."); 566 1.1 cgd return; 567 1.1 cgd } 568 1.1 cgd #ifdef QUEST 569 1.1 cgd pline("The cave lights up around you, then fades."); 570 1.1 cgd return; 571 1.4 christos #else /* QUEST */ 572 1.4 christos if (levl[u.ux][u.uy].typ == CORR) { 573 1.4 christos pline("The corridor lights up around you, then fades."); 574 1.4 christos return; 575 1.4 christos } else if (levl[u.ux][u.uy].lit) { 576 1.4 christos pline("The light here seems better now."); 577 1.4 christos return; 578 1.1 cgd } else 579 1.4 christos pline("The room is lit."); 580 1.4 christos #endif /* QUEST */ 581 1.1 cgd } 582 1.1 cgd 583 1.1 cgd do_it: 584 1.1 cgd #ifdef QUEST 585 1.1 cgd return; 586 1.4 christos #else /* QUEST */ 587 1.4 christos if (levl[u.ux][u.uy].lit == on) 588 1.1 cgd return; 589 1.4 christos if (levl[u.ux][u.uy].typ == DOOR) { 590 1.4 christos if (IS_ROOM(levl[u.ux][u.uy + 1].typ)) 591 1.4 christos zy = u.uy + 1; 592 1.4 christos else if (IS_ROOM(levl[u.ux][u.uy - 1].typ)) 593 1.4 christos zy = u.uy - 1; 594 1.4 christos else 595 1.4 christos zy = u.uy; 596 1.4 christos if (IS_ROOM(levl[u.ux + 1][u.uy].typ)) 597 1.4 christos zx = u.ux + 1; 598 1.4 christos else if (IS_ROOM(levl[u.ux - 1][u.uy].typ)) 599 1.4 christos zx = u.ux - 1; 600 1.4 christos else 601 1.4 christos zx = u.ux; 602 1.1 cgd } else { 603 1.1 cgd zx = u.ux; 604 1.1 cgd zy = u.uy; 605 1.1 cgd } 606 1.4 christos for (seelx = u.ux; (num = levl[seelx - 1][zy].typ) != CORR && num != 0; 607 1.4 christos seelx--); 608 1.4 christos for (seehx = u.ux; (num = levl[seehx + 1][zy].typ) != CORR && num != 0; 609 1.4 christos seehx++); 610 1.4 christos for (seely = u.uy; (num = levl[zx][seely - 1].typ) != CORR && num != 0; 611 1.4 christos seely--); 612 1.4 christos for (seehy = u.uy; (num = levl[zx][seehy + 1].typ) != CORR && num != 0; 613 1.4 christos seehy++); 614 1.4 christos for (zy = seely; zy <= seehy; zy++) 615 1.4 christos for (zx = seelx; zx <= seehx; zx++) { 616 1.1 cgd levl[zx][zy].lit = on; 617 1.5 veego if (!Blind && dist(zx, zy) > 2) { 618 1.4 christos if (on) 619 1.4 christos prl(zx, zy); 620 1.4 christos else 621 1.4 christos nosee(zx, zy); 622 1.5 veego } 623 1.1 cgd } 624 1.4 christos if (!on) 625 1.4 christos seehx = 0; 626 1.4 christos #endif /* QUEST */ 627 1.1 cgd } 628 1.1 cgd 629 1.1 cgd /* Test whether we may genocide all monsters with symbol ch */ 630 1.10 dholland static int 631 1.9 dholland monstersym(int ch) /* arnold@ucsfcgl */ 632 1.1 cgd { 633 1.7 jsm const struct permonst *mp; 634 1.1 cgd 635 1.1 cgd /* 636 1.1 cgd * can't genocide certain monsters 637 1.1 cgd */ 638 1.4 christos if (strchr("12 &:", ch)) 639 1.1 cgd return FALSE; 640 1.1 cgd 641 1.1 cgd if (ch == pm_eel.mlet) 642 1.1 cgd return TRUE; 643 1.4 christos for (mp = mons; mp < &mons[CMNUM + 2]; mp++) 644 1.1 cgd if (mp->mlet == ch) 645 1.1 cgd return TRUE; 646 1.1 cgd return FALSE; 647 1.1 cgd } 648