Travel from inside a Booth (adv3Lite)

Here’s an odd little perplexity. I have a great stone fireplace in a room. It’s implemented as a Booth, so the player can enter it. I’ve fixed it so that when (and only when) the player is in the fireplace, a flue object becomes visible. Thus the command ‘climb flue’ (which simply prints an error message, as the flue is not climbable) is working just fine.

But I would also like the player to be able to type ‘u’ when in the fireplace and redirect that command to ‘climb flue’. I haven’t been able to figure out how to do this. In response to ‘u’, the library has the player first (implicitly) exit the Booth, and that’s not what I need.

In inspecting the code for Container (which is what a Booth is) I don’t see an obvious hook to attach code to. I can put a beforeAction() in the fireplace object and test if gActionIs(Go), but I also need to know that the travel direction is upDir, and I don’t see any way to test that. There’s a getTravelDirection method in TravelConnector, but at the moment when this is happening, there’s not a TravelConnector.

I’ve tried a Doer. Even though I specified ‘go up’ and ‘go upDir’ and tried defining both where = diningHall and where = fireplace, the Doer prohibited ALL travel once the player was in the fireplace, turning it into a trap.

I also tried attaching a TravelConnector to the up direction in the room, but that didn’t work either. The library handling of the travel command makes the player exit the fireplace implicitly before the TravelConnector is called.

This is purely a cosmetic problem, as there’s no actual story element in it. I would just like it to look right. Suggestions would be welcome!

In a game I am working on in ADV3, I have a rope that can be climbed. If the rope has been tied to some Fixture and has been thrown or lowered to make it climbable, I allow up and down to mean Climb the rope. I got this by modifying the TravelAction.execAction to replace the action to climb the rope if its climbable or just let the TravelVia handle the travel.

I did a quick test with the Lite library, I was able to redirect up to examine me using a similar modification. You would just do the checks and replace the action, if necessary, before that While loop that moves you out of your booth. It works I’m just not certain if this kind of hack is worthwhile for just a single flue.

Thanks. That works. For reference, here’s what I did:

modify TravelAction
    execAction(cmd) {
        if ((me.isDirectlyIn(fireplace)) && (direction == upDir)) {
            doInstead(Climb, flue);
        else inherited(cmd);
1 Like

I’ve never looked at adv3Lite yet (only used adv3, but it’s what I’m used to and I like it…) Any commentary on how they compare? Is Lite substantially more user-friendly? Substantially more limited in the details you can achieve?

In adv3 it sounds like you would address this situation by tweaking some of the Booth NestedRoom methods involving preConditions, actorTravelReady, etc…

Eric himself addresses that question in the adv3Lite documentation. Rather than go to the trouble of grabbing that, I’ll just give you my own informal overview.

adv3Lite omits certain features (such as postures and room parts) that aren’t useful in most games. On the flip side, it gives you some features that are specifically inspired by Inform 7, namely Scenes and Regions. There are also Doers, which work somewhat like an Inform 7 “instead” rule.

Basically, adv3Lite’s structure of Classes is “shallow” rather than deep. A lot of the Classes, while you can use them in your code just the way you would in adv3, are simply defined by the Thing class with perhaps one or two different properties, such as isEnterable = true. This makes it a bit easier to deal with the code, I think.

The documentation is much the same, right down to the Library Reference Manual, which works just as you’d expect.

A few coding things are easier. When you write a check() rule for a verb, you don’t have to use the exit macro; adv3Lite simply assumes that if check() prints a double-quoted string, that means the check() wants to stop the action. So there are little things like that to get used to. But basically, I like it. My first couple of T3 games used adv3, but I’m perfectly happy with Lite.

1 Like

Without getting into specifics – like Jim Aikin wrote Eric addresses that exact question – I’ll give you a general thought.

I struggled with adv3 for a while. It was just too heavy for my part-time programming skills. Adv3lite was a breath of fresh air. I got to use the power of TADS, got to program to satisfy that particular itch, but never really felt buried under all the underlying code.

There’s been nothing I wanted to do that has been removed by Adv3lite and I’ve published an IFComp entry, a handful of speed-if’s and currently have a WIP.

I don’t think I would have ever finished my comp entry if I had stuck with TADS and not switched to Adv3lite.


One thing that started to annoy me this morning (and it may be the case in adv3 as well) is that the PC must engage with an NPC before starting to ask useful questions. If you just go into the room where the doctor is and ‘ask about tardis’, adv3Lite will reply, “You’re not talking to anyone.”

To fix this, one has to add this line:

gPlayerChar.currentInterlocutor = doctor;

or its equivalent, in some spot in the code where the game will run it. I’ve been putting it in the room descriptions – but if the player goes to Brief mode, that won’t solve the problem. I suppose I could park it in afterTravel, but I’m not that industrious.

Interesting info, I appreciate it. I (like many of us, I’m sure) have a very limited amount of time that I can spend toward game-making (including the learning process of libraries and documentation.) I’ve already invested so much time in reading the adv3 docs (and consequently feel quite at home with it) that I don’t feel any movings to adopt a new system now… however, the additional Lite features piqued my interest and I want to at least go glance at the Lite LibRef Manual, and see if I’d want to paste any of the new stuff into my adv3 library.
As for the check routine, I just abbreviated failCheck with my own macro, e.g.
fC('You don’t want to try that. ');
Truth be told (and this may horrify “real” programmers) I’ve defined several dozen shortcut macros, just for my own sanity and the feeling of accomplishing more in a limited time frame, for instance:

#define gpc (libGlobal.playerChar)
#define mt modify Thing
#define iO indexOf
#define lP lexicalParent
#define eR enteringRoom(traveler)
#define nT noteTraversal(traveler)
#define nTake cannotTakeMsg
#define tN theName
#define goR gpc.getOutermostRoom()
#define OWRC OneWayRoomConnector
#define SHUF ShuffledEventList
#define ASK AskTopic

and a host of others. Instead of:


verbRule(Kick) ‘kick’ singleDobj : KickAction
verbPhrase = ‘kick/kicking (what)’

modify Thing
dobjFor(Kick) { preCond = [touchObj]
verify() {}
check() {}
action() { "You give <<gDobj.tN>> a kick. "; }

my new verb definitions look like this:

acT(Kick) ; vR(Kick) ‘kick’ singleDobj : KickAction vP = ‘kick/kicking (what)’ ;
mT dF(Kick) pTvca "You give <<gDobj.tN>> a kick. "; } } ;

Anyway… thanks for the input and happy game-writing!

This is a nifty idea, and would save a lot of typing. My only issue with it is that it makes the code less readable. Most IF programmers work alone, so that’s not a big issue unless you happen to want to revisit your source code five or ten years down the line.

The other thing that could happen, and it’s not likely, is that your macro would mangle something in the library files. If that happened the code wouldn’t compile, so I wouldn’t lose sleep over it.

Right… I know readability is a reason why macros usage can be looked down upon by programmers. I guess if I ever come back to the code years from now, I’ll just have to look in my header file to see all the #defines and remember what they mean. But for now I feel it’s worth it for helping me accomplish more in small windows of time…
Also yes, the compiler would be there to help if a macro got typed wrong, so far my macros are working just dandy for me…