-
Notifications
You must be signed in to change notification settings - Fork 0
Trigger Application
The module exposes to the global the parent classes that must be inherited to populate the different parts of a trigger application.
They are available before any of the module's hooks are called (the module being flagged as library).
globalThis.triggerEngine = {
NodeEntry,
NodeField,
TriggerHook,
TriggerNode,
};To register a trigger application, you must use the following hook, which has the register function as its only argument.
Hooks.once("triggerEngine.registerApplication", (registerApplication) => {
registerApplication("<module-id>", "<application-id>", applicationData);
});The applicationData object contains the different parts that define your application.
type ApplicationData = {
convertors?: EntryConvertor[];
entries?: (typeof NodeEntry)[];
hooks?: (typeof TriggerHook)[];
nodes?: (typeof TriggerNode)[];
builtins?: (BuiltInOptions | true);
mode?: "setting" | "free";
setting?: ApplicationMenuOptions;
}Entry convertors are used to automatically convert one entry type to another. As long as a convertors exists for the specified types, the user will be able to drag a connection between them without needing to do anything else.
type EntryConvertor<TInput extends any = any, TOutput extends any = any> = {
output: string;
input: string;
convertToInput: (value: TOutput, userContext: UserPF2e) => Promise<TInput> | TInput;
};https://github.com/reonZ/trigger-engine/blob/master/src/engine/entry/entry.ts
Nodes are comprised of entries of 2 distinct types:
- The first are bridge entries which dictate the chain of execution of nodes
- The second are type entries, those entries represent data that is incoming to (inputs) or outgoing from (output) the node. Connected entries move data dynamically at runtime.
https://github.com/reonZ/trigger-engine/blob/master/src/engine/entry/field/field.ts
Some input entries can have a field allowing for static input directly at build time.
https://github.com/reonZ/trigger-engine/blob/master/src/engine/hooks/hook.ts
Trigger hooks are what runs in the background, they are what decides which trigger is executed and when.
Caution
The TriggerHook#_disabled must disable anything that is currently running for the hook and will be called
every time triggers are saved before calling the TriggerHook#_enabled. So make sure you handle it properly
to avoid hooks or wrappers to be registered multiple times.
Tip
Trigger hooks are not in play with free applications.
https://github.com/reonZ/trigger-engine/blob/master/src/engine/node/node.ts
Trigger nodes are the backbone of triggers, they define logic blocks and are executed in succession. The module allows for non-executable nodes (no bridge entries), in which case their output will be queried from the currently executed node instead.
The module comes bundled with a few of each parts already implemented, they can be added at will to any application,
either as a whole (by setting applicationData.builtins to true) or by specifying the ones needed in each section.
type BuiltInOptions = {
{
entries?: ("number" | "boolean" | "any" | "item" | "target" | "text" | "user")[];
convertors?: ("item-to-target" | "text-to-number" | "number-to-text" | "user-to-target" | "target-to-user")[];
hooks?: (
"create-combatant-hook" | "create-token-hook" | "delete-combatant-hook" | "delete-token-hook" |
"execute-hook" | "move-token-hook" | "region-hook" | "test-hook"
)[];
nodes?: (
"execute-event" | "await-confirm" | "console-log" | "create-message" | "delete-item" |
"execute-script" | "update-item" | "if-truthy" | "is-combatant" | "list-contains" |
"create-combatant-event" | "create-token-event" | "delete-combatant-event" | "delete-token-event" |
"move-token-event" | "region-event" | "test-event" | "extract-actor" | "extract-item" |
"actors-match" | "break-loop" | "compare-numbers" | "filter-targets" | "format-text" |
"resolve-formula" | "texts-match" | "split-boolean" | "split-number" | "split-text" |
"current-combatant" | "scene-targets" | "user-value"
)[];
}}Tip
Each section can be set to true to add all builtin entries for that particular section.
Important
A lot of those parts are interconnected, adding one node without adding the entries that it uses for instance, will break the node and render your trigger invalid.
If you want to make use of the blueprint menu without all the automation and settings associated to an application,
You must declare it as a free application instead of the default setting.
Just like in a lot of other places, the module allows you to localize your application, by default, it will always look for a specific predefined path but you can also override it by providing either a string or a localization key.
This section allow you to override the setting menu localization paths.
The default path for each property is as follow: <module-id>.<application-id>.setting.<property>
type ApplicationMenuOptions = {
hint?: string;
icon?: string;
label?: string;
name?: string;
};Tip
This does nothing for free applications.