Programming with Lego Brick Control OCX

OCX Listing

The listing for the Lego Brick Control OCX (spirit.ocx) is at the end of this document.

Program Structure

The are 5 program slots in the RCX. Each program slot can store up to 8 subroutines and 10 tasks. Tasks are codes that can execute simultaneous. Subroutines are code blocks that store common codes. Subroutines are optional because you can always inline all common codes in the each tasks

A typical RCX program might look like the following:


SelectPrgm(3) // slot # 4
BeginOfSub(3)
... //code for subroutine 3
EndOfSub()

... //other subroutines

BeginOfSub(6)
... //code for subroutine 6
EndOfSub()

BeginOfTask(1)
... //code for task 1
EndOfTask()
BeginOfTask(0)
... //code for task 0
EndOfTask()

 

Task #0 is the default task that executes when you press RUN/STOP button on the RCX. To perform multitasking, you can initiate execution of other tasks by using StartTask():

BeginOfTask(0)
// start 3 tasks
StartTask(1)
StartTask(2)
StartTask(3)
// forever loop
SetVar(0,2,1)
While(0,1,2,2,1)
EndWhile()
EndOfTask()

Now 3 tasks (1,2,3) will be running in parallel. Note that a repeat-forever loop is placed in Task 0 so that you can use the STOP/RUN button to stop the program and turn off the motors.

You cannot call another subroutine within a subroutine.

 

Memory Locations

Many methods in RCX require the [Source,Number] parameter pair. Together, they specify the memory location to be used in each method.

Source (S)

Number (N)

Description

0

0..31

Variables

1

0..4

Timers

2

-32767..32767

Immediate Mode
Returned value is constant value N.

3

0..2

Current State of Motor N
bits 0..2 : motor power
bit 3 : direction (1=fwd, 0=rwd)
bits 4..5 : motor number
bits 6..7 : motor state (0=float, 1=off, 2=on)

4

1..32767

Random Number
Returned value is random number from 0 to N, inclusive.

5

0..2

?

6

?

?

7

?

?

8

0

Program Slot Number

9

0..2

Current Reading of Sensor N
Returned value depends on sensor mode. For example, if the sensor mode for a touch sensor is set to Boolean(1). It returns 1 when pressed and 0 otherwise. On the other hand, it returns a high value (~1023) and low value (~50), respective, when the sensor mode is set to Raw(0).

10

0..2

Sensor Type
0 = none
1 = touch
2 = temperature
3 = light
4 = rotation

11

0..2

Sensor Output Level

12

0..2

Raw Sensor Reading
Returned value is actual sensor reading, ranges from 0 to 1023.

13

0..2

?

14

0

Clock/Watch Value
Returned value is current time in number of minutes. For example, it returns 754 if the clock shows 12:34.

15

0

Received RCX Message ID
Returned value is the ID (0..255) of inter-RCX message received. This value will remain until it is explicitly cleared.

 

Variables and Constants

There are 32 variables: variable number 0 thru 31 ([0,0], [0,1],...[0,31]). I think variable 0 might be a reserved variable. Immediate mode [2,N] is used to specify a constant value N in each call.

Examples:

SetVar (2, 2, 1023) // store 1023 into variable number 2 ([0,2]).

Wait (2, 10) // wait 0.1 second

Wait (0, 10) // wait for duration specified by variable number 10

 

Flow Controls

Using variables and memory locations, loop and branch constructs can be used to control the flow of each task. Four binary logical operators can be specified in the RelOp parameters:

0 = greater than (>)
1 = less than (<)
2 = equal to (==)
3 = not equal to (!=)

Examples:

1. To specify a loop that executes twice using Loop():


Loop(2,2)
... // code to be repeated twice
EndLoop()

 

2. To specify a loop that repeats 10 times using While():

SetVar(5,2,10) // set variable number 5 to 10
While(0,5,1,2,0) // loop until variable number 5 becomes zero
... // code to be repeated 10 times
SubVar(5,2,1) // decrement variable number 5 each iteration
EndLoop()

3. If-else statement:

If (0, 5, 2, 2,4) // test if variable number 5 is equal to 4
... // code to be executed when variable 5 == 4
Else()
... // code to be executed when variable 5 != 4
EndIf()

 

Motors

You can perform the following to each motor:

MotorList parameter is used to specify which motor to control in motor related commands. It is a string containing up to 3 motor id(s):

"0" = motor A
"1" = motor B
"2" = motor C

For example, while "1" indicates motor B, "012" designates all 3 motors.

Sensors

You can have up to 3 sensors connected to the RCX. Each sensor can be one of the following types: turn it on (On)

Each sensor have two reading values: raw reading and a filtered reading. The raw reading will give you a value between 0 and 1023. The filtered reading is set up by the following eight possible sensor mode settings:

 

Downlaoding Firmware

Perform the following sequence to download firmware:

  1. call UnlockPBrick() to obtain ROM version number
  2. call DownloadFirmware("c:\Program Files\Lego Mindstorms\Firm\firm0309.lgo") to download firmware version 3.09
  3. call UnlockFirmware("Do you byte, when I knock?") after the firmware ic completely downloaded to RCX.

Event Handling

You can attach code to execute upon the occurrence of the following events:

Lego Brick Control OCX methods

Program, Task, and Subroutines

SelectPrgm (Number)

Number = 0..4
Select which program slot to download.

BeginOfSub (Number)

Number = 0..7
Specify the start of a subroutine.

EndOfSub ()

Specify the end of a subroutine to be downloaded.

EndOfSubNoDownload ()

Specify the end of a subroutine without download.

BeginOfTask (Number)

Number = 0..9
Specify the start of a task.

EndOfTask ()

Specify the end of a task to be downloaded.

EndOfTaskNoDownload ()

Specify the end of a task without download.

GoSub (Number)


Number = 0..7
Branch to subroutine. You cannot call another subroutine from a subroutine.

StartTask (Number)

Number = 1..9
Start execution of task.

DeleteAllSubs ()

Remove all subroutines from selected program.

DeleteAllTasks ()

Remove all tasks from selected program.

DeleteSub (Number)

Number = 0..7
Remove specified subroutine from selected program.

DeleteTask (Number)

Number = 0..9
Remove specified task from selected program.

StopAllTasks ()

Stop execution of all tasks.

StopTask (Number)

Stop execution of specified task.

Motor Commands

 

On (MotorList)

Turns on motor(s).

Off(MotorList)

Turns off motor(s). The motor(s) are stopped immediately.

Float(MotorList)

Stop the motor(s) smoothly.

SetFwd(MotorList)

Set motor(s) to forward direction.

SetRwd(MotorList)

Set motor(s) to reverse direction.

AlterDir(MotorList)

Change direction.

SetPower(MotorList, Source, Number)

Set the power of the motor(s) using the value from memory location [Source,Number]. The value must be between 0 and 7.

OnWait(MotorList, Number, Time)

OnWaitDifferent(MotorList, Number0, Number1, Number2, Time)

Flow Controls

 

If(Source1, Number1, RelOp, Source2, Number2)
Else()
EndIf()

If-then-else construct:
If [Source1,Number1] RelOp [Source2,Number2] is true, the code block between If() and Else() will execute. Otherwise, code block between Else() and EndIf will execute. Please note that the Else() part is optional.

Loop(Source, Number)
EndLoop()

For-Loop construct:
Repeat the code block between Loop() and EndLoop() N times if the value of the memory location [Source, Number] is N. You cannot have nested Loop()-EndLoop() constructs.

While(Source1, Number1, RelOp, Source2, Number2)
EndWhile()

While-Loop construct:
While [Source1,Number1] RelOp [Source2,Number2] is true, the code block between While() and EndWhile() will execute.

Wait(Source, Number)

Wait for duration specified by memory location [Source.Number]. The value is specified in number of 1/100 seconds.

 

Variable Controls

SetVar(VarNo, Source, Number)

VarNo = [Source,Number]

Store the specified value (Source, Number) into the specified variable (VarNo).

SumVar(VarNo, Source, Number)

VarNo = VarNo + [Source,Number]

Add the specified value (Source, Number) to the specified variable (VarNo).

SubVar(VarNo, Source, Number)

VarNo = VarNo - [Source,Number]

Subtract the specified value (Source, Number) from the specified variable (VarNo).

MulVar(VarNo, Source, Number)

VarNo = VarNo * [Source,Number]

DivVar(VarNo, Source, Number)

VarNo = VarNo / [Source,Number]

AndVar(VarNo, Source, Number)

VarNo = VarNo & [Source,Number]

OrVar (VarNo, Source, Number)

VarNo = VarNo | [Source,Number]

SgnVar(VarNo, Source, Number)

VarNo = sign([Source,Number])

Returns -1 if [Source,Number] < 0,
0 if [Source,Number] == 0,
1 when [Source,Number] > 0.

AbsVar(VarNo, Source, Number)

VarNo = abs([Source,Number]) (?)

 

Sensor Controls

SetSensorType(Number, Type)

Type = 0..4
0 = none
1 = touch
2 = temperature
3 = light
4 = rotation
This call set up a sensor.

SetSensorMode(Number, Mode, Slope)

Mode = 0..7
0 = raw
1 = Boolean
2 = edge
3 = pulse
4 = percent
5 = temperature in degree C
6 = temperature in degree F
7 = rotation angle

Slope = 0..31

This call set up the type of sensor reading values returned in memory locations [9,0], [9,1], and [9,2] for sensor 1, 2, and 3, respectively.

ClearSensorValue(Number)

Number = 0..2

This call clears the sensor reading value at memory locations [9,0], [9,1], and [9,2] for sensor 1, 2, and 3, respectively.

ClearTimer(Number)

This call reset the specified timer to zero value.

Other RCX Controls

PlaySystemSound(Number)

Play a system tone:
0=blip
1=beepbeep
2=down
3=up
4=buzz
5=upfast

PlayTone(Frequency, Time)

Play a tone at specified frequncy (Hz) for duration (1/100 sec).

SetWatch(Hours, Min)

Set RCX free-running clock to hours:min.

SendPBMessage(Source, Number)

Send out a message with value specified by (Source, Number)

ClearPBMessage()

Clear the RCX message number to zero (memory location [15,0])

SelectDisplay(Source, Number)

Select the RCX display format:
0 = Watch
1 = Sensor 1
2 = Sensor 2
3 = Sensor 3
4 = Motor A
5 = Motor B
6 = Motor C

Debug Tools

Poll(Source, Number)

Returns the value at the memory location [Source, Number].

MemMap()

Returns the memory map.

 

SetDatalog(Size)

Allocates memory for the data log in RCX.

DatalogNext(Source, Number)

UploadDatalog(From, Size)

Returns the specified part of the data log.

 

Misc

AboutBox()

Brings up the "about" information dialog.

InitComm()

Initiate communications with RCX.

CloseComm()

Terminate communications with RCX.

UnlockPBrick()

Must be called before downloading firmware.

DownloadFirmware(filename)

Download firmware file to RCX.

UnlockFirmware(UnlockString)

Unlock the previouly downloaded firmware.
UnlockString="Do you byte, when I knock?"

PBAliveOrNot()

Returns whether PC can communicate with RCX.

PBBattery()

Returns voltage of power source (battery or AC adaptor) in 1/1000 Volts.

PBPowerdownTime(Time)

Set RCX automatic power-down time.

PBTurnOff()

Turns off RCX.

PBTxPower(Number)

Set the output power level of the RCX IR transmitter.

TowerAlive()

Returns whether IR tower is alive.

TowerAndCableConnected()

Returns whether IR tower is connected to the PC.

Unknown

ClearAllEvents()

ClearEvent(Source, Number)

SetEvent(Source, Number, Time)

ErrCorAckAddCustom(noOfErrorBytes, noOfErrorBitsInErrorByte, errorByte1, errorByte2, errorByte3, errorByte4)

ErrCorAckDeleteAll()

ErrCorAckGetLStat()

ErrCorAckGetSStat()

ErrCorAckReset()

GetLongTermRetransmitStatistics()

GetShortTermRetransStatistics()

GetThreadPriority(threadNo, threadClass, threadPriority)

IgnDLerrUntilGoodAnswer()

SetRetransmitRetries(immidiateRetries, downloadRetries)

SetThreadPriority(hreadNo, threadClass, threadPriority)

ClearTachoCounter(MotorList)

Drive(Number0, Number1)

 

 

Visual Basic Specification for the Lego Brick Control OCX

Enumeration Types

Enum COMPORTOPTIONS
COM1 = 1
COM2 = 2
COM3 = 3
COM4 = 4
End Enum

Enum ErrorCodes
UNKNOWN = 2000
FATAL = 2001
PROGRAM_ERROR = 2002
PIPE_TO_THREAD_ERROR_SENDER = 2003
PIPE_TO_THREAD_ERROR_RECEIVER = 2004
TOO_MANY_RESENDS = 2005
SYNTAX_MATCHING_ENDIF_NOT_FOUND = 2006
SYNTAX_MATCHING_ENDWHILE_NOT_FOUND = 2007
SYNTAX_MATCHING_ENDLOOP_NOT_FOUND = 2008
SYNTAX_END_REACHED_TOO_SOON = 2009
SYNTAX_TO_MANY_NESTED_LOOPS_IN_TASK = 2010
SYNTAX_TO_MANY_NESTED_LOOPS_IN_SUB = 2011
SYNTAX_ENDOFSUB_RECEIVED_ENDOFTASK_EXPECTED = 2012
SYNTAX_ENDOFTASK_RECEIVED_ENDOFSUB_EXPECTED = 2013
SYNTAX_GOSUB_NOT_ALLOWED_IN_SUBS = 2014
DOWNLOAD_ERROR = 2015
DOWNLOADFIRMWARE_ERROR = 2016
DOWNLOAD_FROM_FILE = 2017
DOWNLOAD_NOT_ENOUGH_MEMORY = 2018
DOWNLOAD_ERROR_IN_DOWNLOAD_CHECKSUM = 2019
DOWNLOAD_ERROR_IN_DOWNLOAD_RAMCHECKSUMERROR = 2020
RETURN_ERROR_FROM BRICK = 2021
RANGE_CHECK_ERROR = 2022
SEMANTIC_IF_ARGUMENTS_OUT_OF_RANGE = 2023
SEMANTIC_WHILE_ARGUMENTS_OUT_OF_RANGE = 2024
SEMANTIC_LOOP_ARGUMENTS_OUT_OF_RANGE = 2025
DOWNLOAD_ERROR_UNKNOWN = 2026
DOWNLOAD_ERROR_ALREADY_IN_DL_WHEN_RECIEVING_BEGIN = 2027
DOWNLOAD_BRICK_IS_NOT_IN_DL_MODE = 2028
DOWNLOAD_SYNTAX_ERROR_IN_BLOCK = 2029
End Enum

Enum LINKTYPEOPTIONS
InfraRed = 0
Cable = 1
Radio = 2
End Enum

Enum PBRICKOPTIONS
Spirit = 0
RCX = 1
End Enum

Enum PROCESSPRIORITYCLASS
DefaultClass = 0
HIGH_PRIORITY_CLASS = 1
IDLE_PRIORITY_CLASS = 2
NORMAL_PRIORITY_CLASS = 3
REALTIME_PRIORITY_CLASS = 4
End Enum

Enum THREADNAME
CommPortThread = 0
EventThread = 1
DownloadThread = 2
End Enum

Enum THREADPRIORITY
THREAD_PRIORITY_ABOVE_NORMAL = 0
THREAD_PRIORITY_BELOW_NORMAL = 1
THREAD_PRIORITY_HIGHEST = 2
THREAD_PRIORITY_IDLE = 3
THREAD_PRIORITY_LOWEST = 4
THREAD_PRIORITY_NORMAL = 5
THREAD_PRIORITY_TIME_CRITICAL = 6
End Enum

Attributes

ComPortNo As COMPORTOPTIONS
LinkType As LINKTYPEOPTIONS
PBrick As PBRICKOPTIONS

Operations

Sub AboutBox ()
Function AbsVar (VarNo As Integer, Source As Integer, Number As Integer) As Boolean
Function AlterDir (MotorList As String) As Boolean
Function AndVar (VarNo As Integer, Source As Integer, Number As Integer) As Boolean
Function BeginOfSub (Number As Integer) As Boolean
Function BeginOfTask (Number As Integer) As Boolean
Function ClearAllEvents () As Boolean
Function ClearEvent (Source As Integer, Number As Integer) As Boolean
Function ClearPBMessage () As Boolean
Function ClearSensorValue (Number As Integer) As Boolean
Function ClearTachoCounter (MotorList As String) As Boolean
Function ClearTimer (Number As Integer) As Boolean
Function CloseComm () As Boolean
Function DatalogNext (Source As Integer, Number As Integer) As Boolean
Function DeleteAllSubs () As Boolean
Function DeleteAllTasks () As Boolean
Function DeleteSub (Number As Integer) As Boolean
Function DeleteTask (Number As Integer) As Boolean
Function DivVar (VarNo As Integer, Source As Integer, Number As Integer) As Boolean
Function DownloadFirmware (filename As String) As Boolean
Function Drive (Number0 As Integer, Number1 As Integer) As Boolean
Function Else () As Boolean
Function EndIf () As Boolean
Function EndLoop () As Boolean
Function EndOfSub () As Integer
Function EndOfSubNoDownload () As Integer
Function EndOfTask () As Integer
Function EndOfTaskNoDownload () As Integer
Function EndWhile () As Boolean
Sub ErrCorAckAddCustom (noOfErrorBytes As Integer,
noOfErrorBitsInErrorByte As Integer,
errorByte1 As Integer, errorByte2 As Integer,
errorByte3 As Integer, errorByte4 As Integer)
Sub ErrCorAckDeleteAll ()
Function ErrCorAckGetLStat () As Variant
Function ErrCorAckGetSStat () As Variant
Sub ErrCorAckReset ()
Function Float (MotorList As String) As Boolean
Function GetLongTermRetransmitStatistics () As Variant
Function GetShortTermRetransStatistics () As Variant
Sub GetThreadPriority (threadNo As THREADNAME,
threadClass As PROCESSPRIORITYCLASS,
threadPriority As THREADPRIORITY)
Function GoSub (Number As Integer) As Boolean
Function If (Source1 As Integer, Number1 As Integer, RelOp As Integer,
Source2 As Integer, Number2 As Integer) As Boolean
Function IgnDLerrUntilGoodAnswer () As Boolean
Function InitComm () As Boolean
Function Loop (Source As Integer, Number As Integer) As Boolean
Function MemMap () As Variant
Function MulVar (VarNo As Integer, Source As Integer, Number As Integer) As Boolean
Function Off (MotorList As String) As Boolean
Function On (MotorList As String) As Boolean
Function OnWait (MotorList As String, Number As Integer, Time As Integer) As Boolean
Function OnWaitDifferent (MotorList As String, Number0 As Integer, Number1 As Integer,
Number2 As Integer, Time As Integer) As Boolean
Function OrVar (VarNo As Integer, Source As Integer, Number As Integer) As Boolean
Function PBAliveOrNot () As Boolean
Function PBBattery () As Integer
Function PBPowerdownTime (Time As Integer) As Boolean
Function PBTurnOff () As Boolean
Function PBTxPower (Number As Integer) As Boolean
Function PlaySystemSound (Number As Integer) As Boolean
Function PlayTone (Frequency As Integer, Time As Integer) As Boolean
Function Poll (Source As Integer, Number As Integer) As Integer
Function SelectDisplay (Source As Integer, Number As Integer) As Boolean
Function SelectPrgm (Number As Integer) As Boolean
Function SendPBMessage (Source As Integer, Number As Integer) As Boolean
Function SetDatalog (Size As Integer) As Boolean
Function SetEvent (Source As Integer, Number As Integer, Time As Integer) As Boolean
Function SetFwd (MotorList As String) As Boolean
Function SetPower (MotorList As String, Source As Integer, Number As Integer) As Boolean
Function SetRetransmitRetries (immidiateRetries As Integer,
downloadRetries As Integer) As Boolean
Function SetRwd (MotorList As String) As Boolean
Function SetSensorMode (Number As Integer, Mode As Integer, Slope As Integer) As Boolean
Function SetSensorType (Number As Integer, Type As Integer) As Boolean
Function SetThreadPriority (threadNo As THREADNAME, threadClass As PROCESSPRIORITYCLASS,
threadPriority As THREADPRIORITY) As Boolean

Function SetVar (VarNo As Integer, Source As Integer, Number As Integer) As Boolean
Function SetWatch (Hours As Integer, Min As Integer) As Boolean
Function SgnVar (VarNo As Integer, Source As Integer, Number As Integer) As Boolean
Function StartTask (Number As Integer) As Boolean
Function StopAllTasks () As Boolean
Function StopTask (Number As Integer) As Boolean
Function SubVar (VarNo As Integer, Source As Integer, Number As Integer) As Boolean
Function SumVar (VarNo As Integer, Source As Integer, Number As Integer) As Boolean
Function TowerAlive () As Boolean
Function TowerAndCableConnected () As Boolean
Function UnlockFirmware (UnlockString As String) As String
Function UnlockPBrick () As String
Function UploadDatalog (From As Integer, Size As Integer) As Variant
Function Wait (Source As Integer, Number As Integer) As Boolean
Function While (Source1 As Integer, Number1 As Integer, RelOp As Integer,
Source2 As Integer, Number2 As Integer) As Boolean

 

Events

Event AsyncronBrickError (Number As Integer, Description As String)
Event DownloadDone (ErrorCode As Integer, DownloadNo As Integer)
Event DownloadSize (DownloadSizeInBytes As Long)
Event DownloadStatus (timeInMS As Long, SizeInBytes As Long, taskNoAs Integer)
Event DownloadTime (DownloadSizeInMS As Long)
Event DownloadTimeAndSize (timeInSeciSeconds As Long, sizeInBytes As Long)
Event InputChange (Number As Integer, Value As Integer)
Event RetransmitInfo (RetransmitCount As Integer)
Event VariableChange (Number As Integer, Value As Integer)