So I’m working on a game that has a
Daemon, which advances an NPC antagonist every
n turns. It might not be every turn; the NPC has an occasional delay that he must wait before being allowed to take an action.
The problem is: I don’t what this NPC to be iterated on after every single player turn. In particular, I don’t want this to happen during system actions (save, load, other settings), “free” actions (looking around the room as a refresher), etc. So far, I have this completely implemented.
However, there’s one thing missing that I need some clarification on: If the player attempts an action, but it gets an
illogical response of any kind, or outright is not a recognized command, how do I test for this to make the player not spend a turn?
The NPC antagonist should only be spending turns on the assumption that the player knows what they’re doing. If the player is struggling to come up with a logical action, then I don’t want to punish them for it. An
illogical response should be treated as though no time has passed, and the parser is just informing the player as to why that wouldn’t work. I don’t want it to be treated as the player spending time attempting and failing to perform the action.
So, more specifically:
- Will a
Daemon iterate after an unrecognized command or
- If it will, then how do I check for evidence these action responses? Because I will need to make the
Daemon skip iteration for that turn.
This will also be useful, as I have some “lingering senses” that I don’t want to vanish in such scenarios either. It would be a shame to miss an opportunity because of a parser error.
System actions and failed commands should not increment
libGlobal.totalTurns (which is the turn count displayed in the status line). Your daemon could track the last turn number it ran and only run again if it’s different (indicating a successful player action was executed in the interim).
(Another way to think of it: TADS treats the turn counter as an indication that the player has done something in the game world, rather than the number of commands it has processed. This distinction is important for extensions that represent turn counts as wall clock time.)
However (this is off the top of my head), I don’t believe daemons execute after system actions or failed turns. My recollection is that both situations result in an exception being thrown which prevents post-command actions to occur (the turn counter is incremented, daemons are run, etc.)
Maybe the best thing to do is write your
Daemon and see if it executes after system actions / failed commands. If it does, you could then track turn counts and only execute when it increments.
Excellent! Thank you so much!!
In adv3Lite system actions do not increment the turn counter or carry out any other turn processing, such as executing Daemons, but actions that fail at the verify stage do. I’m reluctant to change the default behaviour here, since this is at it’s always been and no one else has seemed bothered by it, and changing the default behaviour could affect the backward compatibility of existing game code. So for version 1.61 I’m adding a new property to the Action class, failedActionCountsAsTurn that game code can override to nil to abort any further processing of an action that fails at the verify stage (so that the turn counter won’t be incremented, daemons won’t execute, and so on).
This change has been uploaded to the adv3Lite GitHub repo.
Yeah, changing a default behavior would be really bad; I definitely agree with you there!
Also, thank you for the new Action property!! This will absolutely come in handy!