the-infocom-files / zork1

Zork I: The Great Underground Empire
11 stars 3 forks source link

Missing buoy message #48

Open eriktorbjorn opened 5 years ago

eriktorbjorn commented 5 years ago

In older version (I've tried this with Release 30) you get a slight hint if you pick up the buoy:

>GET BUOY
Taken.
You notice something funny about the feel of the buoy.

But in the current version, you don't get that message:

>GET BUOY
Taken.

It's supposed to be printed by RIVR4-ROOM:

<GLOBAL BUOY-FLAG T>

<ROUTINE RIVR4-ROOM (RARG)
     <COND (<EQUAL? .RARG ,M-END>
        <COND (<AND <IN? ,BUOY ,WINNER> ,BUOY-FLAG>
                   <TELL
"You notice something funny about the feel of the buoy." CR>
               <SETG BUOY-FLAG <>>)>)>>

I can see why that should work, because according to the documentation "A simple way for an event to occur is by having an M-END clause in the room's action routine. At the end of every turn (but before CLOCKER is called) the current room's action routine is automatically called with the argument M-END."

But that doesn't seem to happen. Judging by the debug messages I tried adding to the routine, RARG is only M-ENTER or M-LOOK.

Though when I look at main.zil in zork-substrate, it looks like this is the only reference to M-END:

        <COND (<NOT <==? .V ,M-FATAL>>
           ;<COND (<==? <LOC ,WINNER> ,PRSO>
              <SETG PRSO <>>)>
           <SET V <APPLY <GETP <LOC ,WINNER> ,P?ACTION> ,M-END>>)>

So wouldn't that get called in the boat, not in the room?

We should probably look into other cases where M-END is used, and there may be vehicles involved...

eriktorbjorn commented 5 years ago

Looking further in the ZIL manual, I guess it's deliberate:

Another purpose [of vehicles] is that it gives the vehicle an opportunity to handle the input, via
M-BEG, as you'll read about in the section called The Bigger Picture.
Finally, some vehicles do actually move the player around from room to room,
often in interesting ways.
Next, PERFORM gives the room's action routine an opportunity by calling it with
an argument called M-BEG. (Actually, if the player's LOC is not a room,
PERFORM first calls the vehicle's action routine.)

It's still a bit unclear from that if it should call both the vehicle's and the room's action routine. But it definitely should call the vehicle's. Looking at other games, most seem to call the action routine in <LOC ,WINNER>, though not all of them.

eriktorbjorn commented 5 years ago

The Solid Gold version has the same bug, but interestingly Mini-Zork I doesn't. There the message is handled by BUOY-F instead:

<ROUTINE BUOY-F ()
         <COND (<VERB? OPEN>
                <SCORE-OBJ ,EMERALD>
                <RFALSE>)
               (<AND <VERB? TAKE>
                     <NOT <IN? ,BUOY ,ADVENTURER>>
                     <IN? ,EMERALD ,BUOY>>
                <MOVE ,BUOY ,ADVENTURER>
                <TELL
"As you take the buoy, you notice something odd about the feel of it." CR>)>>

So maybe that's the way to do it here as well?

Note that the original code only prints the message once. Mini-Zork I prints it as long as the emerald is inside the buoy. Also, Mini-Zork I probably allows you to pick up the buoy even if you're carrying too much. (Fortunately, PRE-TAKE still gets to restrict when you can take the buoy.)