mimoLive® - User Manual

Automation

Table of Contents

Streamline Your Production with mimoLive’s Automation Layer

You are currently viewing a placeholder content from YouTube. To access the actual content, click the button below. Please note that doing so will share data with third-party providers.

More Information

The mimoLive Automation Layer was originally developed as a proof of concept but has since proven to be an incredibly useful tool for users. This layer can be used to automate the switching on and off of layers in a specific sequence or at predetermined times, transport information from one layer to another, start and stop Output Destinations, and so much more!

It can be especially helpful for creating complex productions with multiple layers and inputs, as it eliminates the need for manual switching and timing. With this layer, users can focus on creating engaging content while the software handles the timing and sequencing of their production. Now, in version 2 of this layer, we have extended the commands to bring automation in mimoLive to a whole new level.

Example: Automation Layer

Automation

Automation Scripts in mimoLive Do Not Run in Real Time

Please note that the timing of automation scripts in mimoLive may not be accurate due to the asynchronous nature of HTTP requests called by the video rendering engine. These scripts rely on HTTP requests to the API and the length of these requests cannot be accurately determined, resulting in potential timing discrepancies. Please keep this in mind when using automation scripts in your production workflow.

Prerequisite

In order to make this layer work you need to switch on the HTTP Server in mimoLive to enable the Remote Control API. Go to mimoLive -> Preferences -> Remote Controls: Check the “Allow Remote Control Access” option. (Currently Automation layer in mimoLive only works without a password)

6102d04e 4eb3 4600 b410 0d2b2aef0767

Set up the Automation Layer

There are two options on how the layer should behave after switched live:

OptionBehaving
Switch layer off automaticallyFor this option there is only one script available. Once this script has been processed the layer will switch itself of. This option can be used if a sequence should be performed once.
Switch layer off manually (e.g. by operator)In this case there are three scripts available. When the layer is switch live the “On Live” script will be processed. Once this is done the “While Live” script gets processed in an endless loop. Once the layer gets switched off the “Turned Off” script gets processed.
If you don’t have a need for a certain phase you can leave the associated script empty.

Source Code Comments

To help you remember the function of your script we recommend to make use of comments in your script:

// First sleep for 5 seconds...
sleep(5)

// ...then start the stopwatch layer:
layerOn("7C4665C4-0E17-4F63-BCFF-B59D68D75956")

Comments needs to be in a separate line.

Scripting Commands

The scripting language is proprietary and includes several commands. Those commands are listed in a cheat sheet in the layers preview on the right. Because the list might be a bit small to read, you can expand the preview by using the button located above and to the right of the preview area.

layerOn(<API Layer ID as String Expression>)

This command lets you switch on a layer or a layer variant.

// switching on a layer by its id
layerOn("4E38A868-DCB5-4E9C-AC75-231764229BFA")

// switching on a layer variant by its id
layerOn("4E38A868-DCB5-4E9C-AC75-231764229BFA/variants/5F18C566-F59F-45B4-8D40-27EF289D47B1")

// switching on a layer by its long API Endpoint URL
layerOn("/api/v1/documents/863743527/layers/4E38A868-DCB5-4E9C-AC75-231764229BFA")

// switching on a layer with a defined variable
setVariable($myLayerID, "4E38A868-DCB5-4E9C-AC75-231764229BFA")
layerOn($myLayerID)

layerOff(<API Layer ID as String Expression>)

This command lets you switch off a layer or a layer variant.

// switching off a layer by its id
layerOff("4E38A868-DCB5-4E9C-AC75-231764229BFA")

// switching off a layer variant by its id
layerOff("4E38A868-DCB5-4E9C-AC75-231764229BFA/variants/5F18C566-F59F-45B4-8D40-27EF289D47B1")

// switching off a layer by its long API Endpoint URL
layerOff("/api/v1/documents/863743527/layers/4E38A868-DCB5-4E9C-AC75-231764229BFA")

// switching off a layer with a defined variable
setVariable($myLayerID, "4E38A868-DCB5-4E9C-AC75-231764229BFA")
layerOff($myLayerID)

layerSetRecall(<API Layer Set ID as String Expression>)

This command can be used to trigger the recall for a certain Layer Set.

// recall a Layer Set by its id
layerSetRecall("E6950B7A-7457-44C5-81F7-972D9B04DBC3")

// recall a Layer Set by its long API Endpoint URL
layerSetRecall("/api/v1/documents/863743527/layer-sets/E6950B7A-7457-44C5-81F7-972D9B04DBC3")

// recall a Layer Set with a defined variable
setVariable($myLayerSetID, "E6950B7A-7457-44C5-81F7-972D9B04DBC3")
layerSetRecall($myLayerSetID)

outputOn(<API Output Destination ID as String Expression>)

Use this command to turn on an output destination.

// start an Output Destination by its id
outputOn("1953186E-4176-4849-A8ED-5B47EE1627BD")

// start an Output Destination by its long API Endpoint URL
outputOn("/api/v1/documents/1677022440/output-destinations/1953186E-4176-4849-A8ED-5B47EE1627BD")

// start an Output Destination with a defined variable
setVariable($myOutputDestinationtID, "1953186E-4176-4849-A8ED-5B47EE1627BD")
outputOn($myOutputDestinationtID)

outputOff(<API Output Destination ID as String Expression>)

Use this command to turn off an output destination.

// stop an Output Destination by its id
outputOff("1953186E-4176-4849-A8ED-5B47EE1627BD")

// stop an Output Destination by its long API Endpoint URL
outputOff("/api/v1/documents/1677022440/output-destinations/1953186E-4176-4849-A8ED-5B47EE1627BD")

// stop an Output Destination with a defined variable
setVariable($myOutputDestinationtID, "1953186E-4176-4849-A8ED-5B47EE1627BD")
outputOff($myOutputDestinationtID)

getLayerData($resultVariableName, <API Layer ID as String Expression>, <Key Path as String Expression>)

This command combines multiple commands in one script step: It retrieves the layer information from the HTTP server and stores a specific data field from the JSON response into a variable. You need the exact path to the value you want to read. For the input parameter of layers, this path usually starts with ‘data.attributes.input-values’.

// set up useful variables
setVariable($myScoreboardLayerID, "36FA76B4-11FE-4879-8DE1-307222512712")
setVariable($pathToHomeScore, "data.attributes.input-values.tvGroup_Control__Score_Home")

// read the score for the home team from the Basketball layer
getLayerData($currentHomeScore, $myScoreboardLayerID, $pathToHomeScore)

// The variable $currentHomeScore now contains the Home Score input value of the Basketball Score layer

getObjectIDByName($resultVariableName, <Object Type as String Expression>, <Name of Object as String Expression>)

This command obtains the API Endpoint for a specific mimoLive object by its display name. Please be aware that the display name can easily be changed by the mimoLive operator in the mimoLive user interface, and which in turn will break the automation script if it can’t find the specific object anymore. On the other hand, this command can be used to find API endpoints programmatically without the need to hardcode the API Endpoints in the script.

Valid options for <Object Type> are: “source”, “layer”, “layer-set”, “output-destination”

// Get the API Endpoint for the Basketball Score layer
getObjectIDByName($myBasketballScoreLayerID, "layer", "My Basketball Score Keeper")

// switch this layer on
layerOn($myBasketballScoreLayerID)
Screenshot 2024 06 11 at 15.20.42

sleep(<Seconds> as number)

The sleep() command pauses the execution of the script for the given time interval, expressed in seconds.

// pause the script execution for 12 seconds
sleep(12)

// pause the script execution for 35.6 seconds
sleep(35.6)

// pause the script execution for a time interval specified by a variable
setVariable($mySleepInterval, 17)
sleep($mySleepInterval)

sleepUntil(<Time as String Expression>)

The sleepUntil() command lets the script pause until the specified time is reached. If the time has already passed, the script waits until the next day. The format for the time is HH:MM or HH:MM:SS in a 24-hour period.

// sleep until 5:15pm
sleepUntil("17:15:00")

// sleep until 9:12am
sleepUntil("9:12")

// sleep until a time specified by a variable
setVariable($myWakeUpTime, "9:41")
sleepUntil($myWakeUpTime)

sleepOnTheMinute(<Minute as Number Expression>)

This script command pauses the script until the next ‘on the minute’ fraction of an hour is reached.

// go on every 20 minutes: on the hour, 20 and 40 minutes past the hour:
sleepOnTheMinute(20)

// go on "on the hour"
sleepOnTheMinute(60)

// go on every 10 minutes past the hour (specified by a variable)
setVariable($myWakeUpMinute, 10)
sleepOnTheMinute($myWakeUpMinute)

setVariable($variableName, <value>)

To define a local variable, use the setVariable command. You need to specify a variable name (starting with a $) and the value this variable should hold. The value can be a number, text (enclosed in quotation marks), or the boolean values true and false.

setVariable($myText, "This is a text")
setVariable($myNumber, 15.73)
setVariable($myBoolValue, false)

setGlobal($variableName, <value>)

A global variable can be used both in the current layer and in any Automation layers above it. This functionality is particularly useful for sharing the same information across multiple Automation layers, such as the API Endpoints of a certain layer. For the value of the variable, the same rules apply as those for the setVariable command.

Please note that global variables are accessible to other Automation layers as long as the originating layer is live. This arrangement allows you to switch global variables by activating a different layer with distinct global variable definitions. Best practice in this scenario is to set the ‘Switch Layer Off’ option of the Automation layer to ‘Manually’ and define the globals in the ‘On Live’ script.

setGlobal($myGlobalText, "This is a text")
setGlobal($myGlobalNumber, 15.73)
setGlobal($myGlobalBoolValue, false)

concat($resultVariableName, <String Expression>)

This script command concatenates strings together and stores the result as a string.

// define some variables
setVariable($myVariableA, "This is")
setVariable($myVariableB, "text.")

// concatenate those variables and store the result into a new one
concat($myResultVariable, $myVariableA + " a " + $myVariableB)

// The variable $myResultVariable contains "This is a text.".

math($resultVariableName, <Number Expression>)

This command performs simple math calculations, including addition (+), subtraction (-), multiplication (*), and division (/). Please note that calculations are performed in the order they appear and DO NOT follow the PEMDAS/BODMAS rule.

// define some variables
setVariable($myVariableA, 3)
setVariable($myVariableB, 5)

// perform the calculation
math($myResult, $myVariableA + 2 * $myVariableB)

// The result in $myResult is 25 (!) and not 13

if(<Number Expression 1>, <Comparator as String>, <Number Expression 2>) [else] endif

This if statement compares two numerical expressions using a specified comparator. If the comparison is true, then the following command(s) are executed. Otherwise, subsequent commands are skipped until an else or endif is reached.

Valid comparators are:

“==”equals
“!=”not equals
“>”greater than
“<“less than
“>=”greater or equal than
“<=”less or qual than
// define a variable
setVariable($myVariable, 3)

// test if the variable is bigger than 10
if($myVariable, ">", 10)
   setVariable($text, "is bigger than 10")
else
   setVariable($text, "is less or equal 10")
endif

// The result in $text is "is less or equal 10"

ifString(<String Expression 1>, <Comparator as String>, <String Expression 2>) [else] endif

This ifString statement compares two string expressions using a specified comparator. The comparison is based on the ASCII character code of each letter in the strings. If the comparison is true, then the following commands are executed. Otherwise, subsequent commands are skipped until an else or endif is reached.

For valid comparators see the if-command.

// define a variable
setVariable($myVariable, "mimoLive")

// test if the variable is "mimoLive"
if($myVariable, "==", "mimoLive")
   setVariable($text, "yes")
else
   setVariable($text, "no")
endif

// The result in $text is "yes"

ifLayerIsOn(<API Layer ID as String Expression>) – ifLayerIsOff(<API Layer ID as String Expression>) [else] endif

These if statements test whether a certain layer is currently live or not. If the specified condition is met (the layer is on or off), then the following commands are processed. Otherwise, the subsequent commands are skipped until an else or endif is reached.

setVariable($myLayerA, "D6A326CA-72E6-45E5-836D-9795F8F534F4")
setVariable($myLayerB, "8C58DEA7-CCBE-44CB-A60F-97C5BD456C68")

ifLayerIsOn($myLayerA)
   // the layer is live, switch it off
   layerOff($myLayerA)
else
   // the layer is currently off, switch it on
   layerOn($myLayerA)
endif

ifLayerIsOff($myLayerB)
   // the layer is currently off, switch it on
   layerOn($myLayerB)
endif

ifLayerSetIsActive(<API Layer ID as String Expression>) – ifLayerSetIsInactive(<API Layer ID as String Expression>) [else] endif

These if statements test whether a certain Layer Set is currently live or not. If so, the following commands are processed. Otherwise, the subsequent commands are skipped until an else or endif is reached.

setVariable($myLayerSetA, "CEF07AFA-B552-40F8-821C-CF424EB93500")
setVariable($myLayerSetB, "E4B15B8B-EE34-4CCE-BDE7-58120A65E83A")
setVariable($myLayer, "8C58DEA7-CCBE-44CB-A60F-97C5BD456C68")


ifLayerSetIsActive($myLayerSetA)
   // the layer set A is active, switch layer on
   layerOn($myLayer)
else
   // the layer set A is currently inactive, switch the layer off
   layerOff($myLayer)
endif

ifLayerSetIsInactive($myLayerSetB)
   // the layer set B is currently inactive, switch the layer off
   layerOn($myLayer)
endif

ifLayerData(<API Layer ID as String Expression>, <Key Path as String Expression>, <Comparator as String Expression>, <Value as Number Expression>) [else] endif

This complex command allows you to test any parameter of a layer that the HTTP API provides. You need to specify a layer by its API ID, the key path within the JSON data returned by the HTTP API, a comparator (as a string in quotation marks, e.g., “=="), and a value.

Valid comparator values are:

“==”equals
“!=”not equals
“>”greater than
“<“less than
“>=”greater or equal than
“<=”less or qual than
// Example: Testing if the audio volume is turned up on a layer

setVariable($myLayerA, "D6A326CA-72E6-45E5-836D-9795F8F534F4")
setVariable($myLayerB, "8C58DEA7-CCBE-44CB-A60F-97C5BD456C68")

ifLayerData($myLayerA,"data.attributes.volume",">",0.5)
   // The audio volume is bigger than 0.5 so turn layer B on
   layerOn($myLayerB)
else
   // The volume is lower than 0.5, lets turn layer B off
   layerOff($myLayerB)
endif

loop([<Iterations as Number Expression>]) [break] endloop

The loop command allows you to execute code multiple times. If you do not specify the number of iterations, the loop will run indefinitely. The break command lets you exit the loop at any time. endloop is necessary to mark the end of the command block that should be looped.

setVariable($myLayerA, "D6A326CA-72E6-45E5-836D-9795F8F534F4")

// blink layer A 4 times
loop(4)
   layerOn(setVariable(myLayerA)
   sleep(1)
   layerOff(setVariable(myLayerA)
   sleep(1)
endloop

// wait for volume of layer A will be bigger than 0.5
loop()
   ifLayerData($myLayerA,"data.attributes.volume",">",0.5)
      // The audio volume is bigger than 0.5 exit the loop now
      break
   endif
   sleep(1)
endloop

httpRequest(<URL as String Expression>)

The httpRequest() command triggers the given URL. This offers a lot of flexibility in how you can use this script command. In mimoLive, it can even trigger actions in other documents or remote scripts. For details on mimoLiveHTTP API commands, please consult the HTTP API documentation to explore all possible API calls.

// switch on a layer
httpRequest("http://127.0.0.1:8989/api/v1/documents/188462841/layers/BA868701-8131-49CB-8EDD-8C7E6E7CD60B/setLive")

httpRequestJSON($resultVariableName, <URL as String Expression>)

This command reads the response of the HTTP call as JSON and stores the data in the specified result variable. After this, you can access the data via the getJSONData() command.

getJSONData($resultVariableName, $jsonDataVariable, <Key Path as String Expression>)

This command retrieves a specific data value from a JSON structure stored in a variable. You need to specify the variable containing the JSON data ($jsonDataVariable), the path to the data within the JSON structure (<Key Path as String Expression>), and the variable where the result should be stored ($resultVariableName). This allows precise extraction of data for further processing or use in your script.

// get all data of a layer
httpRequestJSON($myLayerData, "http://127.0.0.1:8989/api/v1/documents/188462841/layers/BA868701-8131-49CB-8EDD-8C7E6E7CD60B")

// get the value of the volume dial
getJSONData($volumenDial, $myLayerData, "data.attributes.volume")

// Now, the $volumenDial variable will hold a value between 0 and 1.

> Debugger Break Point

When the script debugger is enabled and the debugging mode is set to ‘Continuously,’ the execution of the script will pause at this marker and wait until the mimoLive operator clicks the ‘Next Step’ button. Please see ‘Best Practices – Debugging Scripts’ for more information about the debugging possibilities.

Data Types

API Endpoints

The parameter should be an API Endpoint for a Layer, a Layer Variant, a Layer Set, a Source or an Output Destination. You can obtain these API Endpoints by right-clicking on the object in the mimoLive document. A context menu should appear with a ‘Copy API Endpoint to Clipboard’ menu item.

This action will copy the API Endpoint for this object to the clipboard. If you paste it elsewhere, it will look something like this:

/api/v1/documents/863743527/layers/D6A326CA-72E6-45E5-836D-9795F8F534F4

/api/v1/documents/863743527/layers/68F63C8F-2376-4CA3-9764-CC17CBFC5F8D/variants/3FF72CC3-AF80-4252-A879-F8AFD68DB922

/api/v1/documents/863743527/layer-sets/E6950B7A-7457-44C5-81F7-972D9B04DBC3

For layer related commands you may reduce the API Endpoints to the important part only by removing the prefix “/api/v1/documents/<documentID>/layers/” . This will make your script shorter as shown here:

// switching on a layer:
layerOn("/api/v1/documents/863743527/layers/D6A326CA-72E6-45E5-836D-9795F8F534F4")
// OR
layerOn("D6A326CA-72E6-45E5-836D-9795F8F534F4")

// switching on a variant:
layerOn("/api/v1/documents/863743527/layers/68F63C8F-2376-4CA3-9764-CC17CBFC5F8D/variants/3FF72CC3-AF80-4252-A879-F8AFD68DB922")
// OR
layerOn("68F63C8F-2376-4CA3-9764-CC17CBFC5F8D/variants/3FF72CC3-AF80-4252-A879-F8AFD68DB922")

 

Best Practice

API Endpoints

How to get API Endpoints

  • By right clicking on the layer and selecting “Copy API Endpoint”
  • by using the getAPIEndpoint() command (see documentation)

Adressing API Endpoints

You can either use the complete API endpoint or remove the “/api/v1/documents/<documentID>/” part to make sure your script also works when copied to another document. However the document ID is important if you want to address a API point in a different mimoLive document.

Debugging Scripts

There is a script debugger build in into the Automation layer. You can switch the layer into Debugging Mode by setting the layer parameter “Debug” to on.

TBD.

Scripting Ideas

Run an ad every 10 minutes

In combination with a “PIP Window” layer an a “Media Playlist source” containing multiple short advertising movie clips you can playback one advertising every 10 minutes. Make sure to uncheck the “Non-Stop” option in the Media Playlist source. This way each time the PIP Window gets set to live it will playback one ad from the Playlist source and switches itself off. After 10 minutes the next ad will be played back.

Run a stinger before you switch to a certain layer

You need to prepare a short stinger video that will have an In-transition until it covers all the screen (e.g. after 1 sec). After 1 second you switch live that layer you want to reveal. Place this layer below the layer playing back the stinger video. Now that the stinger video is covering the screen the switching of the layer below can’t be seen. The stinger video should go on with revealing the layer below. Please make sure that the stinger video is rendered in ProRes4444 video codec so that it carries the transparency necessary for the transition with it.

Create a complex show opener

Because you can switch on and off layers one after another over a longer period of time you can have multiple Text or Annotation layers, Placer layer showing graphics or even lower thirds that fills the screen to make you own animated show opener. Get creative!

Trigger a remote HTTP URL by a tap on the Remote Control Surface

If you need to trigger an HTTP Request by a button on your Remote Control Surface you can add an Automation layer to you layer stack and set the “Switch Layer Off” option of that layer to “Automatically”. Now you can put in a single httpRequest() command in the “On Live” script field. On your Remote Control Surface add the Live button of this layer to the layout. Once you press this button on your Remote Control Surface the HTTP request will be performed.

Your Feedback

How would you rate your experience with this feature of mimoLive®?

User Manual: Recent Updates

Castr

Castr is a cloud-based live re-streaming platform that allows users to stream content to multiple

Read More »

Choose Language