Skip to content

Automations

Jared Quinn edited this page Jul 9, 2026 · 4 revisions

The Scoreboard Engine includes a native, frame-accurate automation processor. This system allows you to build completely sport-agnostic configuration profiles by triggering multiple actions based on value-change boundaries, numeric edges, and directional state transitions.

Core Logic & Edge Detection

Unlike standard condition parsers that fire continuously while a condition remains true, this engine implements True Edge Detection paired with Value-Change Memory.

Startup Immunity: Triggers will never fire on the very first loop frame at engine boot if the state initialized directly on the target value. It requires an active transition.

One-Shot Execution: Once an edge boundary is crossed, the actions execute exactly once. The trigger disarms until the edge condition resets or transitions back.

Transaction Grouping: Multiple sequential mutations targeting the same widget are executed as a single unified frame transaction. The engine forces a manual recalculation pass right after, ensuring that inter-dependent updates (like set_min and set_max) don't overwrite each other's formatting outputs.

Configuration XML Schema

Automations are declared inside your master configuration profiles under the root <ScoreboardConfig> block using <trigger> nodes.

<trigger>
    <condition>
        <widget_id>[target_widget_id_or_property]</widget_id>
        <operator>[== | >= | <= | ++ | --]</operator>
        <value>[numeric_target_value]</value>
    </condition>
    <actions>
        <action>
            <target_id>[target_widget_id]</target_id>
            <action>[action_method]</action>
            <value>[parameter_payload]</value>
        </action>
    </actions>
</trigger>

Condition Operators

Conditions evaluate properties exported via the engine's flat state layout (e.g., match_period_index). The following condition operators are supported:

Operator Type Evaluation Rule Use Case Example
== Scalar Equality True if the current property matches the value within 0.01 tolerance. Tracking clock boundaries or exact scores.
>= Greater Than / Equal True if current value is above or equal to target. Triggering events when values pass ceilings.
<= Less Than / Equal True if current value is below or equal to floor. Countdown timers hitting zero boundaries.
++ Directional Increment True ONLY if the current value matches the target value AND the value stepped UP from the previous frame. Advancing forwards through periods/halves.
-- Directional Decrement True ONLY if the current value matches the target value AND the value stepped DOWN from the previous frame. Backwards operator changes or undo routines.

Values

Any value available in the flattened widgets output is available for use for matching a condition; you can see all of the attributes by hitting http://localhost:3000/widgets/flat

Supported Action Methods Reference

Timer Widgets (Timer)

  • start : Boots the clock into a running state.
  • stop : Pauses timeline execution increments.
  • toggle : Flips running state natively.
  • reset : Hard resets seconds, formats, and accumulated tracking times to boot parameters.
  • set_min / set_max : Dynamically re-allocates baseline floors or ceiling walls (accepts values like 2700 or time string slices like "45:00").
  • set / set_time : Force shifts the running clock value immediately to a target frame.
  • set_initial : Updates the fallback default reset value.

Counter Widgets (Counter)

  • increment / decrement : Offsets active totals by the parameter value (defaults to 1).
  • set : Instantly overrides active registers to specific integers.
  • reset : Reset to initial_value

Real-World Production Examples

Example: Forward Match Period Sequencing

This pattern relies on the ++ directional operator. It ensures that when an operator clicks the dashboard interface to advance from Halftime to the 2nd Half, the clock automatically resets its bounds and positions itself perfectly—but it will not fire if they roll backwards to fix a mistake.

<trigger>
    <!-- Fires ONLY when explicitly stepping UP from Index 1 to Index 2 -->
    <condition>
        <widget_id>match_period_index</widget_id>
        <operator>++</operator>
        <value>2.0</value>
    </condition>
    <actions>
        <!-- 1. Move baseline to 45 mins -->
        <action>
            <target_id>match_clock</target_id>
            <action>set_min</action>
            <value>2700</value>
        </action>
        <!-- 2. Shift ceiling wall to 90 mins -->
        <action>
            <target_id>match_clock</target_id>
            <action>set_max</action>
            <value>5400</value>
        </action>
        <!-- 3. Snap current time index forward -->
        <action>
            <target_id>match_clock</target_id>
            <action>set_time</action>
            <value>2700</value>
        </action>
        <!-- 4. Guarantee clock is held stopped for kickoff -->
        <action>
            <target_id>match_clock</target_id>
            <action>stop</action>
        </action>
    </actions>
</trigger>

Clone this wiki locally