]> granicus.if.org Git - nethack/commitdiff
floor access
authornethack.rankin <nethack.rankin>
Sat, 4 Jun 2005 05:25:28 +0000 (05:25 +0000)
committernethack.rankin <nethack.rankin>
Sat, 4 Jun 2005 05:25:28 +0000 (05:25 +0000)
     A post-3.4.3 change dealing with reaching into pits resulted in "you
sit on the air" if you used the #sit command after escaping a pit trap.
Change can_reach_floor() so that caller explicitly controls whether being
on the brink of a pit is a condition that prevents reaching the floor.
This also splits a fairly common message about not being able to reach the
floor into a separate routine.

     There is still oddness here:  if you're polymorphed into a flyer,
#sit yields "you sit down" followed by "you fly over a pit" (latter occurs
when escaping trap activation).  A ceiling hider behaves similarly, but
the second message is "you escape a pit" and doesn't sound quite as silly.
Perhaps #sit should pass TOOKPLUNGE to dotrap(), or maybe there's some
better way to handle this?

13 files changed:
include/extern.h
src/apply.c
src/dig.c
src/do.c
src/eat.c
src/engrave.c
src/hack.c
src/invent.c
src/lock.c
src/pickup.c
src/potion.c
src/sit.c
src/trap.c

index 2cea07cca6bf53f5c52630a66e8e994f2a8c93fd..ded45696ad1ebe5b9a866bbb9cc053ec2527f959 100644 (file)
@@ -597,7 +597,8 @@ E void FDECL(restore_killers, (int));
 
 E char *FDECL(random_engraving, (char *));
 E void FDECL(wipeout_text, (char *,int,unsigned));
-E boolean NDECL(can_reach_floor);
+E boolean FDECL(can_reach_floor, (BOOLEAN_P));
+E void FDECL(cant_reach_floor, (int,int,BOOLEAN_P,BOOLEAN_P));
 E const char *FDECL(surface, (int,int));
 E const char *FDECL(ceiling, (int,int));
 E struct engr *FDECL(engr_at, (XCHAR_P,XCHAR_P));
index 7f56fac2ce6eed2eb141dc9793d1633cdbd2baae..2cc5b17fa951aa97bc83b185f5c2f3828761542f 100644 (file)
@@ -1,4 +1,4 @@
-/*     SCCS Id: @(#)apply.c    3.5     2005/04/13      */
+/*     SCCS Id: @(#)apply.c    3.5     2005/06/02      */
 /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
 /* NetHack may be freely redistributed.  See license for details. */
 
@@ -169,7 +169,7 @@ int rx, ry, *resp;
     struct obj *corpse = sobj_at(CORPSE, rx, ry),
               *statue = sobj_at(STATUE, rx, ry);
 
-    if (!can_reach_floor()) {  /* levitation or unskilled riding */
+    if (!can_reach_floor(TRUE)) {      /* levitation or unskilled riding */
        corpse = 0;             /* can't reach corpse on floor */
        /* you can't reach tiny statues (even though you can fight
           tiny monsters while levitating--consistency, what's that?) */
@@ -322,9 +322,8 @@ use_stethoscope(obj)
        } else if (u.dz) {
                if (Underwater)
                    You_hear("faint splashing.");
-               else if (u.dz < 0 || !can_reach_floor())
-                   You_cant("reach the %s.",
-                       (u.dz > 0) ? surface(u.ux,u.uy) : ceiling(u.ux,u.uy));
+               else if (u.dz < 0 || !can_reach_floor(TRUE))
+                   cant_reach_floor(u.ux, u.uy, (u.dz < 0), TRUE);
                else if (its_dead(u.ux, u.uy, &res))
                    ;   /* message already given */
                else if (Is_stronghold(&u.uz))
index 7c47e7695881c876b797d38b4f1cee52918b1f50..fa1fdb26e493be3159cbb8743716c9d9ade59175 100644 (file)
--- a/src/dig.c
+++ b/src/dig.c
@@ -1,4 +1,4 @@
-/*     SCCS Id: @(#)dig.c      3.5     2005/04/13      */
+/*     SCCS Id: @(#)dig.c      3.5     2005/06/02      */
 /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
 /* NetHack may be freely redistributed.  See license for details. */
 
@@ -880,6 +880,7 @@ struct obj *obj;
 {
        register int rx, ry;
        register struct rm *lev;
+       struct trap *trap;
        int dig_target;
        boolean ispick = is_pick(obj);
        const char *verbing = ispick ? "digging" : "chopping";
@@ -919,8 +920,7 @@ struct obj *obj;
                dig_target = dig_typ(obj, rx, ry);
                if (dig_target == DIGTYP_UNDIGGABLE) {
                        /* ACCESSIBLE or POOL */
-                       struct trap *trap = t_at(rx, ry);
-
+                       trap = t_at(rx, ry);
                        if (trap && trap->ttyp == WEB) {
                            if (!trap->tseen) {
                                seetrap(trap);
@@ -994,12 +994,17 @@ struct obj *obj;
        } else if (Is_airlevel(&u.uz) || Is_waterlevel(&u.uz)) {
                /* it must be air -- water checked above */
                You("swing %s through thin air.", yobjnam(obj, (char *)0));
-       } else if (!can_reach_floor()) {
-               You_cant("reach the %s.", surface(u.ux,u.uy));
+       } else if (!can_reach_floor(FALSE)) {
+               cant_reach_floor(u.ux, u.uy, FALSE, FALSE);
        } else if (is_pool(u.ux, u.uy) || is_lava(u.ux, u.uy)) {
                /* Monsters which swim also happen not to be able to dig */
                You("cannot stay under%s long enough.",
                                is_pool(u.ux, u.uy) ? "water" : " the lava");
+       } else if ((trap = t_at(u.ux, u.uy)) != 0 &&
+                   uteetering_at_seen_pit(trap)) {
+               dotrap(trap, FORCEBUNGLE);
+               /* might escape trap and still be teetering at brink */
+               if (!u.utrap) cant_reach_floor(u.ux, u.uy, FALSE, TRUE);
        } else if (!ispick) {
                pline("%s merely scratches the %s.",
                                Yobjnam2(obj, (char *)0), surface(u.ux,u.uy));
index d125bd4556660de4f3d723460e032358ca72bf06..931274accb71e83b5ec36806af4ad7113fb829f6 100644 (file)
--- a/src/do.c
+++ b/src/do.c
@@ -1,4 +1,4 @@
-/*     SCCS Id: @(#)do.c       3.5     2005/03/28      */
+/*     SCCS Id: @(#)do.c       3.5     2005/06/02      */
 /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
 /* NetHack may be freely redistributed.  See license for details. */
 
@@ -482,7 +482,7 @@ register struct obj *obj;
                return(1);
            }
 #endif
-           if (!can_reach_floor()) {
+           if (!can_reach_floor(TRUE)) {
                if(flags.verbose) You("drop %s.", doname(obj));
 #ifndef GOLDOBJ
                if (obj->oclass != COIN_CLASS || obj == invent) freeinv(obj);
index 04c93328adcb964aa1659e3fc217ecf26aba7f4b..3d06f201b337514bd0f9f33811116e6b7335298b 100644 (file)
--- a/src/eat.c
+++ b/src/eat.c
@@ -1,4 +1,4 @@
-/*     SCCS Id: @(#)eat.c      3.5     2005/04/08      */
+/*     SCCS Id: @(#)eat.c      3.5     2005/06/02      */
 /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
 /* NetHack may be freely redistributed.  See license for details. */
 
@@ -2515,7 +2515,7 @@ floorfood(verb,corpsecheck)       /* get food from floor or pack */
        boolean feeding = (!strcmp(verb, "eat"));
 
        /* if we can't touch floor objects then use invent food only */
-       if (!can_reach_floor() ||
+       if (!can_reach_floor(TRUE) ||
 #ifdef STEED
                (feeding && u.usteed) || /* can't eat off floor while riding */
 #endif
index 388253cbb8ddec62f0183c171c31baf4eb3f19da..0de15e448f84314b9a478040d16b8ac997f8b1a7 100644 (file)
@@ -1,4 +1,4 @@
-/*     SCCS Id: @(#)engrave.c  3.5     2005/04/22      */
+/*     SCCS Id: @(#)engrave.c  3.5     2005/06/02      */
 /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
 /* NetHack may be freely redistributed.  See license for details. */
 
@@ -130,8 +130,10 @@ unsigned seed;             /* for semi-controlled randomization */
        while (lth && engr[lth-1] == ' ') engr[--lth] = 0;
 }
 
+/* check whether hero can reach something at ground level */
 boolean
-can_reach_floor()
+can_reach_floor(check_pit)
+boolean check_pit;
 {
        struct trap *t;
 
@@ -140,8 +142,8 @@ can_reach_floor()
        /* Restricted/unskilled riders can't reach the floor */
        if (u.usteed && P_SKILL(P_RIDING) < P_BASIC) return FALSE;
 #endif
-       if ((t = t_at(u.ux, u.uy)) != 0 && uteetering_at_seen_pit(t) &&
-               !Flying)
+       if (check_pit && (t = t_at(u.ux, u.uy)) != 0 &&
+               uteetering_at_seen_pit(t) && !Flying)
            return FALSE;
 
        return (boolean)((!Levitation ||
@@ -150,6 +152,18 @@ can_reach_floor()
                          u.umonnum == PM_TRAPPER));
 }
 
+/* give a message after caller has determined that hero can't reach */
+void
+cant_reach_floor(x, y, up, check_pit)
+int x, y;
+boolean up, check_pit;
+{
+       You("can't reach the %s.",
+           up ? ceiling(x, y) :
+             (check_pit && can_reach_floor(FALSE)) ? "bottom of the pit" :
+               surface(x, y));
+}
+
 const char *
 surface(x, y)
 register int x, y;
@@ -246,7 +260,7 @@ void
 u_wipe_engr(cnt)
 register int cnt;
 {
-       if (can_reach_floor())
+       if (can_reach_floor(TRUE))
                wipe_engr_at(u.ux, u.uy, cnt);
 }
 
@@ -292,7 +306,7 @@ register int x,y;
                break;
            case ENGRAVE:
            case HEADSTONE:
-               if (!Blind || can_reach_floor()) {
+               if (!Blind || can_reach_floor(TRUE)) {
                        sensed = 1;
                        pline("%s is engraved here on the %s.",
                                Something,
@@ -300,7 +314,7 @@ register int x,y;
                }
                break;
            case BURN:
-               if (!Blind || can_reach_floor()) {
+               if (!Blind || can_reach_floor(TRUE)) {
                        sensed = 1;
                        pline("Some text has been %s into the %s here.",
                                is_ice(x,y) ? "melted" : "burned",
@@ -471,7 +485,7 @@ doengrave()
                        pline("What would you write?  \"Jonah was here\"?");
                        return(0);
                } else if (is_whirly(u.ustuck->data)) {
-                       You_cant("reach the %s.", surface(u.ux,u.uy));
+                       cant_reach_floor(u.ux, u.uy, FALSE, FALSE);
                        return(0);
                } else
                        jello = TRUE;
@@ -517,8 +531,8 @@ doengrave()
                Your("message dissolves...");
                return(0);
        }
-       if (otmp->oclass != WAND_CLASS && !can_reach_floor()) {
-               You_cant("reach the %s!", surface(u.ux,u.uy));
+       if (otmp->oclass != WAND_CLASS && !can_reach_floor(TRUE)) {
+               cant_reach_floor(u.ux, u.uy, FALSE, TRUE);
                return(0);
        }
        if (IS_ALTAR(levl[u.ux][u.uy].typ)) {
@@ -754,8 +768,8 @@ doengrave()
                    /* type = ENGR_BLOOD wands */
                    }
                } else /* end if zappable */
-                   if (!can_reach_floor()) {
-                       You_cant("reach the %s!", surface(u.ux,u.uy));
+                   if (!can_reach_floor(TRUE)) {
+                       cant_reach_floor(u.ux, u.uy, FALSE, TRUE);
                        return(0);
                    }
                break;
@@ -870,8 +884,8 @@ doengrave()
        }
 
        if (!ptext) {           /* Early exit for some implements. */
-           if (otmp->oclass == WAND_CLASS && !can_reach_floor())
-               You_cant("reach the %s!", surface(u.ux,u.uy));
+           if (otmp->oclass == WAND_CLASS && !can_reach_floor(TRUE))
+               cant_reach_floor(u.ux, u.uy, FALSE, TRUE);
            return(1);
        }
 
@@ -921,7 +935,7 @@ doengrave()
                        return(1);
                    } else
                        if ( (type != oep->engr_type) || (c == 'n') ) {
-                           if (!Blind || can_reach_floor())
+                           if (!Blind || can_reach_floor(TRUE))
                                You("will overwrite the current message.");
                            eow = TRUE;
                        }
index b53f23f58b639d28e94a2b0c03ff7a064ace7cbe..aa673bea2c7664537c2b8c10a15efda189743c57 100644 (file)
@@ -1,4 +1,4 @@
-/*     SCCS Id: @(#)hack.c     3.5     2004/11/11      */
+/*     SCCS Id: @(#)hack.c     3.5     2005/06/02      */
 /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
 /* NetHack may be freely redistributed.  See license for details. */
 
@@ -1944,7 +1944,7 @@ dopickup()
            There("is nothing here to pick up.");
            return 0;
        }
-       if (!can_reach_floor()) {
+       if (!can_reach_floor(TRUE)) {
            if (traphere && uteetering_at_seen_pit(traphere))
                You("cannot reach the bottom of the pit.");
 #ifdef STEED
index acc0acf3600541775f4064b683b354945b2e5c4a..5ff39261be767e541de78f7618f1f8d6a85ff148 100644 (file)
@@ -1,4 +1,4 @@
-/*     SCCS Id: @(#)invent.c   3.5     2005/04/06      */
+/*     SCCS Id: @(#)invent.c   3.5     2005/06/02      */
 /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
 /* NetHack may be freely redistributed.  See license for details. */
 
@@ -2257,7 +2257,7 @@ boolean picked_some;
                }
                if (dfeature && !drift && !strcmp(dfeature, surface(u.ux,u.uy)))
                        dfeature = 0;           /* ice already identifed */
-               if (!can_reach_floor()) {
+               if (!can_reach_floor(TRUE)) {
                        pline("But you can't reach it!");
                        return(0);
                }
index a9d37f97a79a4ce185fa87527b5d332f4ae2a5fd..43e9df0afab748e3ae8c540fd3b5431730ffbfc1 100644 (file)
@@ -1,4 +1,4 @@
-/*     SCCS Id: @(#)lock.c     3.5     2000/02/06      */
+/*     SCCS Id: @(#)lock.c     3.5     2005/06/02      */
 /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
 /* NetHack may be freely redistributed.  See license for details. */
 
@@ -240,7 +240,7 @@ pick_lock(pick) /* pick a lock with a given object */
                pline(no_longer, "hold the", what);
                reset_pick();
                return 0;
-           } else if (xlock.box && !can_reach_floor()) {
+           } else if (xlock.box && !can_reach_floor(TRUE)) {
                pline(no_longer, "reach the", "lock");
                reset_pick();
                return 0;
@@ -290,7 +290,7 @@ pick_lock(pick) /* pick a lock with a given object */
            for(otmp = level.objects[cc.x][cc.y]; otmp; otmp = otmp->nexthere)
                if (Is_box(otmp)) {
                    ++count;
-                   if (!can_reach_floor()) {
+                   if (!can_reach_floor(TRUE)) {
                        You_cant("reach %s from up here.", the(xname(otmp)));
                        return 0;
                    }
index a115df7bbbe5f6ba94e2731671a25d01e0153b81..bcea28a95c403323966765ebe85e0f9537f377e3 100644 (file)
@@ -1,4 +1,4 @@
-/*     SCCS Id: @(#)pickup.c   3.5     2005/04/06      */
+/*     SCCS Id: @(#)pickup.c   3.5     2005/06/02      */
 /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
 /* NetHack may be freely redistributed.  See license for details. */
 
@@ -413,7 +413,7 @@ int what;           /* should be a long */
                }
 
                /* no pickup if levitating & not on air or water level */
-               if (!can_reach_floor()) {
+               if (!can_reach_floor(TRUE)) {
                    if ((multi && !context.run) ||
                            (autopickup && !flags.pickup) ||
                            (ttmp && uteetering_at_seen_pit(ttmp)))
@@ -1464,13 +1464,13 @@ boolean looting;        /* loot vs tip */
 {
        const char *verb = looting ? "loot" : "tip";
 
-       if (!can_reach_floor()) {
+       if (!can_reach_floor(TRUE)) {
 #ifdef STEED
                if (u.usteed && P_SKILL(P_RIDING) < P_BASIC)
                        rider_cant_reach(); /* not skilled enough to reach */
                else
 #endif
-                       You("cannot reach the %s.", surface(x, y));
+                       cant_reach_floor(x, y, FALSE, TRUE);
                return FALSE;
        } else if ((is_pool(x, y) && (looting || !Underwater)) ||
                    is_lava(x, y)) {
@@ -2591,7 +2591,7 @@ struct obj *box;  /* or bag */
     if (empty_it) {
        struct obj *otmp, *nobj;
        boolean verbose = FALSE,
-               highdrop = !can_reach_floor(),
+               highdrop = !can_reach_floor(TRUE),
                altarizing = IS_ALTAR(levl[u.ux][u.uy].typ),
                cursed_mbag = (Is_mbag(box) && box->cursed);
        int held = carried(box);
index f71035b5cad00736a257bd756d3c6dddf750a3b0..f376c1f7af1704c6deff0524fa711eab1ab0814c 100644 (file)
@@ -1,4 +1,4 @@
-/*     SCCS Id: @(#)potion.c   3.5     2005/04/23      */
+/*     SCCS Id: @(#)potion.c   3.5     2005/06/02      */
 /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
 /* NetHack may be freely redistributed.  See license for details. */
 
@@ -342,7 +342,9 @@ dodrink()
                return 0;
        }
        /* Is there a fountain to drink from here? */
-       if (IS_FOUNTAIN(levl[u.ux][u.uy].typ) && can_reach_floor()) {
+       if (IS_FOUNTAIN(levl[u.ux][u.uy].typ) &&
+               /* not as low as floor level but similar restrictions apply */
+               can_reach_floor(FALSE)) {
                if(yn("Drink from the fountain?") == 'y') {
                        drinkfountain();
                        return 1;
@@ -350,7 +352,9 @@ dodrink()
        }
 #ifdef SINKS
        /* Or a kitchen sink? */
-       if (IS_SINK(levl[u.ux][u.uy].typ) && can_reach_floor()) {
+       if (IS_SINK(levl[u.ux][u.uy].typ) &&
+               /* not as low as floor level but similar restrictions apply */
+               can_reach_floor(FALSE)) {
                if (yn("Drink from the sink?") == 'y') {
                        drinksink();
                        return 1;
index 4d80b9a3409787b388af15a99f10cf8c888c77d2..8d4347258076f7a3cf95011427dcc103703db4dd 100644 (file)
--- a/src/sit.c
+++ b/src/sit.c
@@ -1,4 +1,4 @@
-/*     SCCS Id: @(#)sit.c      3.5     2004/12/21      */
+/*     SCCS Id: @(#)sit.c      3.5     2005/06/02      */
 /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
 /* NetHack may be freely redistributed.  See license for details. */
 
@@ -53,7 +53,7 @@ dosit()
        if (u.uundetected && is_hider(youmonst.data) && u.umonnum != PM_TRAPPER)
            u.uundetected = 0;          /* no longer on the ceiling */
 
-       if (!can_reach_floor()) {
+       if (!can_reach_floor(FALSE)) {
            if (Levitation)
                You("tumble in place.");
            else
@@ -73,16 +73,15 @@ dosit()
            if (!(Is_box(obj) || objects[obj->otyp].oc_material == CLOTH))
                pline("It's not very comfortable...");
 
-       } else if (trap != 0 ||
-                  (u.utrap && (u.utraptype >= TT_LAVA))) {
-
+       } else if (trap != 0 || (u.utrap && (u.utraptype >= TT_LAVA))) {
            if (u.utrap) {
                exercise(A_WIS, FALSE); /* you're getting stuck longer */
-               if(u.utraptype == TT_BEARTRAP) {
-                   You_cant("sit down with your %s in the bear trap.", body_part(FOOT));
+               if (u.utraptype == TT_BEARTRAP) {
+                   You_cant("sit down with your %s in the bear trap.",
+                            body_part(FOOT));
                    u.utrap++;
-               } else if(u.utraptype == TT_PIT) {
-                   if(trap && trap->ttyp == SPIKED_PIT) {
+               } else if (u.utraptype == TT_PIT) {
+                   if (trap && trap->ttyp == SPIKED_PIT) {
                        You("sit down on a spike.  Ouch!");
                        losehp(Half_physical_damage ? rn2(2) : 1,
                                "sitting on an iron spike", KILLED_BY);
@@ -90,20 +89,21 @@ dosit()
                    } else
                        You("sit down in the pit.");
                    u.utrap += rn2(5);
-               } else if(u.utraptype == TT_WEB) {
+               } else if (u.utraptype == TT_WEB) {
                    You("sit in the spider web and get entangled further!");
                    u.utrap += rn1(10, 5);
-               } else if(u.utraptype == TT_LAVA) {
+               } else if (u.utraptype == TT_LAVA) {
                    /* Must have fire resistance or they'd be dead already */
                    You("sit in the lava!");
                    u.utrap += rnd(4);
                    losehp(d(2,10), "sitting in lava", KILLED_BY); /* lava damage */
-               } else if(u.utraptype == TT_INFLOOR || u.utraptype == TT_BURIEDBALL) {
+               } else if (u.utraptype == TT_INFLOOR ||
+                       u.utraptype == TT_BURIEDBALL) {
                    You_cant("maneuver to sit!");
                    u.utrap++;
                }
            } else {
-               You("sit down.");
+               You("sit down.");
                dotrap(trap, 0);
            }
        } else if(Underwater || Is_waterlevel(&u.uz)) {
index 3d597ed8d2004f8f9fc98463ac1e1f7418ce001e..87e2b7af322bd427ffef7ed39051c9c998317cac 100644 (file)
@@ -1,4 +1,4 @@
-/*     SCCS Id: @(#)trap.c     3.5     2005/04/13      */
+/*     SCCS Id: @(#)trap.c     3.5     2005/06/02      */
 /* Copyright (c) Stichting Mathematisch Centrum, Amsterdam, 1985. */
 /* NetHack may be freely redistributed.  See license for details. */
 
@@ -3268,7 +3268,7 @@ boolean force_failure;
            }
        }
        /* untrappable traps are located on the ground. */
-       if (!can_reach_floor()) {
+       if (!can_reach_floor(TRUE)) {
 #ifdef STEED
                if (u.usteed && P_SKILL(P_RIDING) < P_BASIC)
                        You("aren't skilled enough to reach from %s.",