-
Notifications
You must be signed in to change notification settings - Fork 1
MATT Action Threads
Actions can be organized into different action threads using Landings and the various logic functions.
Action threads are generally run one a time, but there are a few ways to have simultaneous ones running at once.
Examples below may get increasingly overly complicated in order to demonstrate various interactions.
When a tile is triggered, it starts at the top of the action list (unless auto-landings are involved, more on them later). This is the base action thread, and it will run all the actions in it until some kind of logic or event causes it branch or stop.
There is no limit to how many actions can be in an action thread.
By adding a Landing with Stop When Reached in Code
unchecked (the only checkbox available in the action configuration), you can create Action Subthreads. Actions in a subthread will be run as part of the preceding thread, as well as any other threads that might redirect to this specific landing.
The landing here named Kill Mode
is the start of the subthread.
With the module setting Show Landing Hightlight enabled, threads and subthreads will be color coded up to level 8, along with dotted-lines indicating subthreads and solid lines indicating new threads. Threads 9+ will be grey.
There is no limit to subthreads, beyond what you can work with in the UI.
The action thread completely stops when it encounters one of the following:
A Landing with Stop When Reached in Code
checked. Having this checked will add the ⬛ symbol to the end of the landing in the action list to signify that the landing is a stop. This will cause each Landing to just be the start of a brand new thread, instead of both a new thread and a subthread (more on new threads later).
A tile Activate/Deactivate stops running actions when deactivated; that includes when it deactivates itself. Any further actions in this action thread will have a red line through them to signify that they will not be run (this does not mean the actions cannot be run as part of another subthread).
Example below of a Deactivate that renders the following actions unreachable.
Example below of a Deactivate that does not necessarily render the following actions unreachable, as the actions are still part of the subthread and could be run from a different direction.
Please note, a tile deactivating itself via Use Tagger will not display the red strike-throughs.
Just like Deactivating itself, a Stop Remaining Actions will cause the action thread to cease, and any actions following it to not run. This action does not display a red line crossing out the following actions in the subthread however. These actions can still be from an alternate action thread.
Example below of a Stop Remaining Actions targeting the tile itself.
Trigger Tile can also cause a stop.
Some actions create a soft stop; the action flow will pause until some kind of decision or input is dealt with.
- Show Dialog soft stops until the dialog has been resolved.
- Request Roll & Request Contested Roll soft stop until the requests have been processed and the results are known.
As mentioned above, to have new action threads, use Landing with Stop When Reached in Code
checked; this will add the 🔳 to the end of the landing in the action display.
Action threads can be separated to keep specific actions limited to specific trigger events or specific logic results, while subthreads can be used to keep your action count minimized by utilizing the same action for multiple threads. Example below:
In this setup, we could duplicate the Active Effect that either adds or reduces frightened on crit fail/crit success restively, but we don't need to. Just uncheck Stop When Reached in Code
on the fail
and crit success
landings so that they're subthreads and will be reached by continuing down the action list.
Automatic Landings can be used to run specific actions based on some criteria; this includes allowing different sets of actions for different trigger events. These are effectively new starting points in the action list.
Example below of an enter
trigger that turns a light on, and an exit
trigger that turns the light off.
A triggered event automatically start at the first valid auto-landing, if one exists. If an auto-landing that meets any of the requirements does not exist, the action flow instead starts at the Basic Action Thread like usual. Example below:
The _enter
landing has Stop When Reached in Code
unchecked. This means that any triggered event that does not meet either the _enter
or _exit
method requirements starts at the top. Since this tile has the double-click
trigger as well, that means that anyone double-clicking the tile will start there and proceed to activate the light.
By checking Stop When Reached in Code
on the _enter
landing, its possible to set up an action flow that prevents the tile from being run except by any event that matches the used auto-landings. Example below:
The double-click trigger is still present, but any time the tile is triggered via this method, it will start at the top and hit the _enter
landing, automatically stopping it before anything actually runs. _enter
and _exit
start at their respective auto-landings still.
Some triggers can fulfill multiple auto-landings at once. A trigger always starts at the first valid auto-landing.
In the below example, the GM will never trigger the _exit
or _dblclick
actions, as well as never triggering the Basic Action Thread, as the _gm
landing is first and takes priority for the Gamemaster. Players will start at the Basic Action Thread when they trigger it via enter
, _exit
when they trigger it via exit
, and _dblclick
when they double-click
the tile.
Before covering the various ways to move around in the action flow, it will be prudent to know what not to do, and that is create an Infinite Loop.
- Infinite loops can crash Foundry.
- Infinite loops can cause performance issues.
- Infinite loops can cause data loss when editing embedded scene objects (editing tile action lists, among other things).
Landings and any of the various logic functions that redirect the action flow to landings can cause an infinite loop if the landing is placed before the jump/redirect to that landing. Jump to Landing does include a limit field, if there is a value there, it only loop the specified amount of times.
Whether the infinite loop crashes Foundry is dependent on the speed the infinite loop tries to resolve at; the example below will crash Foundry, because there's nothing to actually slow it down.
By adding actions/logic that can result in the loop eventually being broken, or simply by adding a Delay, you can run infinite loops without crashing Foundry. It is still not recommended; it can cause performance issues or cause data loss when editing embedded objects on scenes.
Below is an example of an infinite loop that just toggles a light on and off repeatedly.
Despite not having any jumps, or even more than the Basic Action Thread, a tile can still cause an infinite loop.
In the example below, the tile creates a token inside the tile, which triggers on a token being created within the tile, to create another token within the tile, and so on. This example would result in your Foundry data getting bloated up with token data and likely brick your world eventually,
Any combination of actions + their respective trigger can result in a self-triggering loop, although some might also be self-ending, such as Movement
trigger + the Move action (with Trigger Tiles While Moving
checked); this would most likely result in the token moving, triggering the tile, moving it again, and so on, until the token is finally moved outside the tile, ending the loop.
Some self triggering examples:
- An
On Token Create
trigger that Creates a Token within the tile. - An
On Rotate
trigger that Rotates a token within the tile. - An
On Elevation Change
trigger that change the Elevation of a token within the tile. - A pair of tiles with
Enter
triggers that Teleport (withTrigger Tiles at Destination
checked) will result in your token teleporting back and forth repeatedly. - The Trigger Tile action targeting the same tile.
There are a few methods you can use to stop infinite loops. Deleting a tile running an infinite loop will not stop it!
- Deactivate the tile; either by right-clicking and doing it manually, or with another tile using the Activate/Deactivate action.
- Another tile can use Stop All Remaining Actions targeting the looping tile; this may have some timing issues depending on where in the loop the stop is triggered.
- Restart Foundry. The loop will not be running once Foundry has been restarted.
- If you set up an infinite loop that instantly crashes Foundry upon loading in, you will need to boot Foundry up in safe mode and delete the tile. The example below is of a setup that will instantly crash your Foundry and require safe mode,
$\color{red}{\textsf{Do Not Do This!}}$
Jump
, Go to
, & Redirect
are the same thing and the terms can be used interchangeably. It just means "Now go to a Landing whose name matches". See Jump to Landing
below.
If a Jump to a landing occurs, but the landing doesn't exist, the action thread will simply stop, unless the auto-landing _failedlanding
is being used somewhere in the tile, in which case, it will instead jump to _failedlanding
.
Jump to Landing can be used to "jump" over sections of actions to continue their action thread.
In the example below, the Attack is never going to be ran, as the Jump to Landing immediately skips it by jumping to the End
landing.
This can cause an Infinite Loop if your landing being jumped to precedes the actual jump. Infinite loops will have a dedicated section later.
Take care not to create Infinite Loops with your Go To
fields.
The various Check actions can be used to create If/Then
action branching. For all of these, the Go To
fields can instead be intentionally left blank to trigger a hard stop if the logic is false.
Example below: The action thread ran will depending on whether the shift
key was being held when the tile triggered. If it wasn't being held, the triggering token is hurt for 1000 damage. If they were holding the shift
key, the triggering token is instead healed for 1000.
Checks can be used to create action threads that only will be run once, by adding some kind of action inside the thread that will disable it on future triggers.
The example below uses Check Entity Count to check whether any entities exist with a Tagger Tag (called "A Unique Tagger Tag" in the tile setup); once it confirms that none exist, it continues down the action thread, then adds the Tag to itself, preventing the enter
thread from continuing on future triggers, while not affecting the exit
thread at all.
This can be utilized in reverse, to create action threads that are gated off until their requirements have been met.
You can do this in various ways:
- The above method, Check Entity Count followed up by an Alter Tag that modifies the Tagged entity count.
- Check Variable followed up by a Set Active Tiles Variable that modifies the variable.
- Filter by Items followed up by either Add Item or Remove Item.
- Other ways exist, just get creative with it.
This adds a % based chance to continue the action thread, with the remaining percentage being either to completely end the action thread, or instead go to a landing matching the Go To
field.
Creates an If/Then
statement based on what trigger method was used. The chosen method continues down the action thread, while all other methods will stop, or redirect if a Go To
is entered.
This can also be used to create If/Then
action branching, but based on the permission levels of the triggering user. Example below:
Any users who trigger the tile will be sent to Player Enter
if they are only player level and will be hit with the Attack, while any Gamemaster level users will instead be sent to GM Enter
and be shown a dialog.
Not to be confused with Infinite Loops above.
Loop Through Entities takes whatever collection of objects you given it, and runs each of them one at a time through a specific action thread. This can used used to have a random outcome for each entity, instead of having the same random outcome for the entire collection.
Show Dialog will soft stop when the action is run, and depending on the type, can used to create an arbitrary number of branches.
The Confirm
& Custom
dialog types can be set up to allow a choice of buttons linked to Landings, that when clicked, will redirect the action flow to that particular landing & action thread.
The example below has four buttons, but only three matching landings. If a landing doesn't exist, nothing happens and the action thread stops.
This dialog type just soft stops until the dialog button is pressed, at which point it continues down the thread it was in.
Redirect Request Results takes the token collection from the preceeding Request Roll action, and sends each of them to the appropriate action thread whose landing is specified in the Redirect Request Results action.
The Continue
to landing will merge the Current Tokens
from each thread once they finish running and continue the action thread from there.
If you have module questions or concerns, please feel free to contact me on Discord. ironmonk88
This wiki is being maintained by crow_guard. If you have questions, want to see something added to the wiki, find a broken link or out-dated information, just message me and I'll fix it.
Or come over to Ironmonk's Discord channel. https://discord.gg/MStYmeRfn3
If you like Monk's mods and feel like being generous, stop by Monk's Patreon.
Not necessary but definitely appreciated.
If you find the wiki helpful and feel like being generous, stop by Crow's Ko-Fi.
Also not necessary but greatly appreciated.
Many of the assets shown in the tutorial images & GIFs are from https://www.forgotten-adventures.net/.
- Always HP
- Breaktime
- Enhanced Terrain Layer
- Monk's Active Tile Triggers
- Monk's Bloodsplats
- Monk's Chat Timer
- Monk's Combat Details
- Monk's Combat Marker
- Monk's Common Display
- Monk's Enhanced Journal
- Monk's Hotbar Expansion
- Monk's Little Details
- Monk's PF2E Encounter Aftermath
- Monk's Player Settings
- Monk's Scene Navigation
- Monk's Shops
- Monk's Sound Enhancements
- Monk's Tokenbar
- Monk's Wall Enhancement
- Multiple Document Selection