Custom inventory

In this game, I’ve separated the inventory into clothing, worn objects that aren’t clothing (eg, binoculars around the neck) and carried objects, listing contents of containers separately after the appropriate category:

"Test" by Colleen Boye

[clothing and inventory management]
A garment is a kind of wearable thing.
Definition: a thing is a non-garment if it is not a garment.
[suppresses listing contents of things like the pistol cylinder]
A container can be interesting or uninteresting. A container is usually interesting.

[lists the contents of a container]
Pedantically listing something is an activity on things.
Rule for pedantically listing a thing (called X):
	if X is open or X is transparent:
		if X contains something and X is interesting:
			if X contains exactly one thing:
				say "[The X] [contain] ";
				list the contents of X, giving brief inventory information;
				say ".[line break]";
			otherwise:
				say "[The X] [contain]: [line break]";
				list the contents of X, with newlines, indented, giving brief inventory information, with extra indentation.
	
[custom way of listing inventory]
Instead of taking inventory: 
	if the number of things enclosed by the player is 0, say "You are empty-handed." instead; 
	if the player wears a garment: 
		now all things enclosed by the player are unmarked for listing; 
		now all garments worn by the player are marked for listing; 
		say "The clothing you are wearing: [line break]"; 
		list the contents of the player, with newlines, indented, with extra indentation, giving brief inventory information, listing marked items only;
	[contents of clothing containers listed individually]
	repeat with X running through garments worn by the player:
		carry out the pedantically listing activity with X;
		[containers enclosed by clothing]
		repeat with Y running through interesting containers enclosed by X:
			carry out the pedantically listing activity with Y;
	if the player wears a non-garment: [binoculars, etc]
		now all things enclosed by the player are unmarked for listing; 
		now every non-garment worn by the player is marked for listing; 
		say "You are also wearing: [line break]"; 
		list the contents of the player, with newlines, indented, with extra indentation, giving brief inventory information, listing marked items only;
	[contents of worn non-clothing containers listed individually]
	repeat with X running through non-garment things worn by the player:
		carry out the pedantically listing activity with X;
		[containers enclosed by non-clothing]
		repeat with Y running through interesting containers enclosed by X:
			carry out the pedantically listing activity with Y;
	if the player carries something: 
		now all things enclosed by the player are unmarked for listing; 
		now all things carried by the player are marked for listing; 
		say "You are carrying: [line break]"; 
		list the contents of the player, with newlines, indented, giving brief inventory information, with extra indentation, listing marked items only;
	[lists contents of carried containers individually]
	repeat with X running through things carried by the player:
		carry out the pedantically listing activity with X;
		[containers enclosed by carried objects]
		repeat with Y running through interesting containers enclosed by X:
			carry out the pedantically listing activity with Y.
			
[example]
The airport is a room.
The player is in the airport.

The coat is a garment.
The pockets are part of the coat. They are plural-named. They are a container.
Rule for printing the name of the pockets while taking inventory: say "coat pockets".
A train ticket is in the pockets.
A pen is in the pockets.

The binoculars are a wearable thing. They are plural-named.
Rule for printing the name of the binoculars while taking inventory:
	say "pair of binoculars".
	
The wrong suitcase is a container.
A thing called someone else's clothing is in the wrong suitcase.

The player wears the coat. The player wears the binoculars. The player carries the wrong suitcase.

test me with "i".

There are a few further refinements I’d like add. First, as with the binoculars, sometimes I want a plural-named item to be treated as singular only when taking inventory. It should show up as “a pair of binoculars,” not “some pair of binoculars.”

Second, if there are multiple identical containers with identical contents, I’d like them to group together (eg, “Each box of Girl Scout cookies contains 20 thin mints.”). But naturally, they should be separate if they have different contents, and with appropriate adjectives modifying the names (“One box of Girl Scout cookies contains 20 thin mints. Another box of Girl Scout cookies contains 16 samoas. A third box of Girl Scout cookies contains 25 trefoils.”).

Third, I’d like to mark items that weren’t in your inventory last time you checked (bold, with an asterisk, whatever).

Can anyone help me with these problems?

Your first question is pretty easy:

The indefinite article of the binoculars is "a".

No, that’s exactly what I don’t want: Then they’ll show up as “a binoculars” when I’m not taking inventory.

Here’s a solution for your third question:

A thing can be checked or unchecked. A thing is usually unchecked.

Before printing the name of an unchecked thing while taking inventory:
	say "[bold type]".
	
After printing the name of an unchecked thing (called item) while taking inventory:
	say "*[roman type]".
	
After taking inventory:
	now every thing that is enclosed by the player is checked.
	
When play begins:
	now every thing that is enclosed by the player is checked.
	
Every turn:
	now every checked thing that is not enclosed by the player is unchecked.

Whoops, sorry; I originally wrote the sample code assuming the full name of the object was “pair of binoculars” (which stays grammatically correct with both “a” or “the”), and then changed it without checking all cases.

You could do this instead: strike your rule for printing the name of the binoculars while taking inventory, and add this:

The indefinite article of the binoculars is "a pair of"

That makes them “a pair of binoculars” whenever the game wants to use the indefinite article (which includes taking inventory), and “the binoculars” everywhere else.

Thanks, those are both elegant solutions!

What if I wanted a different definite article? Like if I want it to say “Your pockets contain:” and “You put your pen into your pockets” and so on, but I don’t want to make the actual name of the item “your pockets” or “your pen”.

Number 3 is pretty straightforward, at least in the simplest cases; just set a property to see if something was in the inventory last time you checked, and print the asterisk if it isn’t in the inventory. Since you’re using an “instead” rule for taking inventory I put the phrase that does this as the last line of the rule, instead of in an “after” rule.

The tricky thing might be if you have multiple instances of something, in which case I don’t think you’d print the name of it. Maybe you could also hook it on to printing the plural name. I also thought it would be simplest just to deal with all the things enclosed by the player, but if there are things enclosed by the player hidden in the inventory (say, the contents of a closed container) that might not work as well–in that case maybe you’d want to set the “noted in inventory” property after printing the name of something while taking inventory, though again you’d have to watch out for plural names.

Also, I found out that your code prints “You are also wearing” for the binoculars even when you aren’t wearing the coat, so I included a test for that. Anyway, hope the other thing is helpful, even if it doesn’t work smoothly out of the box!

"Test" by Colleen Boye

[clothing and inventory management]
A garment is a kind of wearable thing.
Definition: a thing is a non-garment if it is not a garment.
[suppresses listing contents of things like the pistol cylinder]
A container can be interesting or uninteresting. A container is usually interesting.

[lists the contents of a container]
Pedantically listing something is an activity on things.
Rule for pedantically listing a thing (called X):
	if X is open or X is transparent:
		if X contains something and X is interesting:
			if X contains exactly one thing:
				say "[The X] [contain] ";
				list the contents of X, giving brief inventory information;
				say ".[line break]";
			otherwise:
				say "[The X] [contain]: [line break]";
				list the contents of X, with newlines, indented, giving brief inventory information, with extra indentation.
	
[custom way of listing inventory]
Instead of taking inventory: 
	if the number of things enclosed by the player is 0, say "You are empty-handed." instead; 
	if the player wears a garment: 
		now all things enclosed by the player are unmarked for listing; 
		now all garments worn by the player are marked for listing; 
		say "The clothing you are wearing: [line break]"; 
		list the contents of the player, with newlines, indented, with extra indentation, giving brief inventory information, listing marked items only;
	[contents of clothing containers listed individually]
	repeat with X running through garments worn by the player:
		carry out the pedantically listing activity with X;
		[containers enclosed by clothing]
		repeat with Y running through interesting containers enclosed by X:
			carry out the pedantically listing activity with Y;
	if the player wears a non-garment: [binoculars, etc]
		now all things enclosed by the player are unmarked for listing; 
		now every non-garment worn by the player is marked for listing; 
		say "You are [if the player wears a garment]also [end if]wearing: [line break]"; 
		list the contents of the player, with newlines, indented, with extra indentation, giving brief inventory information, listing marked items only;
	[contents of worn non-clothing containers listed individually]
	repeat with X running through non-garment things worn by the player:
		carry out the pedantically listing activity with X;
		[containers enclosed by non-clothing]
		repeat with Y running through interesting containers enclosed by X:
			carry out the pedantically listing activity with Y;
	if the player carries something: 
		now all things enclosed by the player are unmarked for listing; 
		now all things carried by the player are marked for listing; 
		say "You are carrying: [line break]"; 
		list the contents of the player, with newlines, indented, giving brief inventory information, with extra indentation, listing marked items only;
	[lists contents of carried containers individually]
	repeat with X running through things carried by the player:
		carry out the pedantically listing activity with X;
		[containers enclosed by carried objects]
		repeat with Y running through interesting containers enclosed by X:
			carry out the pedantically listing activity with Y;
	mark the inventory.
			
[example]
The airport is a room.
The player is in the airport.

The coat is a garment.
The pockets are part of the coat. They are plural-named. They are a container.
Rule for printing the name of the pockets while taking inventory: say "coat pockets".
A train ticket is in the pockets.
A pen is in the pockets.

The binoculars are a wearable thing. They are plural-named. The indefinite article of the binoculars is "a pair of".	

The wrong suitcase is a container.
A thing called someone else's clothing is in the wrong suitcase.

The player wears the coat. The player wears the binoculars. The player carries the wrong suitcase.

A thing can be noted in inventory. 
To mark the inventory:
	now everything is not noted in inventory;
	now everything enclosed by the player is noted in inventory.
When play begins: mark the inventory.
Before printing the name of a not noted in inventory thing while taking inventory: say "*[run paragraph on]".

test me with "i/drop coat/i/take coat/i".

The thing you want to do with the boxes of Girl Scout cookies seems like it’ll have to involve grouping things together, which can be a real bear when you’re trying to do something complicated with it… I wouldn’t be able to look at it for a little while. (I think the bugs we’re talking about in that thread are all fixed, though.)

It’s very helpful, though I’m still working out some kinks with the new item marking. The one additional thing it needed was of course the same rule after printing the plural name of something. But after adding that it works just right with the item checking at the end of the inventory-listing algorithm.

I was hoping to check items immediately after naming them, so that they won’t also show up checked when it says “The suitcase* contains…” It seems like this ought to do it:

[emphasizing new items by printing a note after them]
A thing can be checked or unchecked. A thing is usually unchecked.
After printing the name of an unchecked thing (called X) while taking inventory:
	say " [bracket]new item[close bracket]";
	now X is checked.
	
[unchecked groups of items]
After printing the plural name of an unchecked thing (called X) while taking inventory:
	say " [bracket]new items[close bracket]";
	now X is checked.

But instead the behavior in the airport gets REALLY strange (I’ve left everything initially unchecked for test purposes). Anything that uses the default indefinite article “a” doesn’t get marked as a new item, and anything that doesn’t use that article (plural items, names with no article, items with a different article specified) does get marked. This can be verified by changing the indefinite articles of the various items. Why on earth would that happen?

(Full text of the example below.)

"Test" by Colleen Boye

[clothing and inventory management]

[separating clothes from other worn things]
A garment is a kind of wearable thing.
Definition: a thing is a non-garment if it is not a garment.
[manually suppresses listing contents of certain things]
A container can be interesting or uninteresting. A container is usually interesting.

[emphasizing new items by printing a note after them]
A thing can be checked or unchecked. A thing is usually unchecked.
After printing the name of an unchecked thing (called X) while taking inventory:
	say " [bracket]new item[close bracket]";
	now X is checked.
	
[unchecked groups of items]
After printing the plural name of an unchecked thing (called X) while taking inventory:
	say " [bracket]new items[close bracket]";
	now X is checked.
	
[When play begins:
	now every visible thing enclosed by the player is checked.]

[lists the contents of a container]
Pedantically listing something is an activity on things.
Rule for pedantically listing a thing (called X):
	if X is open or X is transparent:
		if X contains something and X is interesting:
			if X contains exactly one thing:
				say "[The X] [contain] ";
				list the contents of X, giving brief inventory information;
				say ".[line break]";
			otherwise:
				say "[The X] [contain]: [line break]";
				list the contents of X, with newlines, indented, giving brief inventory information, with extra indentation.
	
[custom way of listing inventory]
Instead of taking inventory: 
	if the number of things enclosed by the player is 0, say "You are empty-handed." instead;
	if the player wears a garment: 
		now all things enclosed by the player are unmarked for listing; 
		now all garments worn by the player are marked for listing; 
		say "The clothing you are wearing: [line break]"; 
		list the contents of the player, with newlines, indented, with extra indentation, giving brief inventory information, listing marked items only;
	[contents of clothing containers listed individually]
	repeat with X running through garments worn by the player:
		carry out the pedantically listing activity with X;
		[containers enclosed by clothing]
		repeat with Y running through interesting containers enclosed by X:
			carry out the pedantically listing activity with Y;
	if the player wears a non-garment: [binoculars, etc]
		now all things enclosed by the player are unmarked for listing; 
		now every non-garment worn by the player is marked for listing; 
		say "You are also wearing: [line break]"; 
		list the contents of the player, with newlines, indented, with extra indentation, giving brief inventory information, listing marked items only;
	[contents of worn non-clothing containers listed individually]
	repeat with X running through non-garment things worn by the player:
		carry out the pedantically listing activity with X;
		[containers enclosed by non-clothing]
		repeat with Y running through interesting containers enclosed by X:
			carry out the pedantically listing activity with Y;
	if the player carries something: 
		now all things enclosed by the player are unmarked for listing; 
		now all things carried by the player are marked for listing; 
		say "You are carrying: [line break]"; 
		list the contents of the player, with newlines, indented, giving brief inventory information, with extra indentation, listing marked items only;
	[lists contents of carried containers individually]
	repeat with X running through things carried by the player:
		carry out the pedantically listing activity with X;
		[containers enclosed by carried objects]
		repeat with Y running through interesting containers enclosed by X:
			carry out the pedantically listing activity with Y.
	[now every visible thing enclosed by the player is checked.]
			
[example]
The airport is a room.
The player is in the airport.

The coat is a garment.
The pockets are part of the coat. They are plural-named. They are a container.
Rule for printing the name of the pockets while taking inventory: say "coat pockets".
A train ticket is in the pockets.
A pen is a kind of thing.
There are two pens in the pockets.

The binoculars are a wearable thing. They are plural-named. The indefinite article of the binoculars is "a pair of".	

The wrong suitcase is a closed, opaque, openable container.
A thing called someone else's clothing is in the wrong suitcase.

The player wears the coat. The player wears the binoculars. The player carries the wrong suitcase.

In the airport is a coin.

test me with "i/take coin/i/open suitcase/i".

I added this to your code to get a better view of what’s happening:

A thing has a number called times printed.	

Before printing the name of a thing (called X) while taking inventory:
	say "([times printed of X])";
	now times printed of X is times printed of X + 1.

Before printing the plural name of a thing (called X) while taking inventory:
	say "([times printed of X])";
	now times printed of X is times printed of X + 1.

That gives us this:

Test
An Interactive Fiction by Colleen Boye
Release 1 / Serial number 160405 / Inform 7 build 6M62 (I6/v6.33 lib 6/12N) SD

airport
You can see a coin here.

>i
The clothing you are wearing: 
  a (1)coat
The (1)coat pockets contain: 
  a (1)train ticket
  two (0)pens [new items]
You are also wearing: 
  a pair of (0)binoculars [new item]
You are carrying: 
  a (1)wrong suitcase (closed)

>i
The clothing you are wearing: 
  a (3)coat
The (3)coat pockets contain: 
  a (3)train ticket
  two (1)pens
You are also wearing: 
  a pair of (1)binoculars
You are carrying: 
  a (3)wrong suitcase (closed)

>i
The clothing you are wearing: 
  a (5)coat
The (5)coat pockets contain: 
  a (5)train ticket
  two (2)pens
You are also wearing: 
  a pair of (2)binoculars
You are carrying: 
  a (5)wrong suitcase (closed)

We can see that the objects with default articles have their names printed twice each time that we take inventory.

After some investigation, I found this thread that explains what’s going on.

The thread’s author, Taryn Michelle, packaged the workaround as an extension called Print Stage Detection. I did a quick comparison of the I6 PrefaceByArticle code in the extension with the version generated by I7 6M62, and it appears to be identical other than the article_choosing stuff that Taryn added.

So, I’d suggest grabbing and installing the extension, at which point you can do:

Include Print Stage Detection by Taryn Michelle.

After printing the name of an unchecked thing (called X) while taking inventory:
	say " [bracket]new item[close bracket]";
	if the print-stage is name-printing:
		now X is checked.

[unchecked groups of items]
After printing the plural name of an unchecked thing (called X) while taking inventory:
	say " [bracket]new items[close bracket]";
	if the print-stage is name-printing:
		now X is checked.

This is the output:

Test
An Interactive Fiction by Colleen Boye
Release 1 / Serial number 160405 / Inform 7 build 6M62 (I6/v6.33 lib 6/12N) SD

airport
You can see a coin here.

>test me
(Testing.)

>[1] i
The clothing you are wearing: 
  a coat [new item]
The coat pockets [new item] contain: 
  a train ticket [new item]
  two pens [new items]
You are also wearing: 
  a pair of binoculars [new item]
You are carrying: 
  a wrong suitcase [new item] (closed)

>[2] take coin
Taken.

>[3] i
The clothing you are wearing: 
  a coat
The coat pockets contain: 
  a train ticket
  two pens
You are also wearing: 
  a pair of binoculars
You are carrying: 
  a coin [new item]
  a wrong suitcase (closed)

>[4] open suitcase
You open the wrong suitcase, revealing someone else's clothing.

>[5] i
The clothing you are wearing: 
  a coat
The coat pockets contain: 
  a train ticket
  two pens
You are also wearing: 
  a pair of binoculars
You are carrying: 
  a coin
  a wrong suitcase
The wrong suitcase contains someone else's clothing [new item].

>

Here’s the full code:

"Test" by Colleen Boye

Include Print Stage Detection by Taryn Michelle.

[clothing and inventory management]

[separating clothes from other worn things]
A garment is a kind of wearable thing.
Definition: a thing is a non-garment if it is not a garment.
[manually suppresses listing contents of certain things]
A container can be interesting or uninteresting. A container is usually interesting.

A person has a number called rule count.

[emphasizing new items by printing a note after them]
A thing can be checked or unchecked. A thing is usually unchecked.

After printing the name of an unchecked thing (called X) while taking inventory:
	say " [bracket]new item[close bracket]";
	if the print-stage is name-printing:
		now X is checked.

[unchecked groups of items]
After printing the plural name of an unchecked thing (called X) while taking inventory:
	say " [bracket]new items[close bracket]";
	if the print-stage is name-printing:
		now X is checked.

[When play begins:
now every visible thing enclosed by the player is checked.]

[lists the contents of a container]
Pedantically listing something is an activity on things.
Rule for pedantically listing a thing (called X):
	if X is open or X is transparent:
		if X contains something and X is interesting:
			if X contains exactly one thing:
				say "[The X] [contain] ";
				list the contents of X, giving brief inventory information;
				say ".[line break]";
			otherwise:
				say "[The X] [contain]: [line break]";
				list the contents of X, with newlines, indented, giving brief inventory information, with extra indentation.

[custom way of listing inventory]
Instead of taking inventory: 
	if the number of things enclosed by the player is 0, say "You are empty-handed." instead;
	if the player wears a garment: 
		now all things enclosed by the player are unmarked for listing; 
		now all garments worn by the player are marked for listing; 
		say "The clothing you are wearing: [line break]"; 
		list the contents of the player, with newlines, indented, with extra indentation, giving brief inventory information, listing marked items only;
	[contents of clothing containers listed individually]
	repeat with X running through garments worn by the player:
		carry out the pedantically listing activity with X;
		[containers enclosed by clothing]
		repeat with Y running through interesting containers enclosed by X:
			carry out the pedantically listing activity with Y;
	if the player wears a non-garment: [binoculars, etc]
		now all things enclosed by the player are unmarked for listing; 
		now every non-garment worn by the player is marked for listing; 
		say "You are also wearing: [line break]"; 
		list the contents of the player, with newlines, indented, with extra indentation, giving brief inventory information, listing marked items only;
	[contents of worn non-clothing containers listed individually]
	repeat with X running through non-garment things worn by the player:
		carry out the pedantically listing activity with X;
		[containers enclosed by non-clothing]
		repeat with Y running through interesting containers enclosed by X:
			carry out the pedantically listing activity with Y;
	if the player carries something: 
		now all things enclosed by the player are unmarked for listing; 
		now all things carried by the player are marked for listing; 
		say "You are carrying: [line break]"; 
		list the contents of the player, with newlines, indented, giving brief inventory information, with extra indentation, listing marked items only;
	[lists contents of carried containers individually]
	repeat with X running through things carried by the player:
		carry out the pedantically listing activity with X;
		[containers enclosed by carried objects]
		repeat with Y running through interesting containers enclosed by X:
			carry out the pedantically listing activity with Y.
	[now every visible thing enclosed by the player is checked.]

[example]
The airport is a room.
The player is in the airport.

The coat is a garment.
The pockets are part of the coat. They are plural-named. They are a container.
Rule for printing the name of the pockets while taking inventory: say "coat pockets".
A train ticket is in the pockets.
A pen is a kind of thing.
There are two pens in the pockets.

The binoculars are a wearable thing. They are plural-named. The indefinite article of the binoculars is "a pair of".	

The wrong suitcase is a closed, opaque, openable container.
A thing called someone else's clothing is in the wrong suitcase.

The player wears the coat. The player wears the binoculars. The player carries the wrong suitcase.

In the airport is a coin.

test me with "i/take coin/i/open suitcase/i".

An addendum:

Ideally, the Print Stage Detection extension wouldn’t be needed. While looking at katz’s issue, I found this in the Standard Rules:

Before printing the name of a thing (called the item being printed)
	(this is the make named things mentioned rule):
	if expanding text for comparison purposes, continue the activity;
	now the item being printed is mentioned.

To decide if expanding text for comparison purposes:
	(- say__comp -).

Maybe I7 should set say__comp during article choosing in PrefaceByArticle.

Erm…Inform’s refusing to install that extension for me. (This is 6L38.)

On which platform? Does it produce an error msg?

As far as I know, there’s nothing to the installation process other than copying the file to //.i7x
On my OS X box, that’s /Users/vince/Library/Inform/Extensions/Taryn Michelle/Print Stage Detection.i7x

The Mac Inform app has a “File->Show Installed Extensions Folder” menu option that will locate the extensions directory for you. I assume that a similar option exists on other platforms as well.

38 on a Mac won’t do extensions at all.

I’ve just been talking about this in another thread, but first - what OS are you using? There’s a workaround if you have 10.6.8 (and if you have later, you can get 62, which should be able to handle extensions properly). If your OS is older than 10.6.8, then you probably won’t be able to get extensions at all.

If you use Windows or Linux, feel free to ignore this post.

Er, not sure what you mean. You can compile a game with extensions. I recall there were some bugs but I don’t remember which ones you’re referring to.

I ran 6L38 on a Mac until very recently, and I was able to install extensions both manually (copying the files to the correct location) and via the public library. However, when I opened an uninstalled extension with Inform and clicked its install button, nothing would happen.

Also, the current release of 6M62 will now run w/o crashing on 10.6.8, although it still has an issue where the grey progress bar area at the top floats around the workspace when the window is resized.

I’m using Windows 7. It just says “Failed to install extension” when I try to install through the IDE. I tried manually putting it in the right folder and then including it in the game but Inform barfed in a bad way:

It looks like you tried feeding Inform an html version of the extension. Try again with the raw plaintext version and see if it works.

Everyone else is right, of course; 38 on 10.6.8 does work with public library after all, but through a combination of that failure-to-install bug that vlaviano mentioned and a different quirk regarding failure of the inbuilt extensions (does Rideable Animals even work any more?), I’ve only just realised that any of this is possible without downloading the extensions via 62 first.

Slightly annoyed with myself for not realising this earlier, of course.

(And unless there’s been a new version of 62 since Sunday, it still doesn’t run without crashing on 10.6.8. But that’s for another thread.)

Didn’t mean to derail yours, katz, sorry.

Yeah.

Include Rideable Vehicles by Graham Nelson.

West End of Road is west of East End of Road.

The horse is a rideable animal in West End of Road.

Test me with "mount horse / e".

I think there very well might have been. Emily posted that a new version was available on Monday, and I downloaded it and confirmed that it no longer crashed. My previous attempt had been on Thursday March 31st, and it still crashed at that time.

Got it working–so far, so good. Thanks, everyone!