The HistoryBook is an especially useful feature; it's a record of every Event that has taken place in the play of your storyworld. Think of it as "the history of the storyworld so far." You can look up Events in the HistoryBook to recall exactly what happened. Here are the Operators you can use:
EventHappened
This is a boolean Operator; it returns a simple yes-or-no answer to the question "Did the Event fitting this description ever take place?" It takes a single argument, another boolean, that provides the description in proper form. Here's an example:
This means, Has any Event ever happened in which the Subject was the ReactingActor and the Verb was "punch?" You may be a little confused by the use of "CandidateEvent." Remember, when we ask the Engine to look for "any Event," we are telling it to look at each and every Event to make a decision; that decision has to consider each Event individually. "CandidateEvent" is that "each Event individually." So we could expand the terse description above into the following more specific version:
Engine, I want you to examine each and every Event in the whole HistoryBook. When you look at each Event, we'll call that Event you're looking at "CandidateEvent." Now, I want you to get the Subject and Verb of that CandidateEvent. If the Subject of that CandidateEvent is the ReactingActor, and the Verb is "punch," then return "true."
We also provide a handy little helper Operator: MainClauseIs. We learned in practice that many of our EventHappened Operators ended up looking like this:
Over and over again, we found ourselves specifying the Subject, Verb, and DirObject of the PastEvent. This became rather tiresome, so we came up with this handy-dandy little shortcut:
This means exactly the same thing as the previous version, but it's a lot easier to use.
Why would you use EventHappened? Normally you use it to check whether some Event has taken place that would be required for a later choice to be made. For example, suppose that you don't want the Prince to be able to rescue the Princess until after the Dragon has been slain? Then you might have an Inclination Script for the Option rescue looking something like this:
PickUpperIf
EventHappened
MainClauseIs
Prince
slay
Dragon
Maxi
Mini
LookupEvent
This is what you use to answer questions such as "Is this the same Prop that the Subject used to hit the ReactingActor previously?" Here is how it is typically used:
AreSameProp
This4Prop
Past4Prop of:
LookupEvent of:
AND
MainClauseIs
ThisSubject
hit with
ReactingActor
AreSameProp
This4Prop
Past4Prop of:
CandidateEvent
LookupEvent is found under the History Operators menu.
Here's a fine point about LookupEvent: it searches backwards from the present and stops at the first Event it finds that meets the specifications. This means that it will find the most recent Event that meets the specs.
CountEvents
This Operator answers the question "How many times has this happened before?" For example, you might want to have Charlie Brown ask himself, "How many times has Lucy yanked the football away when I ran to kick it?" Presumably this would be used in a Script like this:
Offer to hold football: CharlieBrown: refuse to kick football: Inclination
Number2BNumber of:
quotient of:
CountEvents of:
MainClauseIs
Lucy
yank football
Charlie Brown
100
There are several important things to notice about this script.
First, note that the entire clause starts off with the Operator Number2BNumber. You might ask why we need this. If you'll recall from our tutorial on Attributes, all traits are BNumbers, and range from -1.0 to +1.0. Again, we do this to be sure we are always comparing apples to apples, and making it easier to keep our scripts contained within a similar range of values. But a storyworld's Events don't range between -1 and +1. They range from 0 on up to 100, 1,000 or more. To use CountEvents (or any regular number) in a script, we must first convert it to a BNumber.
Second, note that we divide CountEvents by 100, using the Operator quotient. This is basically saying that Charlie Brown is in fact capable of learning from his mistakes, albeit rather slowly. If we wanted to make him a quicker learner, we'd do this by making the 100 a smaller number—say, 10—or even eliminate the quotient altogether, and just have Number2BNumber of: CountEvents. Charlie Brown's inclination to refuse to kick the football would increase a good deal more rapidly in that case.
"Causal" tests
There is also a corresponding set of Operators that use a slightly different way of searching the HistoryBook. All the Operators above start at the current Event and work backwards in time. "Causal" tests (CausalEventHappened, LookupCausalEvent, CountCausalEvents) only follow the chain of causality backwards. These tests ignore unrelated Events and look only at those Events that are directly in the chain of causality leading to the Event being reacted to. This is a more precisely targeted test that is necessary when you want to make sure that you're not fooled by an Event that meets your specs but is, by some strange chance, unrelated to the current Event.
ElapsedTimeSince
This is another rarely-used Operator; you use it to find out how much time has passed since an Event took place. Example:
The ReactingActor's Inclination to accept the donut is proportional to how much time has passed since he last ate a donut. (Notice that when counting time, as with counting Events, we have to convert the regular number to a BNumber in order to use it in the script.)
IHaventDoneThisBefore
This is a particularly useful Operator that is meant to obviate repetitious behavior. What's neat about it is that it's so smart. You can bury it inside a WordSocket and it will look for matches right up to and including that WordSocket, but it will ignore anything beyond it. In other words, you don't have to specify the contents of the WordSockets; it automatically fills them in for you. That's probably confusing, so here's an example. Suppose that you are having a conversation with another Actor about a third party. You've been comparing notes about the various Attributes of that third party. You don't want to ask about an Attribute that you've previously asked about. You could do this with LookUpCausalEvent, but there's an easier way:
agree to talk: DirObject: gossip about: ActorAttribute: Acceptable
IHaventDoneThisBefore
That's all it takes! This Operator can only be used within an Option, so you will notice that it does not appear in the History menu under, for instance, AssumeRoleIf or Emotional Reaction scripts.
IHaventDoneThisSince
This is a variation on IHaventDoneThisBefore, but it adds a backwards time limit. It means "I haven't done this in the last X moments." As with IHaventDoneThisBefore, this Operator can only be used within an Option.