# Actions

Actions control the robot's movement and lights; they can be listed in Oval programs by ending with a ; and separated with line breaks like the Hello World! program. Sphero robots move with three basic instructions: speed, delay, and heading. For example, if you set speed = 60, delay = 3s and heading = 0°, the robot would roll forward for 3s at a moderate speed.

### Set Speed

// type: float // access: read & write // range: 0.0 - 255.0 // units: none

controlSystemTargetSpeed sets (writes) the speed of the robot from 0 to 255. Each robot translates the value differently into a real world speed; Ollie is almost three times faster than Sphero. For example, use controlSystemTargetSpeed = 188 to set the speed to 188 which persists until you set a different speed. You can also get (read) speed.

What is the 0-255 scale? The memory on Sphero is tiny, only 256,000 bytes, compared to your computer which has billions of bytes. Using the raw value of 0-255 takes up only 1 byte, the smallest amount of space possible, therefore leaving more space to run interesting programs.

What is a byte? A computer reads 1's and 0's, and a byte is eight 1's or 0's. Here is how a computer counts to 5 : 0 = 0, 1= 1, 2 = 10, 3 = 11, 4 = 100, 5 = 101. With eight digits, the biggest number you can make is 255 = 11111111. Therefore the possible speed range using one byte is 0-255.

Why not tranlate the raw scale into a percent? We decided to keep the 0-255 scale instead of a percentage so that users could learn about how computers store information, and so they could create variables to represent raw Speed values in the Lightning Lab app.

### Real-World Speed

The robot can't set a real world speed or distance because it does not have a speedometer, nor is it aware of the rolling surface. Luckily, you can use some basic data gathering, calculate the real-world speed, and then reliably predict distances that you can program. You can use our data collected using a SPRK+ robot on a concrete floor, or repeat this process on your surface to ensure the data is accurate for your environment:

1. Setup a measuring tape on the floor and tape a cross at 0cm to place Sphero on.
2. Aim your robot with the blue tail-light facing you, making sure it's perfectly straight.
3. Write a program that rolls forward at 60 speed (or any speed you prefer), and add a delay for your longest measurement. Make sure you start with the longest delay.
4. Run the program ensuring the robot rolls perfectly straight. If it's not straight, adjust your aim. When straight, measure and log the distance in a spreadsheet.
5. Repeat step 5 with shorter delays and record the distances. Be precise.
6. Now you can solve Speed = Distance / Delay for each distance and use it to calculate implied speeds to reduce the work of recording more distances. Notice that shorter distances report slower speeds? That's because we're not accounting for acceleration in this basic example.

Speed(0-255) Delay(s) Distance(cm) Speed(cm/s)
60 1.0 55.00 55.00
60 2.0 111.25 55.63
60 3.0 167.75 55.92
60 4.0 230.50 57.63
60 5.0 288.25 57.65
---------------------- -------------- --------------------- --------------

### Stop

// type: float // access: read & write // range: 0.0 - 255.0 // units: none

controlSystemTargetSpeed = 0 sets the speed to zero to stop the robot.

// type: float // access: read & write // range: -180 - 180 // units: degrees

controlSystemTargetYaw sets the direction the robot rolls. Assuming you aim the robot with the blue tail light facing you, then 0° is forward, 90° is right, 270° is left, and 180° degrees is back. For example, use controlSystemTargetYaw = 90 to set the heading to 90° to turn right.

### Set Color

// type: float // access: write // range: 0.0 - 255.0 // units: none

setRgbLed changes the color of the main LED lights. Set this using RGB (red, green, blue) values on a scale of 0 - 255. For example, the below green color can be expressed as setRgbLed(90, 255, 90):

nextRandomFloat chooses a random value from zero to an upper bound. For example, use setRgbLed(nextRandomFloat * 255, nextRandomFloat * 255, nextRandomFloat * 255)  to set a random color from the full spectrum of 0-255. If used in a loop you can expect the RGB values to be different each time through the loop. In the block canvas, the Randomize toggle on the color picker has the same effect.

You can also set each color channel independently using color commands one at a time using
redLed = 13
greenLed = 255
blueLed = 13

There is also a Color "Sensor" documented so that beginners using the block canvas can easily embed it in conditions, and the Set Block. While the Oval code for controlling color is the same for the Action and the Sensor, the context is different.

### Back LED

// type: float // access: write // range: 0 - 255 // units: none

backLed sets the brightness of the back aiming LED, aka the Tail Light. This LED is limited to blue only, on a scale from 0 to 255. For example, use backLed = 255 to set the back LED to full brightness. Use delay to set the backLed on for a duration. For example, to create a dim and a bright blink sequence use:

void startProgram()
{
backLed = 10;
delay(1);
backLed = 0;
delay(1);
backLed = 255;
delay(2);
backLed = 0;
}

### Stabilization

// type: int // access: read & write // range: true, false // units: boolean

controlSystemIsOn turns the stabilization system on (1) or off (0). Stabilization is normally on (1) to keep the robot upright using the Inertial Measurement Unit (IMU) - a combination of readings from the Accelerometer (directional acceleration), Gyroscope (rotation speed), and Encoders (derrived distance). When off (0) the robot will not balance, resulting in unstable behaviors like jumping or wobbling. Some use cases to turn off are:

1. Jumping: Set Motor Power to max values and the robot will jump off the ground!
2. Gyro-Accuracy: Programs like the Spinning Top, where you don't want the robot spinning inside itself, are used to isolate and enable accurate Gyroscope readings.

Warning!
When stabilization is off you can't use controlSystemTargetSpeed to set a speed because it requires the control system to be on to function. However, it is possible to control the motors using Motor Power with rightMotorPwm and leftMotorPwm when the control system is off.

### Reset Aim

// type: int // access: read & write // range: 0 - 360 // units: none

setCalibration resets the heading calibration (aim) angle to use the current direction of the robot as 0 degrees, with a range of 0-360 degrees. For example, use setCalibration = 90 to use the current right facing direction of the robot as 0 degrees. When used in the block canvas, Reset Aim is limited to set the current front facing direction of the robot as 0°, with setCalibration = 0.

### Play Sound

This allows you to play a sound from the list below, such as the Monkey sound from the Animal category in the below example. Sounds play from your device's speaker, so remember to turn up your volume. While you can use playSound like a normal Oval command in Lightning Lab, it is not native Oval. We extended the Oval language with added sounds just for the app app as a fun addition to your programs.

playSound(3, 15);
delay(.05);

Only one sound can be played at a time, so the delay(.05) is a brief offset to prevent subsequent sounds from overlapping. If you tried to play sounds in a tight loop without any delay, the Oval runtime won’t have enough time to send data back to your device. We solved this on the Block Canvas by adding default delay between all playSound calls. If you want to play sounds back to back or in a loop, you should add a longer duration like delay(1.5) after each playSound command to prevent overlapping.

- -

### All

-
Random playSound(-1, -1)

### Effects

-
Random playSound(0, -1)
Applause playSound(0, 0)
Beep playSound(0, 1)
Boil playSound(0, 2)
Boing playSound(0, 3)
Bowling Pins playSound(0, 4)
Click playSound(0, 5)
Creaky Door playSound(0, 6)
Ding playSound(0, 7)
Door Bell playSound(0, 8)
Explosion playSound(0, 9)
Fairy playSound(0, 10)
Fast Forward playSound(0, 11)
Hum playSound(0, 12)
Keyboard playSound(0, 13)
Laser playSound(0, 14)
Record Scratch playSound(0, 15)
Rewind playSound(0, 16)
Thunder playSound(0, 17)
Whip playSound(0, 18)
Whistle playSound(0, 19)

### Personality

--------------
Random playSound(1, -1)
Alert playSound(1, 0)
Boo playSound(1, 1)
Celebrate playSound(1, 2)
Cry playSound(1, 3)
Curious playSound(1, 4)
Dizzy playSound(1, 5)
Dreaming playSound(1, 6)
Laugh Evil playSound(1, 7)
Laugh Nice playSound(1, 8)
No playSound(1, 9)
Sad playSound(1, 10)
Suprised playSound(1, 11)
Thinking playSound(1, 12)
Yawn playSound(1, 13)
Yes playSound(1, 14)

### Mechanical

--------------
Random playSound(2, -1)
Accelerate playSound(2, 0)
Airplane playSound(2, 1)
Ambulance playSound(2, 2)
Chainsaw playSound(2, 3)
Collision playSound(2, 4)
Drill playSound(2, 5)
Engine Drive By playSound(2, 6)
Engine Idle playSound(2, 7)
Engine Peak playSound(2, 8)
Engine Rev playSound(2, 9)
Engine Start playSound(2, 10)
Freefall playSound(2, 11)
Gyromax playSound(2, 12)
Helicopter playSound(2, 13)
Honk playSound(2, 14)
Landing playSound(2, 15)
Police Siren playSound(2, 16)
Skid playSound(2, 17)
Tractor playSound(2, 18)
Train playSound(2, 19)

### Animal

--------------
Random playSound(3, -1)
Aligator playSound(3, 0)
Bear playSound(3, 1)
Bird playSound(3, 2)
Cat playSound(3, 3)
Chicken playSound(3, 4)
Cow playSound(3, 5)
Dog playSound(3, 6)
Dolphin playSound(3, 7)
Donkey playSound(3, 8)
Duck playSound(3, 9)
Elephant playSound(3, 10)
Dog playSound(3, 11)
Horse playSound(3, 12)
Horse Gallop playSound(3, 13)
Lion playSound(3, 14)
Monkey playSound(3, 15)
Pig playSound(3, 16)
Rooster playSound(3, 17)
Sea Lion playSound(3, 18)
Sheep playSound(3, 19)
Tiger playSound(3, 20)
Whale playSound(3, 21)

### Water

--------------
Random playSound(4, -1)
Anchor Splash playSound(4, 0)
Boat Engine playSound(4, 1)
Boat Horn playSound(4, 2)
Boat In Water playSound(4, 3)
Boat Start playSound(4, 4)
Brass Bell playSound(4, 5)
Bubbles playSound(4, 6)
Dive Alram playSound(4, 7)
Engine Room playSound(4, 8)
Sonar playSound(4, 9)
Submarine playSound(4, 10)
Waves playSound(4, 11)
-------------- --------------

### Speak

Enter any text and the text-to-speech engine will speak the words, in any language supported by your device. You can add a lot of interesting logic with this block. For example, in the Fortune Teller program you can replace the Play Sound blocks with Speak blocks that give fun asnwers, like "Yes, of course," or "Never in a million years." This feature is not currenlty available in the text canvas but will be supported in a future release, along with the ability to embed and read out variable and sensor values.

Where are the other Action blocks?
The Roll, Raw Motor, Spin, Fade and Strobe blocks are actually Functions, not pure Oval code. Head to the Functions page to learn how to use them in the text canvas.

## Beyond Blocks

Oval "Action-like" commands that are not available in the block programming canvas.

### Motor Power

// type: int // access: read & write // range: -4095 - 4095 // units: none

rightMotorPwm and leftMotorPwm control the electrical power sent to the left and right motors independently, on a scale from -4095 to 4095. If you set both motors to full power the robot will jump because stabilization is disabled when using this command. Motor Power is different from Set Speed because Raw Motor sends an "Electromotive force" to the motors, whereas Set Speed is a target speed measured by the encoders. The Raw Motor function sets these values for a duration.

### Current Robot Time

// type: float // access: read & write // range: any // units: seconds

currentRobotTime read and write the local time on the robot. For example, we use currentRobotTime in the _doRoll function:

void _doRoll(float duration, float speed, float direction)
{
if (duration > 0)
{
controlSystemTargetYaw = direction;
controlSystemTargetSpeed = speed;

float finishTime = currentRobotTime + duration;
while (currentRobotTime < finishTime)
{
wait;
}
}
controlSystemTargetSpeed = 0;
}

### Inverted

// type: int // access: read & write // range: 0,1 // units: boolean

controlSystemIsInverted enables the control system to be inverted to balance and roll upside down. This works predictably for Ollie, but not very well on Sphero or BB-8. Use controlSystemIsInverted = 1 and the robot will attempt to stabilize upside down. Use 0 controlSystemIsInverted = 0 to return to normal.