There's an important bit of information to recognize when using ARC. That information is regarding what a control is. Within the ARC project desktop, there are plenty of windows, and each window is a control. A control is actually a little program that runs within ARC. For example, there are hundreds of available controls in ARC which you can add to the project desktop. Each control is a behavior that gives your robot more ability. The most common controls that you will see in the default JD/Six/Roli projects are Connection, Camera, and Auto Position. These controls are each separate programs that do something specific, such as processing video image data from the camera, or move servos in animations. Because each control is a separate program, ARC provides a mechanism for controls to talk to each other. This mechanism is the script ControlCommand(). Using this command, an event of one control, can instruct another control to do something. For example, if the Speech Recognition control detects the phrase "Follow My Face", the respective code may be instructed to inform the Camera control to enable Face Tracking.
For a larger series of messages, this detailed example detects speech recognition text and uses cognitive services. The manuals for each skill will be important to review when creating projects.
In The Code
In the above example, the "Follow My Face" phrase within the Speech Recognition control instructed the Camera to begin Face Tracking. Let's take a look at the code within the Speech Recognition control that made this happen. Below, you will see the Blockly and respective script that was assigned to the "Follow My Face" within the Speech Recognition control.
What Commands Are There?
Each control will accept a certain number of ControlCommand()s. Not all controls accept the same commands. ARC will query each control and ask "What control commands do you accept?", and create a list for you. The list is presented in three places. Here are screenshots of each location to find the available ControlCommands() for all controls within the project.
The Cheat Sheet tab is displayed when editing script
Right-Click in the editor when editing script
Blockly provides a block in the Utility category
How Does It Work?
Behind the scenes, ARC has a Control Manager, which knows of all the controls within the project. The Control Manager knows each control by its name. Controls are given an unique name by the Control Manager when added to a project. Although, you may also edit the name of controls within their configuration page. The ControlCommand() requires the name of the control that it will be speaking to as the first parameter. All other parameters are dependent on the control as presented in the previous step (Cheat sheet, right-click, blockly).
ControlCommmand() Never Waits
controlCommand("Auto Position", "AutoPositionAction", "Wave"); Audio.SayEZB("I am waving");
The above code instructed the Auto Position to wave and immediately spoke the phrase "I am waving" out of the EZ-B's speaker. The script did not wait for the Wave action to complete before speaking the phrase. This is because the Auto Position control is a separate program. The script used ControlCommand() to instruct the Auto Position to execute the Wave action, and immediately moved onto the next line of code without waiting for the Auto Position Wave to complete. This is because ControlCommand() is one direction. Meaning, the ControlCommand() can only nudge another control by saying "Hey, do this...." and does not receive a response.
What If I Want To Wait?
The ControlCommand() instructs another control to "do something" and does not wait for it to finish. The only exception to this rule is when the ControlCommand() parameter explicitly specifies that it waits. An example would be the Scripting control. This is because the Scripting control accepts an unique ControlCommand() parameter "ScriptStartWait", which will wait for the script to complete. There are very few ControlCommands()'s that behave this way, and those that do will have "Wait" specified in the parameter name. This is because ControlCommand() is generally a non-blocking method.
In the previous step, the Auto Position Wave action executes, and the next line of code is immediately executed. If you wanted to wait until the Wave was completed in the Auto Position, you can still do that. This is because some controls will populate variables that hold their operation status. Meaning, some controls will create a variable (i.e. $AutoPositionStatus) which is TRUE (1) or FALSE (0) regarding the status. In the above scenario, we can wait for the Auto Position to complete by monitoring the variable. It is important to notice that not all controls provide a status variable. The controls that do provide a status variable will generally have the variable displayed its configuration settings page. Otherwise, viewing all variables within the project can be done using the Variable Watcher.
controlCommand("Auto Position", "AutoPositionAction", "Wave"); sleep(500); while (getVar("$AutoPositionStatus")); Audio.SayEZB("I finished waving");
Examining the above code, one will notice the familiarity of the ControlCommand() instructing the Auto Position to execute the Wave action. However, the next 2 lines of code are new. The Sleep(500) provides a short delay to give the Auto Position control enough time to begin executing the instruction. The following line WaitFor(getVar("$AutoPositionStatus")) will wait for ever until the specified condition is met. In this case, the specified condition is $AutoPositionStatus = 0, which means when the Auto Position control is no longer active. This while() will wait until the Auto Position has completed, because the Auto Position will set the $AutoPositionStatus value to FALSE (0) when it has. Finally, the last line of the script will speak after the Auto Position has completed.