Carry Out rules

As I mentioned in my post-match interview, ‘course correction’ was basically the first time I used action rules that weren’t ‘Instead’. However, I found that more often than not, if I tried to use ‘carry out’, it didn’t do what I expected it to do. If I changed the ‘carry out’ to ‘check’, then stuff did what I had thought I understood ‘carry out’ was doing.

Here’s one example, simplified:

Testing is a room.

Large hole is a door.  It is east of Testing and west of Test2.

Before going east from Testing:
	say "You crawl through the hole";
	try entering large hole instead;

carry out entering large hole:
	say "Well, here we go.";

If you go east from Testing, it just takes you straight to Test2:

>e
You crawl through the hole.

Test2
You can see Large hole here.

>

But if I change ‘carry out’ to ‘check’, it Does What I Meant:

>e
You crawl through the hole.

Well, here we go.

Test2
You can see Large hole here.

>

When I had zero time to investigate, I just changed to using ‘check’, but now there’s time! Can someone explain what’s going on? I feel like it has to be ‘carry out doesn’t mean what you think it means’.

1 Like

This is a very specific edge case!

The trick is, when you enter a door, the standard rules convert that into “going the door”. So first, the player tries to “go east”, then your rule converts that into “enter the door”, then the standard rules convert that into “go the door”. The “enter the door” action never reaches the carry out stage, just like the “go east” action never does.

5 Likes

Oh! So if instead of checking ‘enter the door’ I check ‘go the door’, I wouldn’t need my ‘before’ rule! And then I could use a ‘carry out going the door’.

1 Like

@lpsmith Do you know about the testing commands ACTIONS and RULES?

If you type ACTIONS (every action carried out will be named while you’re testing) then make the move EAST, you will see the cascade of stuff that happens when you have that Before rule in place.

EDIT - Put on RULES as well for even more detail.

-Wade

3 Likes

I knew about ACTIONS, but I’m not sure I would have thought to use it in this case? I had forgotten about RULES, though; that’s a good one.

When an action rule doesn’t seem to be triggering, ACTIONS is generally a good place to turn. Many times, the action in question is never happening at all! (This has happened to me quite a lot.)

1 Like

In this case, I knew it was triggering because changing it to ‘check’ made it work. I would not have guessed that a different check caused a redirect, partly because I had been told that ‘before’ rules were the place to put redirects!

I did remember hearing that doors in I7 were wonky, and that it was often better to just not try to use them. But it was very old advice, so I figured ‘maybe they’ve gotten better; how wonky can they be?’ This wonky, apparently! Makes sense after the fact, at least.

But that’s good to know in general; thank you. One of my goals with this project was to learn I7 better, and that is absolutely happening, largely thanks to you all.

-Lucian

I don’t think there’s a good reason to use Carry Out here (or, most likely, for any predefined action – unless you’re completely rewriting its inner workings). Either Check or Instead seems like it should be sufficient, although given that you’re only printing text, I wonder if maybe First Report would be better.

This was just a simple example; the actual original routine is:

which does a whole scene transition! It worked to put it in a ‘check’ rule, but it seemed a bit much for that sort of thing, just semantically. As you say, it ‘completely rewrites its inner workings’.

Doing it ‘right’ would involve changing ‘entering’ to ‘going’, and putting the first two bits in a ‘check’, and then the last bit in a ‘carry out’. I think. I’m testing things now.

Again, it works as-written, but part of the point of this is to figure out the way to write stuff the ‘right way’, to avoid friction in the future.

I think you misunderstood something? What you showed isn’t rewriting the inner workings of the going action – far from it. Rewriting the inner workings would essentially be deleting everything from the Check, Carry Out, and Report rulebooks for that action, and defining your own rules in their place.

To put it another way: I think you generally shouldn’t use Carry Out rules unless the action is something that you control the entirety of. It’s an action you’ve defined yourself from the ground up.

I’m not sure I can think of a better place to put “run all the normal checks for this action, then completely override its internal behavior” than “first carry out”, though.

There’s also Last Check as a possibility for that case. I’m not sure if there’s a practical difference between the two…

I feel like I’m going to be able to better remember what goes where if I think of ‘checks’ as, well, checking, and ‘carry outs’ as doing a thing. I get semantically itchy looking at my ‘check’ code and see it changing the world state, especially to that extent. As you say, no practical difference; it’s just readability and understanding.

But it does seem like I definitely want it ‘First’!

1 Like

The intent of the design is that there’s a stark dividing line between Check rules and Carry out rules. Actions that get stopped during their Check rules (or prior) failed and any action still going beyond that point has succeeded (whether there were any more rules to be followed) by definition.[1]

Now, unless you’re using unsucessful attempt by rules or are attempting the fairly doomed endeavor of testing whether an action succeeded, this distinction… doesn’t matter a lot.

But what can matter a fair bit, though, is developing and employing consistent habits of where you put what so you don’t sabotage your future self’s ability to apprehend your own code. Ideally, your first guess about how would I have done that? should actually be right.

These principles inform my habits.

Before rules are where you re-dispatch to a different action, as appropriate. Once we’re past considering whether that’s appropriate, any number of other things tappropriate to do prior to the Basic Visibility, Basic Accessibility, and Carrying Requirements rules might happen, but typically not stopping the action because that looks like a job for…

Check rules arewhere you test whether the action should continue and, if not, output an appropriate message and stop the action. Instead rules are where you do those things if there’s a compelling reason you can’t do them in Check rules.

Changing the world state is the domain of (principally) Carry Out rules, but it’s acceptable in After rules. If something really couldn’t be done otherwise, I’d consider a Before or Instead rule, but if the day came that I was considering a Check or Report rule, I’d conclude my thinking had gone off the rails and I should start over.

Output is the domain of Report rules. In a pinch I’d consider an After rule, but I prefer to write a first report rule with stop the action to the common Inform idiom of using an After rule just for customize output and skip the default Report rules.

…unless it’s an action whose whole point is to generate output without changing the world state like examining or taking inventory. The Standard Rules’ norm is to implement those through Carry Out rules and it does no harm.

I’m not saying the above is correct but I am saying that I have benefited from following a scheme consistently.


  1. per my merciless pedantry pledge, there’s a bug in 10.1 by which an explicit rule fails in an after rule ends up flouting the definitive behavior ↩︎

6 Likes

If you get into NPCs doing actions then it’s more important to use the report rules, as they might not be doing something in the sight of the player.

1 Like