comparison arogue7/daemons.c @ 125:adfa37e67084

Import Advanced Rogue 7.7 from the Roguelike Restoration Project (r1490)
author John "Elwin" Edwards
date Fri, 08 May 2015 15:24:40 -0400
parents
children cadff8f047a1
comparison
equal deleted inserted replaced
124:d10fc4a065ac 125:adfa37e67084
1 /*
2 * daemon.c - All the daemon and fuse functions are in here
3 *
4 * Advanced Rogue
5 * Copyright (C) 1984, 1985, 1986 Michael Morgan, Ken Dalka and AT&T
6 * All rights reserved.
7 *
8 * Based on "Rogue: Exploring the Dungeons of Doom"
9 * Copyright (C) 1980, 1981 Michael Toy, Ken Arnold and Glenn Wichman
10 * All rights reserved.
11 *
12 * See the file LICENSE.TXT for full copyright and licensing information.
13 */
14
15 /*
16 * All the daemon and fuse functions are in here
17 *
18 */
19
20 #include "curses.h"
21 #include "rogue.h"
22
23 /*
24 * doctor:
25 * A healing daemon that restors hit points after rest
26 */
27
28 doctor(tp)
29 register struct thing *tp;
30 {
31 register int ohp;
32 register int limit, new_points;
33 register struct stats *curp; /* current stats pointer */
34 register struct stats *maxp; /* max stats pointer */
35
36 curp = &(tp->t_stats);
37 maxp = &(tp->maxstats);
38 if (curp->s_hpt == maxp->s_hpt) {
39 tp->t_quiet = 0;
40 return;
41 }
42 tp->t_quiet++;
43 switch (tp->t_ctype) {
44 case C_MAGICIAN:
45 limit = 8 - curp->s_lvl;
46 new_points = curp->s_lvl - 3;
47 when C_THIEF:
48 case C_ASSASIN:
49 case C_MONK:
50 limit = 8 - curp->s_lvl;
51 new_points = curp->s_lvl - 2;
52 when C_CLERIC:
53 case C_DRUID:
54 limit = 8 - curp->s_lvl;
55 new_points = curp->s_lvl - 3;
56 when C_FIGHTER:
57 case C_RANGER:
58 case C_PALADIN:
59 limit = 16 - curp->s_lvl*2;
60 new_points = curp->s_lvl - 5;
61 when C_MONSTER:
62 limit = 16 - curp->s_lvl;
63 new_points = curp->s_lvl - 6;
64 otherwise:
65 debug("what a strange character you are!");
66 return;
67 }
68 ohp = curp->s_hpt;
69 if (off(*tp, HASDISEASE) && off(*tp, DOROT)) {
70 if (curp->s_lvl < 8) {
71 if (tp->t_quiet > limit) {
72 curp->s_hpt++;
73 tp->t_quiet = 0;
74 }
75 }
76 else {
77 if (tp->t_quiet >= 3) {
78 curp->s_hpt += rnd(new_points)+1;
79 tp->t_quiet = 0;
80 }
81 }
82 }
83 if (tp == &player) {
84 if (ISRING(LEFT_1, R_REGEN)) curp->s_hpt++;
85 if (ISRING(LEFT_2, R_REGEN)) curp->s_hpt++;
86 if (ISRING(LEFT_3, R_REGEN)) curp->s_hpt++;
87 if (ISRING(LEFT_4, R_REGEN)) curp->s_hpt++;
88 if (ISRING(RIGHT_1, R_REGEN)) curp->s_hpt++;
89 if (ISRING(RIGHT_2, R_REGEN)) curp->s_hpt++;
90 if (ISRING(RIGHT_3, R_REGEN)) curp->s_hpt++;
91 if (ISRING(RIGHT_4, R_REGEN)) curp->s_hpt++;
92 }
93 if (on(*tp, ISREGEN))
94 curp->s_hpt += curp->s_lvl/10 + 1;
95 if (ohp != curp->s_hpt) {
96 if (curp->s_hpt >= maxp->s_hpt) {
97 curp->s_hpt = maxp->s_hpt;
98 if (off(*tp, WASTURNED) && on(*tp, ISFLEE) && tp != &player) {
99 turn_off(*tp, ISFLEE);
100 tp->t_oldpos = tp->t_pos; /* Start our trek over */
101 }
102 }
103 }
104 }
105
106 /*
107 * Swander:
108 * Called when it is time to start rolling for wandering monsters
109 */
110
111 swander()
112 {
113 daemon(rollwand, 0, BEFORE);
114 }
115
116 /*
117 * rollwand:
118 * Called to roll to see if a wandering monster starts up
119 */
120
121 int between = 0;
122
123 rollwand()
124 {
125
126 if (++between >= 4)
127 {
128 /* Theives may not awaken a monster */
129 if ((roll(1, 6) == 4) &&
130 ((player.t_ctype != C_THIEF && player.t_ctype != C_ASSASIN) ||
131 (rnd(30) >= dex_compute()))) {
132 if (levtype != POSTLEV)
133 wanderer();
134 kill_daemon(rollwand);
135 fuse(swander, 0, WANDERTIME, BEFORE);
136 }
137 between = 0;
138 }
139 }
140 /*
141 * this function is a daemon called each turn when the character is a thief
142 */
143 trap_look()
144 {
145 if (rnd(100) < (2*dex_compute() + 5*pstats.s_lvl))
146 search(TRUE, FALSE);
147 }
148
149 /*
150 * unconfuse:
151 * Release the poor player from his confusion
152 */
153
154 unconfuse()
155 {
156 turn_off(player, ISHUH);
157 msg("You feel less confused now");
158 }
159
160
161 /*
162 * unsee:
163 * He lost his see invisible power
164 */
165 unsee()
166 {
167 if (!ISWEARING(R_SEEINVIS)) {
168 turn_off(player, CANSEE);
169 msg("The tingling feeling leaves your eyes");
170 }
171 }
172
173 /*
174 * unstink:
175 * Remove to-hit handicap from player
176 */
177
178 unstink()
179 {
180 turn_off(player, HASSTINK);
181 }
182
183 /*
184 * unclrhead:
185 * Player is no longer immune to confusion
186 */
187
188 unclrhead()
189 {
190 turn_off(player, ISCLEAR);
191 msg("The blue aura about your head fades away.");
192 }
193
194 /*
195 * unphase:
196 * Player can no longer walk through walls
197 */
198
199 unphase()
200 {
201 turn_off(player, CANINWALL);
202 msg("Your dizzy feeling leaves you.");
203 if (!step_ok(hero.y, hero.x, NOMONST, &player)) death(D_PETRIFY);
204 }
205
206 /*
207 * land:
208 * Player can no longer fly
209 */
210
211 land()
212 {
213 turn_off(player, ISFLY);
214 msg("You regain your normal weight");
215 running = FALSE;
216 }
217
218 /*
219 * sight:
220 * He gets his sight back
221 */
222
223 sight()
224 {
225 if (on(player, ISBLIND))
226 {
227 extinguish(sight);
228 turn_off(player, ISBLIND);
229 light(&hero);
230 msg("The veil of darkness lifts");
231 }
232 }
233
234 /*
235 * res_strength:
236 * Restore player's strength
237 */
238
239 void
240 res_strength(howmuch)
241 int howmuch;
242 {
243
244 /* If lost_str is non-zero, restore that amount of strength,
245 * else all of it
246 */
247 if (lost_str) {
248 chg_str(lost_str);
249 lost_str = 0;
250 }
251
252 /* Now, add in the restoral, but no greater than maximum strength */
253 if (howmuch > 0)
254 pstats.s_str =
255 min(pstats.s_str + howmuch, max_stats.s_str + ring_value(R_ADDSTR));
256
257 updpack(TRUE, &player);
258 }
259
260 /*
261 * nohaste:
262 * End the hasting
263 */
264
265 nohaste()
266 {
267 turn_off(player, ISHASTE);
268 msg("You feel yourself slowing down.");
269 }
270
271 /*
272 * noslow:
273 * End the slowing
274 */
275
276 noslow()
277 {
278 turn_off(player, ISSLOW);
279 msg("You feel yourself speeding up.");
280 }
281
282 /*
283 * suffocate:
284 * If this gets called, the player has suffocated
285 */
286
287 suffocate()
288 {
289 death(D_SUFFOCATION);
290 }
291
292 /*
293 * digest the hero's food
294 */
295 stomach()
296 {
297 register int oldfood, old_hunger, food_use, i;
298
299 /*
300 * avoid problems of fainting while eating by just not saying it
301 * takes food to eat food
302 */
303 if (player.t_action == C_EAT)
304 return;
305
306 old_hunger = hungry_state;
307 if (food_left <= 0)
308 {
309 /*
310 * the hero is fainting
311 */
312 if (player.t_action == A_FREEZE)
313 return;
314 if (rnd(100) > 20)
315 return;
316 if (hungry_state == F_FAINT && rnd(20) == 7) /*must have fainted once*/
317 death(D_STARVATION);
318 player.t_action = A_FREEZE;
319 player.t_no_move = movement(&player) * (rnd(8) + 4);
320 if (!terse)
321 addmsg("You feel too weak from lack of food. ");
322 msg("You faint");
323 running = FALSE;
324 if (fight_flush) md_flushinp();
325 count = 0;
326 hungry_state = F_FAINT;
327 }
328 else
329 {
330 oldfood = food_left;
331 food_use = 0;
332 for (i=0; i<MAXRELIC; i++) { /* each relic eats an additional food */
333 if (cur_relic[i])
334 food_use++;
335 }
336 food_use += (ring_eat(LEFT_1) + ring_eat(LEFT_2) +
337 ring_eat(LEFT_3) + ring_eat(LEFT_4) +
338 ring_eat(RIGHT_1) + ring_eat(RIGHT_2) +
339 ring_eat(RIGHT_3) + ring_eat(RIGHT_4) +
340 foodlev);
341 if (food_use < 1)
342 food_use = 1;
343 food_left -= food_use;
344 if (food_left < MORETIME && oldfood >= MORETIME) {
345 msg("You are starting to feel weak");
346 running = FALSE;
347 if (fight_flush) md_flushinp();
348 count = 0;
349 hungry_state = F_WEAK;
350 }
351 else if (food_left < 2 * MORETIME && oldfood >= 2 * MORETIME)
352 {
353 msg(terse ? "Getting hungry" : "You are starting to get hungry");
354 running = FALSE;
355 hungry_state = F_HUNGRY;
356 }
357 else if(food_left<STOMACHSIZE-MORETIME && oldfood>=STOMACHSIZE-MORETIME)
358 {
359 hungry_state = F_OKAY;
360 }
361 }
362 if (old_hunger != hungry_state) {
363 updpack(TRUE, &player);
364 status(TRUE);
365 }
366 wghtchk();
367 }
368 /*
369 * daemon for curing the diseased
370 */
371 cure_disease()
372 {
373 turn_off(player, HASDISEASE);
374 if (off (player, HASINFEST))
375 msg(terse ? "You feel yourself improving"
376 : "You begin to feel yourself improving again");
377 }
378
379 /*
380 * appear:
381 * Become visible again
382 */
383 appear()
384 {
385 turn_off(player, ISINVIS);
386 PLAYER = VPLAYER;
387 msg("The tingling feeling leaves your body");
388 light(&hero);
389 }
390 /*
391 * dust_appear:
392 * dust of disappearance wears off
393 */
394 dust_appear()
395 {
396 turn_off(player, ISINVIS);
397 PLAYER = VPLAYER;
398 msg("You become visible again");
399 light(&hero);
400 }
401 /*
402 * unchoke:
403 * the effects of "dust of choking and sneezing" wear off
404 */
405 unchoke()
406 {
407 if (!find_slot(unconfuse))
408 turn_off(player, ISHUH);
409 if (!find_slot(sight))
410 turn_off(player, ISBLIND);
411 light(&hero);
412 msg("Your throat and eyes return to normal");
413 }
414 /*
415 * make some potion for the guy in the Alchemy jug
416 */
417 alchemy(obj)
418 register struct object *obj;
419 {
420 register struct object *tobj;
421 register struct linked_list *item;
422
423 /*
424 * verify that the object pointer we have still points to an alchemy
425 * jug (hopefully the right one!) because the hero could have thrown
426 * it away
427 */
428 for (item = pack; item != NULL; item = next(item)) {
429 tobj = OBJPTR(item);
430 if (tobj == obj &&
431 tobj->o_type == MM &&
432 tobj->o_which== MM_JUG &&
433 tobj->o_ac == JUG_EMPTY )
434 break;
435 }
436 if (item == NULL) { /* not in the pack, check the level */
437 for (item = lvl_obj; item != NULL; item = next(item)) {
438 tobj = OBJPTR(item);
439 if (tobj == obj &&
440 tobj->o_type == MM &&
441 tobj->o_which== MM_JUG &&
442 tobj->o_ac == JUG_EMPTY )
443 break;
444 }
445 }
446 if (item == NULL) /* can't find it.....too bad */
447 return;
448
449 switch(rnd(11)) {
450 case 0: tobj->o_ac = P_PHASE;
451 when 1: tobj->o_ac = P_CLEAR;
452 when 2: tobj->o_ac = P_SEEINVIS;
453 when 3: tobj->o_ac = P_HEALING;
454 when 4: tobj->o_ac = P_MFIND;
455 when 5: tobj->o_ac = P_TFIND;
456 when 6: tobj->o_ac = P_HASTE;
457 when 7: tobj->o_ac = P_RESTORE;
458 when 8: tobj->o_ac = P_FLY;
459 when 9: tobj->o_ac = P_SKILL;
460 when 10:tobj->o_ac = P_FFIND;
461 }
462 }
463 /*
464 * otto's irresistable dance wears off
465 */
466
467 undance()
468 {
469 turn_off(player, ISDANCE);
470 msg ("Your feet take a break.....whew!");
471 }
472
473 /*
474 * if he has our favorite necklace of strangulation then take damage every turn
475 */
476 strangle()
477 {
478 if ((pstats.s_hpt -= 6) <= 0) death(D_STRANGLE);
479 }
480 /*
481 * if he has on the gauntlets of fumbling he might drop his weapon each turn
482 */
483 fumble()
484 {
485 register struct linked_list *item;
486
487 if (cur_weapon!=NULL &&
488 !(cur_weapon->o_flags & ISCURSED) &&
489 cur_weapon->o_type != RELIC &&
490 rnd(100)<3) {
491 for (item = pack; item != NULL; item = next(item)) {
492 if (OBJPTR(item) == cur_weapon)
493 break;
494 }
495 if (item != NULL) {
496 switch(mvwinch(stdscr, hero.y, hero.x)) {
497 case PASSAGE:
498 case SCROLL:
499 case POTION:
500 case WEAPON:
501 case FLOOR:
502 case STICK:
503 case ARMOR:
504 case POOL:
505 case RELIC:
506 case GOLD:
507 case FOOD:
508 case RING:
509 case MM:
510 drop(item);
511 running = FALSE;
512 break;
513 default:
514 break;
515 }
516 }
517 }
518 }
519 /*
520 * this is called each turn the hero has the ring of searching on
521 */
522 ring_search()
523 {
524 search(FALSE, FALSE);
525 }
526 /*
527 * this is called each turn the hero has the ring of teleportation on
528 */
529 ring_teleport()
530 {
531 if (rnd(100) < 2) teleport();
532 }
533 /*
534 * this is called to charge up the quill of Nagrom
535 */
536 quill_charge()
537 {
538 register struct object *tobj;
539 register struct linked_list *item;
540
541 /*
542 * find the Quill of Nagrom in the hero's pack. It should still be there
543 * because it can't be dropped. If its not then don't do anything.
544 */
545 for (item = pack; item != NULL; item = next(item)) {
546 tobj = OBJPTR(item);
547 if (tobj->o_type == RELIC && tobj->o_which == QUILL_NAGROM)
548 break;
549 }
550 if (item == NULL)
551 return;
552 if (tobj->o_charges < QUILLCHARGES)
553 tobj->o_charges++;
554 fuse (quill_charge, 0, player.t_ctype == C_MAGICIAN ? 4 : 8, AFTER);
555 }
556 /*
557 * take the skills away gained (or lost) by the potion of skills
558 */
559 unskill()
560 {
561 if (pstats.s_lvladj != 0) {
562 pstats.s_lvl -= pstats.s_lvladj;
563 pstats.s_lvladj = 0;
564 msg("You feel your normal skill level return.");
565 status(TRUE);
566 }
567 }
568 /*
569 * charge up the cloak of Emori
570 */
571
572 cloak_charge(obj)
573 register struct object *obj;
574 {
575 if (obj->o_charges < 1)
576 obj->o_charges = 1;
577 }
578
579 /*
580 * nofire:
581 * He lost his fire resistance
582 */
583 nofire()
584 {
585 if (!ISWEARING(R_FIRE)) {
586 turn_off(player, NOFIRE);
587 msg("Your feeling of fire resistance leaves you");
588 }
589 }
590
591 /*
592 * nocold:
593 * He lost his cold resistance
594 */
595 nocold()
596 {
597 if (!ISWEARING(R_WARMTH)) {
598 turn_off(player, NOCOLD);
599 msg("Your feeling of warmth leaves you");
600 }
601 }
602
603 /*
604 * nobolt:
605 * He lost his protection from lightning
606 */
607 nobolt()
608 {
609 turn_off(player, NOBOLT);
610 msg("Your skin looses its bluish tint");
611 }
612 /*
613 * eat_gold:
614 * an artifact eats gold
615 */
616 eat_gold(obj)
617 register struct object *obj;
618 {
619 if (purse == 1)
620 msg("%s demand you find more gold", inv_name(obj, FALSE));
621 if (purse == 0) {
622 if (--pstats.s_hpt <= 0)
623 death(D_RELIC);
624 }
625 else
626 purse--;
627 }
628 /*
629 * give the hero back some spell points
630 */
631 spell_recovery()
632 {
633 int time;
634
635 time = SPELLTIME - max(17-pstats.s_intel, 0);
636 time = max(time, 5);
637 if (spell_power > 0) spell_power--;
638 fuse(spell_recovery, NULL, time, AFTER);
639 }
640 /*
641 * give the hero back some prayer points
642 */
643 prayer_recovery()
644 {
645 int time;
646
647 time = SPELLTIME - max(17-pstats.s_wisdom, 0);
648 time = max(time, 5);
649 if (pray_time > 0) pray_time--;
650 fuse(prayer_recovery, NULL, time, AFTER);
651 }
652 /*
653 * give the hero back some chant points
654 */
655 chant_recovery()
656 {
657 int time;
658
659 time = SPELLTIME - max(17-pstats.s_wisdom, 0);
660 time = max(time, 5);
661 if (chant_time > 0) chant_time--;
662 fuse(chant_recovery, NULL, time, AFTER);
663 }