An issue with the U-Stor-It example

The U-Stor-It example (number 58 in the documentation) gives a way to make a chest, a container whose lid acts as a supporter. For the most part the code works great.

But I’ve found what I think is a bug in it. If a chest is closed and opaque, and its lid is enterable, then when standing on the lid you can’t see anything in the room. In other words, a supporter that’s part of a closed container is assumed to be on the outside for most purposes (you don’t need to pass through the container to touch it) but on the inside when calculating visibility from it (if you’re standing on it, you can’t see the room).

Is there a straightforward way to fix this?

5 Likes

It requires modification of:

  • OffersLight()
  • VisibilityParent()
  • FindVisibilityLevels()
  • the room description heading rule

which when done produces output like:

U-Stor-It Facility
You can see a sea trunk (closed), a shipping crate (closed) and a metal box (on which is a small card) here.

>OPEN TRUNK
You open the sea trunk.

>ENTER IT
You get into the sea trunk.

>LOOK
U-Stor-It Facility (in the sea trunk)
You can see a shipping crate (closed) and a metal box (on which is a small card) here.

>GET OUT
You get out of the sea trunk.

U-Stor-It Facility
You can see a sea trunk (empty), a shipping crate (closed) and a metal box (on which is a small card) here.

>CLOSE TRUNK'S LID
You close the sea trunk.

>GET ON IT
You get onto the sea trunk's lid.

>LOOK
U-Stor-It Facility (on the sea trunk's lid) (attached to the sea trunk)
You can see a shipping crate (closed) and a metal box (on which is a small card) here.

>GET OFF
You get off the sea trunk's lid.

U-Stor-It Facility
You can see a sea trunk (closed), a shipping crate (closed) and a metal box (on which is a small card) here.

>LOOK
U-Stor-It Facility
You can see a sea trunk (closed), a shipping crate (closed) and a metal box (on which is a small card) here.

EDIT: Note that the code behind the transcript was not posted because it does not resolve other issues related to the situation involving accessibility. See the two threads mentioned in the post below.

6 Likes

The less-intrusive way to deal with this is to make the ‘chest’ part of the ‘lid’ rather than vice versa.

Think of an enterable desk incorporating an enterable drawer. Then divert actions appropriately- e.g. open desk → open drawer.

EDIT The only problem that then needs to be solved is that when in the open ‘chest’ the look action (somewhat surprisingly) reports (on the lid) rather than (in the chest)

4 Likes

FYI to interested parties, there are some previous topics that deal with this and related issues:

(You were the last poster on one of them, Draconis.)

4 Likes

Aha, so I was! This looks like exactly the same bug.

Due to a sudden last-minute issue I needed to combine a container (opening it is a puzzle) and an enterable supporter (standing on it is part of a puzzle) into a single object, and I thought the U-Stor-It example would be exactly what I needed. I’d forgotten that I’d seen this same bug all those years ago.

There are a lot more details to address, including ensuring the lid and body move at the sime time if they’re portable or pushable between rooms, but I think this approach is probably viable.

hinged-box-body is kind of container.
hinged-box-body is usually closed.
hinged-box-body is usually openable.
hinged-box-lid is kind of supporter.

Rule for writing a paragraph about hinged-box-lid (called top):
    now top is mentioned.

hinged-box-body has a hinged-box-lid.
hinged-box-lid has a hinged-box-body.

enliddification relates one hinged-box-lid to one hinged-box-body.
the verb to enliddify means the enliddification relation.
every hinged-box-body is enliddified by a hinged-box-lid (called its lid).

after starting the virtual machine:
    repeat with x running through the hinged-box-bodies begin;
      let top be a random hinged-box-lid that enliddifies x;
      now the hinged-box-lid of x is top;
      now the hinged-box-body of top is x;
      move the top to the location of x;
    end repeat;

first before an actor doing anything except climbing with a hinged-box-lid (called the top): now the noun is (the hinged-box-body of the top).

first before an actor putting something on a hinged-box-body (called the box): now the noun is (the hinged-box-lid of the box).
first before an actor climbing a hinged-box-body (called the box): now the noun is (the hinged-box-lid of the box).

check an actor opening a closed hinged-box-body (called the box) when the hinged-box-lid of the box encloses the actor:
  if the actor is the player, say "[We] well have to remove [list of things on the hinged-box-lid of the box].";
  stop the action.

check an actor opening a closed hinged-box-body (called the box) when the first thing held by the hinged-box-lid of the box is not nothing:
    if the actor is the player, say "[We] will have to remove [list of things on the hinged-box-lid of the box].";
    stop the action.

understand the commands "sit", "stand" as something new.

the block climbing rule is not listed in the check climbing rules.

Understand "sit on top of [something]" as climbing.
Understand "sit on [something]" as climbing.
Understand "sit in/inside [something]" as entering.
Understand "stand on [something]" as climbing.

[ go on to make enter something that is specific to containers and climbing something specific to supporters... ]

[ edited to add: to no great surprise, I started turning this into an extension, and having gotten most of the way there, I continue to think the approach is viable… ]

2 Likes

That would be perfect, except that sadly the puzzle reasons for merging the two objects require it to be pushable between rooms.

If you do make an extension that fixes the issue, though, I’ll definitely make use of it, whether it’s fixing the visibility code or making chests work altogether differently.

1 Like

I’m feeling inclined to have it include the Modified Exit and Postures extensions: things don’t make sense if both standing on the trunk and getting into the trunk map to entering the trunk. What do you think?

2 Likes

Overkill for my one particular use case—I specifically made the interior not enterable to avoid that ambiguity—but sounds like a good thing to have in general!

In an ideal world, clearly the top of the chest and the inside of it should be independently potentially enterable from the holder of the ‘chest as composite object’ and exiting either should return the occupant to the holder of the ‘chest as composite object’.

1 Like

I’ve worked out an extension to change the world model logic so that this commonly-attemped scenario will work as naively expected. Both lighting and movement are handled.

Would anyone like to try out the alpha version?

Here’s the test transcript:

test transcript
U-Stor-It Facility
You can see a sea trunk (closed), a shipping crate (closed), a metal box (on which is a small card) and a glowing stone (providing light) here.

>test basics
(Testing.)

>[1] open trunk
You open the sea trunk.

>[2] enter it
You get into the sea trunk.

>[3] look
U-Stor-It Facility (in the sea trunk)
You can see a shipping crate (closed), a metal box (on which is a small card) and a glowing stone (providing light) here.

>[4] get out
You get out of the sea trunk.

U-Stor-It Facility
You can see a sea trunk (empty), a shipping crate (closed), a metal box (on which is a small card) and a glowing stone (providing light) here.

>[5] close trunk's lid
You close the sea trunk.

>[6] get on it
You get onto the sea trunk's lid.

>[7] look
U-Stor-It Facility (on the sea trunk's lid) (attached to the sea trunk)
You can see a shipping crate (closed), a metal box (on which is a small card) and a glowing stone (providing light) here.

>[8] get off
You get off the sea trunk's lid.

U-Stor-It Facility
You can see a sea trunk (closed), a shipping crate (closed), a metal box (on which is a small card) and a glowing stone (providing light) here.

>[9] open trunk
You open the sea trunk.

>[10] enter it
You get into the sea trunk.

>[11] close it
You close the sea trunk.

It is now pitch dark in here!

>[12] look
Darkness
It is pitch dark, and you can't see a thing.

>[13] open trunk
You open the sea trunk.

U-Stor-It Facility (in the sea trunk)
You can see a shipping crate (closed), a metal box (on which is a small card) and a glowing stone (providing light) here.

>[14] get out
You get out of the sea trunk.

U-Stor-It Facility
You can see a sea trunk (empty), a shipping crate (closed), a metal box (on which is a small card) and a glowing stone (providing light) here.

>[15] close trunk
You close the sea trunk.

>[16] put rug on crate
You put the rug on the shipping crate's lid.

>[17] put bin on trunk
You put the bin on the sea trunk's lid.

>[18] get in bin
(getting onto the sea trunk's lid)
You get into the bin.

>[19] get on rug
(getting out of the bin)
(getting off the sea trunk's lid)
(getting onto the shipping crate's lid)
You get onto the rug.

And this is some code I added to RB Ex 58 U-Stor-It (in addition to including the extension, of course) to test the changes:

expansions to scenario
Section 6 - Entering

[added because no rules comparable to those for insertion and support are included]

Before entering a closed chest (called the item):
	say "(assuming you mean [the random lid part of the item] because [the item] is closed)[command clarification break]";
	try entering a random lid part of the item instead.

Instead of entering a lid which is part of an open chest (called the item):
	say "[The item] would need to be closed first."

Section 7 - Example lighting restrictions

[added to illustrate modifications to lighting]

A glowing stone is in Facility. It is lit.
The Facility is dark.

Section 8 - Example movable and enterable items

[allows certain container and supporter pieces to be entered]  

The sea trunk and the sea trunk's lid are enterable.
The shipping crate's lid is enterable.

[added for flexibility in creating mixed containment/support situations]

The player carries an enterable supporter called a rug.
The player carries an enterable container called a bin.

Section 9 - Example reaching restrictions

[added to illustrate modifications to reaching]

Rule for reaching outside crate's lid:
	say "You can't reach outside the top of the crate.";
	deny access.

Rule for reaching inside a bin:
	say "You can't reach inside the bin.";
	deny access.

Section 10 - Additional testing

Test basics with "open trunk / enter it / look / get out / close trunk's lid / get on it / look / get off / open trunk / enter it / close it / look / open trunk".
2 Likes

User zednenem did a pretty good job of laying out the root cause in those two posts from a few years back that I mentioned. Most of the fix consists of setting up a ParentOfCoreOf() routine (as suggested by matt w) and using it where appropriate, including as part of a new CommonHolder() routine that works much like CommonAncestor().

The difficulties seem to have been introduced by the changes made to reconcile the I6-style object tree with the new incorporation tree. The existing code retains an orientation toward the primacy of the object tree and does not recognize that objects within an incorporation tree can be the parts that matter – instead, the general method seems to be to first resolve any incorporated object to its highest ancestor in the incorporation tree (aka its “core”), then try to use the object tree to determine position. With the addition of the assumption that things incorporated by others are externally-accessible (which was not necessarily the case in I6), the semantic assumptions of parts of this older code are invalidated. However, the object tree parent of a “core” object (which again is the root of an incorporation tree) will always be a semantically-valid position within the revised world model, unless it resolves to nothing (as happens for a room or for something whose core is off-stage).

Because incorporation, containment and support all count as mutually-exclusive spatial relations, it is not possible for something to be, for example, both “inside” and “part of” the same object simultaneously. Simulating an internal holder (either container or supporter) may be best achieved by using containment in combination with the fixed in place property, as suggested by zednenem, but such an object (e.g. the shelf inside a safe he suggested) would not count as “part of” its theoretical parent. I don’t see any way around that short of a change to the world model: Either incorporation could be split into internal incorporation and external incorporation or an either-or property internally-affixed/externally-affixed could work in conjunction with incorporation. I would guess that the majority of authors would find zednenem’s method to be satisfactory without a change in world model.

As it stands with the extension, it works as you described. Items linked via chains of incorporation all resolve to the same “parent of core of” object, so if there is a room Yard in which there is a thing tree that incorporates a supporter branch, and a container birdhouse is part of the branch, then exiting the birdhouse or exiting the branch both resolve to being in the Yard. This seems natural enough to me and to two other I7 authors (one programmer-oriented and one writer-oriented) with whom I discussed it. The alternative arrangement would be to make the birdhouse supported by the branch and also fixed in place, as with the “shelf inside a safe” example, in which case exiting the birdhouse resolves to being on the branch.

1 Like

Some smart people have kicked the tires on the extension, so it’s made it out of alpha stage. Here are beta 6M62 and v10 versions:

Basic Container Supporter Incorporation.i7x (17.0 KB)
Basic Container Supporter Incorporation v10.i7x (11.5 KB)

[EDIT: Updated to new beta versions (Sep 06) after an extensive discussion with drpeterbatesuk and others. The changes reduce the impact on built-in room description machinery.]

Containers and supporters part of other things should not cause any trouble for lighting or movement purposes if this extension is included in your project. There’s no documentation, but it does nothing except change the operation of some underlying I6 code and Standard Rules phrases, so there’s nothing an author needs to learn in order to to use it.

If you give it a try and find any bugs, please let me know by DM or posting here. I am interested in fixing any that turn up.

4 Likes

drpeterbatesuk identified an additional issue that occurs in this type of scenario when the player is on a lid part of a closed opaque container: the accidental listing of the items inside.

EDIT: The updated versions above are no longer affected by this issue.

1 Like