In my WIP I currently allow the player only to refer to things they have seen. E.g. a room with a door with a warning notice on it will be described as a room with a door. But when examining the door the player will notice the warning on it. And then the player can subsequently refer to it and e.g. examine it (which will automatically read it).
IMHO this allows me to keep room descriptions more succinct without information overloading the player and rewards exploration. But it would stop the player from taking shortcuts (e.g. if they played the game previously, they already know there is a warning notice on the door and might expect to be able to read it immediately without examining the door.)
I basically want to avoid scenarios like the following (taken from the Cragne Manor game where I did this as my very first move. None of the four objects matched by ALL here are mentioned in the initial room description. The rat and the vending machine do have a mention. But allowing for this kinda breaks things IMHO.)
>get all
brass winding key: That seems to belong to the rat.
plastic bubble: The vending machine isn't open.
golden eyepiece: The plastic bubble isn't open.
familiar gold wristwatch: Taken.
Iâve been dealing with similar design problems in my WIP. My general approach is to use dynamic vocabulary:
Objects get new vocabulary to reflect new player knowledge (âodd objectâ becomes âalien artifactâ or whatever)
In general (that is, except in cases where it would cause confusion) the old vocabulary remains valid in addition to whatever new vocabulary is added to it. So the tarnished bronze key becomes the mausoleum key, but the player can still >X BRONZE KEY. But if the photo of an unknown person becomes a photo of Bob, then that should probably have special logic for handling >X PHOTO OF UNKNOWN PERSON after the reveal
In cases where not-currently-valid vocabulary getting a generic failure response would sound odd, a handler is added for it. In TADS3 thereâs the Unthing, which basically catches vocabulary if and only if nothing currently in scope for the action would catch it otherwise. So an Unthing that matches âphoto of unknown personâ can always shadow the photoâs game object; when the ârealâ object also handles âphoto of unknown personâ then itâll always have priority over the Unthing; when the ârealâ object no longer has that vocabulary the Unthing will automagically start handling things instead (e.g. by prepending âThe person isnât unknown anymore; itâs Bob.â or something, possibly also remapping the action to apply to the ârealâ object)
Thatâs for things where it actually makes a gameplay difference and where the reveal would be a spoiler of some sort. Because if the player already knows something from a prior playthrough or a walkthrough or somethingâso? Having the game try to play dumb wonât make the player forget what theyâve learned via the side channel. Unless itâs actually sequence-breaking something in the game, my approach is to generally just not worry about it. If metagame knowledge is a sin (and Iâm not convinced that it generally is), then it is also its own punishment.
The scenario you want to avoid is all about the parser making smart choices in what it includes in âALLâ and perhaps which objects can be matched when input is ambiguous.
For any serious parser-driven IF design system, I would expect there to be ways to nudge or tell the parser how to do this, to get the effect youâre after.
In Inform 6, if an object has the concealed attribute, it wonât be included in ALL, and it will be disqualified if input is ambiguous and the other objects are not concealed, e.g. âOPEN SECRET DOORâ will open the door, but âOPEN DOORâ wonât ask the player whether they mean the front door or the secret door - instead it will open the front door.
adv3Lite has isHidden, hiddenIn, and SecretDoor, and it looks like Adv3 has Hidden and HiddenDoor, donât those work similarly to what Onno describes? Or do they prevent metagaming in order to skip discoveryâŚ? (I donât know TADS 3 intimately enough to say)
If you use TADS3 (both libraries) you can exploit to the hilt the .greveal macro, (this reminds me, time and again, that I still have to release The Portraitâs source codeâŚ) and I note that TADS3 has an easy mechanism for dynamically altering the vocabulary, but the mechanism differs between the two libraries.
I think the good thing about GET ALL is itâs an easy thing to test; just do it in each location and see if you like what happens or not VS the initial description.
Do you care if someone gets a certain thing thatâs present but not in the initial description? Youâll quickly found out how you feel when you try. With this method, youâre mostly checking for initial situations that meet your disapproval. After things have been moved or manipulated, the most common expectation is that they are then manipulable by GET ALL.
In the Cragne example, the bubble and eyepiece are in a transparent container, so theyâre reacting as expected. The key on the rat⌠I forget if that should have been hidden. But as you can see, doing GET ALL has told you what you think in each case.
Keeping objects in certain kinds of containers from showing in GET ALL is a general programming step you could take. But you can often tweak individual cases in simpler ways, and doing it in concert with the physicality of the world model is a good way to go (and usefully makes you dwell on how much you do or donât really want to police things, which can be part of the writing aesthetic as much as it is a mechanical programming issue). For instance, if you really donât want something to be accessible at all, donât have it in the world/room until the player has carried out the steps to reveal it.
Maybe my biggest challenge is in trying to present my story piecemeal using the parser as a medium, in order to avoid creating huge infodumps.
E.g. the kind of logic I am thinking of:
>x door
... describing the door, mentioning there is a warning plastered across it ...
>x warning / read warning
... (infodump) tells the PC why the door has been sealed and hints at how to unseal it ...
>do the proper thing as deducted from the warning
... door gets unsealed and the PC can enter ...
Now a player who previously played my game (yay! they want to play again! or maybe someone else told them what to do, or they consulted a walkthrough) might shortcut this all by skipping the first two steps, and just directly do what they need to do in the end. I can of course still force the infodump on the player by doing something like this instead (similar to automatically unlocking and opening doors when the PC tries to pass through locked doors):
>do the proper thing as written in the walkthrough
(implicit x door)
... describing the door, mentioning there is a warning plastered across it ...
(implicit x warning / read warning)
... (infodump) tells the PC why the door has been sealed and hints at how to unseal it ...
... door gets unsealed and the PC can enter ...
This way the player still can get the infodump but I find this can get a bit too much in one step. Hence I was wondering if using a slower reveal might be better. And to me the trick of only allowing the player to refer to seen things seemed the most natural.
A third approach to stay with the âstoryâ idea might be to do something like:
>do the proper thing as written in the walkthrough
... amazement or admiration expressed about the PC's insight by the NPCs in the location ...
... door gets unsealed and the PC can enter ...
Then the player will still be aware they âmissed outâ on something. Their loss I guess. But then I have to worry about sounding too âcampyâ.
----- cut here -----
Not really sequence breaking, more like players âmissing outâ. Maybe I should stop worrying about such things.
I know I can use concealed stuff or just swap in/out things as needed (I did this in my One King game of IFComp 2023) but that would be more work mechanics wise.
I fully agree. Once the player is aware of something they can manipulate I definitely do not want to stop them from doing so. I only used the Cragne Manor example to show that GET ALL might accidentally reveal things which was probably not intended by the original author.
Yeah I am doing this e.g. with an NPC:
... room description with an NPC described as a "stranger" ...
>talk to stranger
... (infodump) NPC and PC introduce themselves to each other (stranger -> Mike) ...
>give SOME_OBJECT to mike
... (Mike gives something in return) ...
Technically I allow the player to refer to the stranger as âstrangerâ and âmikeâ. Similar as above, I can force the infodumping when the player decides to skip the talking step because giving stuff to unknown shady people sounds a bit weird IMHO and messes up my idea of âgood behaviorâ.
An alternate approach suggested on Discord is to just stop the player dead in their tracks and let the NPC refuse interaction with the PC until properly introduced. And as for the door example, prevent the player from interacting with the door until the warning has been examined. I prefer to keep the game flow going if I can.
I believe Dialog also does what you want with the ($ is hidden) flag. Things that are hidden will never be referenced by the game until you explicitly ârevealâ them (by printing their name or unsetting the flag), or until the player interacts with them. This means they wonât be listed in room descriptions, wonât appear in disambiguation questions, wonât be included in ALL, wonât be inferred in an incomplete command, and so on, but will be acknowledged if the player references them unambiguously (like TAKE WARNING).
You can see this in Miss Gosling with the smoke detector, which is hidden until it goes off for the first time. But if youâre on a second playthrough, you can TAKE SMOKE DETECTOR any time youâre in the dining room, after which it will no longer be hidden.
Okay thank you all once again for providing cool little nuggets of knowledge on
TADS3
Inform 6
adv3Lite
Adv3
Dialog
I was posting in General Design Discussions in the hopes of getting some ideas for a consistent strategy in dealing with such scenarios independent of the framework/language used (I currently use Inform7 for parser stuff, but Dialog et al looks interesting too⌠maybe another time!).
I think I will stick to the forced infodumping for now (basically execute the missing steps, re-using my story mode mechanic to advance the story), then at least I have a consistent approach to catering for different play styles:
the experienced generic parser player new to the game doing the usual stuff like examining everything and taking everything in sight
the player new to parser games who will be guided at useful commands to try at every step (more than strictly speaking necessary probably, a bit like the tutorial mode as used by Emily Short in Bronze which I quite liked)
the player who played the game previously or uses a walkthrough provided by external means (e.g. DavidWâs excellent walkthroughs), only doing whatâs strictly necessary, with the game filling in the missing bits
the player relying on story mode to let the game play itself when they feel like it (but still allowing for experimentation or skipping âboringâ bits)
the experienced diehard parser player out to show me the errors of my ways and trying to lick everything in sight and do other nefarious things with my poor suffering game world
⌠maybe some other use cases which I did not think about âŚ
----- cut here -----
After some discussion on Discord (thx @pieartsy !)⌠I probably should have rephrased my original design question differently:
The most general question was about how to deal with player / PC knowledge. The playerâs knowledge might exceed the PC knowledge (previous playing experience, friends hinting at them what to do, walkthroughs, etc) and I was basically looking for a clean way to handle thisâŚ
[1] stopping it by basically not allowing the player to refer to unseen or unknown things
[2] adding the missing steps so the player knows what is going on
[3] describing in another way the player missed some lore
[4] stopping it directly by disallowing the action for other reasonsâŚ
[1] seemed cleanest and code wise easiest hence why I mentioned it originally.
For now Iâll try out [2] and let the beta tester gods tell me what they think of it.
Itâs a hard trick, but making someone read something isnât the same as making them want to. Despite there being a ton of text in Repeat the Ending, I decided not to make anyone read a whole lot of it outside of what is mechanically required to finish the game. Thereâs no way to sequence break in RTE. You have to do everything, but you donât have to examine things or read footnotes or the guide. Thereâs no copy protection in the feelie. Etc.
I want everyone to read everything, just like any writer would, of course, but we parser players tend to resent being pushed. So I let that go. I was glad in the end.
You got a very good point there. I do not really want to push things if that will be perceived as force feeding the player. Then I would definitely be better off just skipping things and not providing any explanation why things happen as they do (assuming the player is already aware since they probably skipped actions intentionally). Since I cannot know the players true intentions (did they skip by accident or on purpose) I can only assume the best and hope they do not get lost in the mysteryâŚ
The whole situation youâve been describing, Iâm dealing with in almost every room of my WIP. But my game has ultra-characterised PCs. In other words, if the PC hasnât grokked something, the player wonât be able to do anything with that something.
In practice, this means sometimes I can solve a problem by writing carefully, to describe something in a way that is satisfactory whether the player knows about it from before or not.
A lot of the time Iâm using knowledge flags. You know, if youâre following the prose, looking at A reveals the presence of B. Looking at B reveals the way to reveal C. But since the object is indeed in the room and was mentioned in its most basic form when they entered, Iâll let the player jump straight to C if they type the right thing. However, when I describe that moment, I tweak what prose is printed depending on what was done with A and B on the way (or if nothing was done) so it follows the characterâs thought process, and then I change what they see regarding A or B from that point on, etc. The ultimate goal is to maintain the flow of prose and sense from the characterâs POV.
So really what Iâm doing is of a version of your âadding the missing steps so the player knows what is going onâ. But I have the sort of benefit of the characters being a very hard filter on what is attemptable at any time in my game.
Yeah, sorry; the idea in my head was originally a response in two parts and then I guess I got distracted and ended up just talking about the second part. Probably because itâs the one Iâve been hammering on recently.
Anyway yeah, specifically for preventing ALL from slurping up things it maybe shouldnât the things you mention work (as well as a couple of others, like using nonObvious or dangerous in verify() results).
The other part of the problem, which is all I actually ended up talking about in my reply, is when you donât want to telegraph information via failure messages, noun resolution choices, and so on.
Yeah, I think Dialogâs âhiddenâ implementation is a good middle ground. Donât let the game ever mention it early, via ALL, disambiguation, and so on. But let the player mention it early if they want to.
Yeah. Iâm not sure how clear the point I was trying to make is (I clearly structured it confusingly in that I managed to forget to say anything about roughly half of it), but the thing Iâm talking about is when the parser might accidentally leak information âpassivelyâ.
Iâm not familiar with the example in the OP (and from context Iâm guessing itâs probably something like a key around the ratâs neck or something like that, but bear with me), but imagine we have a brass key sitting on the wainscoting and a rat that blocks the player if they attempt to do anything with it. Marking the object as hidden will prevent >TAKE ALL from implying >TAKE KEY if the player hasnât examined the wainscoting first. But you also donât want to refer to the key as the âratâs keyâ or whatever until the player has triggered whatever it is that grants them that knowledge.
Thatâs different from blocking, for example, >TAKE KEY FROM WAINSCOTING, which should probably be allowed even if the player hasnât examined the wainscoting this playthrough.