Home > Articles > Programming > Java

Lego Mindstorms Programming: RCX Communications

Brian Bagnall discusses RCX communications in this sample chapter from Core LEGO MINDSTORMS Programming: Unleash the Power of the Java Platform. Learn about: the communications API, uploading map data, controlling the RCX through a network, controlling the RCX from a Web page, alternate data transfer methods, and alternate communication uses.
This sample chapter is excerpted from Core LEGO MINDSTORMS Programming: Unleash the Power of the Java Platform, by Brian Bagnall.
This chapter is from the book

Topics in this Chapter

  • The Communications API
  • Uploading Map Data
  • Controlling the RCX Through a Network
  • Controlling the RCX from a Web Page
  • Alternate Data Transfer Methods
  • Alternate Communication Uses

Communications between the RCX brick and a PC can greatly expand the potential of robotics projects. Memory is quite limited on the RCX but today's PCs contain an abundance. A clever programmer can off load complex code to the PC side, allowing the PC to control the RCX brick. For example, one acclaimed RCX project involves a Rubik's Cube solver that scans the faces of the cube, then rotates the cube until it is solved. This project actually uses an algorithm on the PC to analyze the cube faces and calculate a solution—a very memory-intensive operation. Once the solution is found it uploads the sequence of moves as an array to the RCX brick.

Of course, it is also possible for the RCX to send useful data back to the PC to be analyzed. Projects are often created using the RCX to monitor repetitive events, such as toilet flushes or the number of times a light has been turned on in a room. Light levels are also sometimes measured over long periods of time, especially for experiments in which it is necessary to see how much light a plant is taking in over time. Of course, mapping a location and sending the map coordinates back to the PC is a classic example of data collection, which is shown in this chapter.

There are also possibilities for telerobotics, the ability to control a robot from vast distances. Using the java.io package, commands to the RCX can be sent across any network, including the Internet. This opens up the possibility of controlling and monitoring experiments away from the lab. This chapter shows you how to control the RCX from any computer using Java data streams, as well as setting up a simple Web server to control a robot through a Web page using JavaScript.

Finally, it is also possible for two RCX bricks to communicate with each other using infrared signals. Communication between two RCX bricks is often used to make a "super RCX brick" with six inputs, six outputs, and 64 kB of memory. In this architecture, usually one brick is the controller brick, and the other merely takes commands for turning motors on and off or reading sensors. RCX robots can also be built to interact with each other, sending messages to achieve interesting "social" behavior. Communications truly opens up incredible possibilities for robotics.

The Communications API

Data flow is the lifeblood of computers, and leJOS allows communication on many levels: IR tower to RCX, RCX to RCX, and probably even IR tower to IR tower (although there isn't much practical use for this). In fact, leJOS can also receive data from the LEGO MINDSTORMS remote control (see Appendix A)—both to the RCX, or even to the IR tower to control your computer. All of these combinations can be handled with leJOS.

The leJOS Communications API can be found in the java.io, pc.irtower.comm, and josx.platform.rcx.comm packages. The communications classes use streams, just like the standard java.io package, so anyone familiar with streams will find it easy to use. The leJOS java.io package contains only the most basic streams relevant to sending and receiving data: InputStream, OutputStream, DataInputStream, and DataOutputStream. Input/Output Streams are the foundation of Streams, and they are only useful for sending bytes. If you want to send other data types such as characters, integers, and floating-point numbers, you will need to use data streams (see "DataInputStream" and "DataOutputStream" later).


InputStream is the superclass of all classes representing an input stream of bytes. It is an abstract class so it cannot be instantiated on its own. The main function of InputStream is to return the next byte of input from a data source. In leJOS an instance of InputStream can be obtained using DataPort.getInputStream() (see "PCDataPort" and "RCXDataPort" later).

  • public int read() throws IOException
    Reads the next byte of data from the input stream. The value byte is returned as an int in the range 0 to 255. This method blocks (waits) until input data is available, the end of the stream is detected, or an exception is thrown.

  • public int read(byte[] b) throws IOException
    Reads some number of bytes from the input stream and stores them in the buffer array b. The number of bytes actually read is returned as an integer. This method blocks until input data is available, the end of the file is detected, or an exception is thrown.



    The buffer into which the data is read.

  • public int read(byte[] b, int off, int len) throws IOException
    Reads up to len bytes of data from the input stream into an array of bytes. An attempt is made to read as many as len bytes, but a smaller number may be read, possibly zero. The number of bytes actually read is returned as an integer.



    The buffer into which the data is read.



    The start offset in array b at which the data is written.



    The maximum number of bytes to read.

  • public void close() throws IOException

    Closes this input stream, calls flush() and releases any system resources associated with the stream.


    In standard java.io.InputStream the methods mark() and reset() are used to jump back to a previous point in a stream. There are also methods for skip() and available(). The leJOS java.io.InputStream does not support any of these methods.


OutputStream is the superclass of all classes representing an output stream of bytes. It is an abstract class so it cannot be instantiated on its own. Its main function is to send a byte of data to a destination. Like InputStream, an instance of OutputStream can be obtained using DataPort.getOutput-Stream() (see "PCDataPort" and "RCXDataPort" later).

  • public void write(int b) throws IOException
    Writes the specified byte to this output stream. The general contract for write is that one byte is written to the output stream. The byte to be written is the eight low-order bits of the argument b. The 24 high-order bits of b are ignored.

  • public void write(byte b[]) throws IOException
    Writes b.length bytes from the specified byte array to this output stream. The general contract for write(b) is that it should have exactly the same effect as the call write(b, 0, b.length).



    The data.

  • public void write(byte b[], int off, int len) throws IOException
    Writes len bytes from the specified byte array starting at offset off to this output stream. The general contract for write(b, off, len) is that some of the bytes in the array b are written to the output stream in order; element b[off] is the first byte written and b[off+len-1] is the last byte written by this operation.



    The data.



    The start offset in the data.



    The maximum number of bytes to write.

  • public void flush() throws IOException
    Flushes this output stream and forces any buffered output bytes to be written out. The general contract of flush() is that calling it is an indication that, if any bytes previously written have been buffered by the implementation of the output stream, such bytes should immediately be written to their intended destination.


    Flush is one of the most important but often forgotten methods of streams. The nonuse of this method probably accounts for most bugs when using the java.io package. Don't forget to call flush() after sending data, otherwise the data may never be sent to the destination!

  • public void close() throws IOException

    Closes this output stream and releases any system resources associated with this stream. The general contract of close is that it closes the output stream. A closed stream cannot perform output operations and cannot be reopened. A call to flush() is made in this method as well.


DataInputStream extends InputStream, so it has all the methods of Input-Stream implemented (discussed earlier). This method allows data types other than bytes to be sent. This includes short, int, float, double, char, and boolean. Unlike the standard Sun java.io.DataInputStream class, the leJOS version does not include methods for receiving strings. If you wish to receive strings you can simply write code to read char values and assemble a new string. Also, to save memory the leJOS DataInputStream class does not extend FilterInputStream nor does it implement a DataInput interface.


The java.io classes are used on the PC side as well as on the RCX. The PC side uses standard Sun Java classes, but the RCX uses special java.io classes written specifically for the RCX. Both "brands" communicate fine with one another, however (i.e., the leJOS OutputStream can talk to the Sun InputStream and vice versa).

  • public DataInputStream(InputStream in)
    Returns an instance of DataInputStream. The constructor requires an InputStream object obtained using RCXDataPort.getInputStream().



    The input stream.

  • public final boolean readBoolean() throws IOException
    Used to send a Boolean value through a stream. Reads one input byte and returns true if that byte is nonzero, false if that byte is zero.

  • public final byte readByte() throws IOException
    Reads and returns one input byte. The byte is treated as a signed value in the range –128 through 127, inclusive.

  • public final short readShort() throws IOException
    Reads two input bytes and returns a short value.

  • public final char readChar() throws IOException
    Reads an input char and returns the char value (a Unicode char is made up of two bytes).

  • public final int readInt() throws IOException
    Reads four input bytes and returns an int value.

  • public final float readFloat() throws IOException
    Reads four input bytes and returns a float value.

  • public final double readDouble() throws IOException
    Reads eight input bytes and returns a double value.


If DataInputStream is the catcher then DataOutputStream is the pitcher. It encodes various data types into byte values and sends them across a data stream. DataOutputStream extends OutputStream, so it has all the methods described in the OutputStream API. Unlike the Sun DataOutputStream, DataOutputStream does not extend FilterOutputStream, nor does it implement DataOutput. It has most methods of the standard java.io.DataOutput-Stream, but excludes methods dealing with text data transfer.

  • public DataOutputStream(OutputStream out)
    Creates a new data output stream to write data to the specified underlying output stream.



    The output stream.

  • public final void writeBoolean(boolean v) throws IOException

    Writes a Boolean value to this output stream.



    A Boolean value.

  • public final void writeByte(int v) throws IOException
    Writes to the output stream the eight low-order bits of the argument v.



    A byte value.

  • public final void writeShort(int v) throws IOException
    Writes two bytes to the output stream to represent the value of the argument.



    A short value.

  • public final void writeChar(int v) throws IOException
    Writes a char value, which is comprised of two bytes, to the output stream.



    A char value.

  • public final void writeInt(int v) throws IOException
    Writes an int value, which is comprised of four bytes, to the output stream.



    An int value.

  • public final void writeFloat(float v) throws IOException
    Writes a float value, which is comprised of four bytes, to the output stream.



    A float value.

  • public final void writeDouble(double v) throws IOException
    Writes a double value, which is comprised of eight bytes, to the output stream.



    A double value.


DataPort is an abstract class at the top of the RCX communications hierarchy. A data port is a pretty general term, and can refer to a USB port, a serial port, or an RCX IR port. The DataPort class functions much like java.net.Socket in standard Java. These classes have in common the ability to hand out InputStream and OutputStream objects, which are absolutely vital for sending and receiving data in Java. Anyone familiar with Sockets should be comfortable using DataPort.

  • public InputStream getInputStream()
    Returns an input stream for this DataPort.

  • public OutputStream getOutputStream()
    Returns an output stream for this DataPort.


    You might wonder how this receives an InputStream or OutputStream object because these are abstract classes. The underlying returned classes are actually called RCXInputStream and RCXOutputStream, which are protected inner classes of DataPort.

  • public void close()
    Closes this DataPort.

  • public void setTimeOut(int timeOut)
    The timeOut value represents the amount of time the DataPort will keep trying to exchange data. If it fails to receive a response from the target it will keep trying for this number of milliseconds. (The value is 0 by default, meaning it will keep trying forever.)



    The number of milliseconds to keep trying if data communication fails.

  • public int getTimeOut()
    Returns the current timeout value for this DataPort.


PCDataPort extends the DataPort abstract class and implements all abstract methods. The main purpose of this class is to provide an InputStream or Out-putStream on the PC side to communicate through the IR tower. This class cannot and should not be used in any code intended for the RCX brick. To use this code in your regular Java code, simply import the pc.irtower.comm package (or import just the PCDataPort class).

Communication with the IR tower is complicated by the fact that the IR tower can only receive data while the green LED is on. If an RCX brick is sitting in front of the IR tower and it starts sending data, the IR tower does not detect this. It sits there, unpowered, until the PC side sends data. In other words, the PC must initiate all data transfers. The leJOS API deals with this problem, however, so it is almost invisible for a programmer:

  • public PCDataPort(String port) throws IOException
    Returns an instance of PCDataPort.



    A string describing the port to use. Accepts a value from COM1 to COM4 or USB (case does not matter).

  • public InputStream getInputStream()
    Returns an input stream for this DataPort.

  • public OutputStream getOutputStream()
    Returns an output stream for this DataPort.


RCXData port allows data to be sent from the RCX IR port to another source and vice versa. This class is very easy to use, and the only methods of importance come from extending DataPort—getInputStream() and getOutput-Stream():

  • public RCXDataPort()
    Returns an instance of RCXDataPort.

  • public InputStream getInputStream()
    Returns an input stream for this DataPort.

  • public OutputStream getOutputStream()
    Returns an output stream for this DataPort.


    There are plans to implement a java.net package for leJOS so the RCX brick could communicate through IP addresses directly to the Internet. (This will require a small server class on the PC side.)


There is nothing special to do to use the leJOS Communications API with the RCX, but the PC side must have access to special classes to work. Currently the leJOS Communications API depends on the JavaComm API to work. This is needed because different platforms use different forms of communicating with ports, so a platform-independent solution is needed.


By the time this book hits the shelves installation of the Javacomm API may be unnecessary. There are plans to include Java Native Interface (JNI) communications within leJOS, eliminating the need for Javacomm installation. Check with the leJOS readme file first for installation notes.


  1. Download the Windows version of JavaComm 2.0 from Sun at java.sun.com/products/javacomm/.

  2. Extract the zipped file to any directory.

  3. Copy Win32comm.dll to the bin directory of your JDK (e.g., C:\jdk1.3.1\bin).

  4. Copy comm.jar to the lib directory of your JDK (e.g., C:\jdk1.3.1\lib).

  5. Copy javax.comm.properties to the lib directory of your JDK (e.g., C:\jdk1.3.1\lib).

  6. Add the comm.jar file to the CLASSPATH system variable (e.g., set CLASSPATH=c:\jdk1.1.6\lib\comm.jar).


  1. Download the Solaris CommAPI release at java.sun.com/products/ javacomm.

  2. Copy comm.jar into your JDK bin directory.

  3. Add this JAR file to your CLASSPATH (e.g., export CLASS-PATH=$CLASSPATH:/usr/local/jdk1.1.5/bin/comm.jar).

  4. Download and build RXTX at http://www.rxtx.org

  5. Add the RXTX directory to your CLASSPATH as instructed in the RXTX documentation.

  6. Create a text file in your JDK lib directory. This file must be named javax.comm.properties. The contents of this file is a single line that should read:

  7. You can test your installation by running the BlackBox demo included with CommAPI: java -classpath BlackBox.jar:$CLASSPATH BlackBox

IDE Setup

If you plan on using an IDE (such as JCreator) to program your PC side programs, then it is necessary to include some settings in the IDE. JCreator automatically overrides the system CLASSPATH settings when compiling and running Java programs (it does not override these settings for the leJOS tools, however). For this reason we must add the settings to JCreator.

  1. In JCreator, select Project Project Settings and click the Required Libraries tab (Figure 11–1).

    Figure 11-1 Project settings dialog box.

  2. Click New to add a new CLASSPATH setting and a dialog box appears (Figure 11–2). Type in leJOS Comm as the name. Click Add Add Package, and browse to the leJOS classes.jar file (e.g., C:\lejos\lib\classes.jar). Click OK when done.

    Figure 11-2 Adding leJOS to the CLASSPATH.

  3. Now add the Javacomm CLASSPATH setting. Click New and type Javacomm as the name (Figure 11–3). Click Add Add Package, and browse to the comm.jar file (e.g., C:\jdk1.3.1\lib\comm.jar). Click OK when done.

    Figure 11-3 Adding Javacomm to the CLASSPATH

  4. Select the check boxes next to the two settings (Figure 11–4). That's it! You can now use the Compile File and Execute File buttons on the toolbar for PC Java programs using leJOS Comm.

    Figure 11-4 Activating the CLASSPATH setting for the project.

InformIT Promotional Mailings & Special Offers

I would like to receive exclusive offers and hear about products from InformIT and its family of brands. I can unsubscribe at any time.


Pearson Education, Inc., 221 River Street, Hoboken, New Jersey 07030, (Pearson) presents this site to provide information about products and services that can be purchased through this site.

This privacy notice provides an overview of our commitment to privacy and describes how we collect, protect, use and share personal information collected through this site. Please note that other Pearson websites and online products and services have their own separate privacy policies.

Collection and Use of Information

To conduct business and deliver products and services, Pearson collects and uses personal information in several ways in connection with this site, including:

Questions and Inquiries

For inquiries and questions, we collect the inquiry or question, together with name, contact details (email address, phone number and mailing address) and any other additional information voluntarily submitted to us through a Contact Us form or an email. We use this information to address the inquiry and respond to the question.

Online Store

For orders and purchases placed through our online store on this site, we collect order details, name, institution name and address (if applicable), email address, phone number, shipping and billing addresses, credit/debit card information, shipping options and any instructions. We use this information to complete transactions, fulfill orders, communicate with individuals placing orders or visiting the online store, and for related purposes.


Pearson may offer opportunities to provide feedback or participate in surveys, including surveys evaluating Pearson products, services or sites. Participation is voluntary. Pearson collects information requested in the survey questions and uses the information to evaluate, support, maintain and improve products, services or sites, develop new products and services, conduct educational research and for other purposes specified in the survey.

Contests and Drawings

Occasionally, we may sponsor a contest or drawing. Participation is optional. Pearson collects name, contact information and other information specified on the entry form for the contest or drawing to conduct the contest or drawing. Pearson may collect additional personal information from the winners of a contest or drawing in order to award the prize and for tax reporting purposes, as required by law.


If you have elected to receive email newsletters or promotional mailings and special offers but want to unsubscribe, simply email information@informit.com.

Service Announcements

On rare occasions it is necessary to send out a strictly service related announcement. For instance, if our service is temporarily suspended for maintenance we might send users an email. Generally, users may not opt-out of these communications, though they can deactivate their account information. However, these communications are not promotional in nature.

Customer Service

We communicate with users on a regular basis to provide requested services and in regard to issues relating to their account we reply via email or phone in accordance with the users' wishes when a user submits their information through our Contact Us form.

Other Collection and Use of Information

Application and System Logs

Pearson automatically collects log data to help ensure the delivery, availability and security of this site. Log data may include technical information about how a user or visitor connected to this site, such as browser type, type of computer/device, operating system, internet service provider and IP address. We use this information for support purposes and to monitor the health of the site, identify problems, improve service, detect unauthorized access and fraudulent activity, prevent and respond to security incidents and appropriately scale computing resources.

Web Analytics

Pearson may use third party web trend analytical services, including Google Analytics, to collect visitor information, such as IP addresses, browser types, referring pages, pages visited and time spent on a particular site. While these analytical services collect and report information on an anonymous basis, they may use cookies to gather web trend information. The information gathered may enable Pearson (but not the third party web trend services) to link information with application and system log data. Pearson uses this information for system administration and to identify problems, improve service, detect unauthorized access and fraudulent activity, prevent and respond to security incidents, appropriately scale computing resources and otherwise support and deliver this site and its services.

Cookies and Related Technologies

This site uses cookies and similar technologies to personalize content, measure traffic patterns, control security, track use and access of information on this site, and provide interest-based messages and advertising. Users can manage and block the use of cookies through their browser. Disabling or blocking certain cookies may limit the functionality of this site.

Do Not Track

This site currently does not respond to Do Not Track signals.


Pearson uses appropriate physical, administrative and technical security measures to protect personal information from unauthorized access, use and disclosure.


This site is not directed to children under the age of 13.


Pearson may send or direct marketing communications to users, provided that

  • Pearson will not use personal information collected or processed as a K-12 school service provider for the purpose of directed or targeted advertising.
  • Such marketing is consistent with applicable law and Pearson's legal obligations.
  • Pearson will not knowingly direct or send marketing communications to an individual who has expressed a preference not to receive marketing.
  • Where required by applicable law, express or implied consent to marketing exists and has not been withdrawn.

Pearson may provide personal information to a third party service provider on a restricted basis to provide marketing solely on behalf of Pearson or an affiliate or customer for whom Pearson is a service provider. Marketing preferences may be changed at any time.

Correcting/Updating Personal Information

If a user's personally identifiable information changes (such as your postal address or email address), we provide a way to correct or update that user's personal data provided to us. This can be done on the Account page. If a user no longer desires our service and desires to delete his or her account, please contact us at customer-service@informit.com and we will process the deletion of a user's account.


Users can always make an informed choice as to whether they should proceed with certain services offered by InformIT. If you choose to remove yourself from our mailing list(s) simply visit the following page and uncheck any communication you no longer want to receive: www.informit.com/u.aspx.

Sale of Personal Information

Pearson does not rent or sell personal information in exchange for any payment of money.

While Pearson does not sell personal information, as defined in Nevada law, Nevada residents may email a request for no sale of their personal information to NevadaDesignatedRequest@pearson.com.

Supplemental Privacy Statement for California Residents

California residents should read our Supplemental privacy statement for California residents in conjunction with this Privacy Notice. The Supplemental privacy statement for California residents explains Pearson's commitment to comply with California law and applies to personal information of California residents collected in connection with this site and the Services.

Sharing and Disclosure

Pearson may disclose personal information, as follows:

  • As required by law.
  • With the consent of the individual (or their parent, if the individual is a minor)
  • In response to a subpoena, court order or legal process, to the extent permitted or required by law
  • To protect the security and safety of individuals, data, assets and systems, consistent with applicable law
  • In connection the sale, joint venture or other transfer of some or all of its company or assets, subject to the provisions of this Privacy Notice
  • To investigate or address actual or suspected fraud or other illegal activities
  • To exercise its legal rights, including enforcement of the Terms of Use for this site or another contract
  • To affiliated Pearson companies and other companies and organizations who perform work for Pearson and are obligated to protect the privacy of personal information consistent with this Privacy Notice
  • To a school, organization, company or government agency, where Pearson collects or processes the personal information in a school setting or on behalf of such organization, company or government agency.


This web site contains links to other sites. Please be aware that we are not responsible for the privacy practices of such other sites. We encourage our users to be aware when they leave our site and to read the privacy statements of each and every web site that collects Personal Information. This privacy statement applies solely to information collected by this web site.

Requests and Contact

Please contact us about this Privacy Notice or if you have any requests or questions relating to the privacy of your personal information.

Changes to this Privacy Notice

We may revise this Privacy Notice through an updated posting. We will identify the effective date of the revision in the posting. Often, updates are made to provide greater clarity or to comply with changes in regulatory requirements. If the updates involve material changes to the collection, protection, use or disclosure of Personal Information, Pearson will provide notice of the change through a conspicuous notice on this site or other appropriate way. Continued use of the site after the effective date of a posted revision evidences acceptance. Please contact us if you have questions or concerns about the Privacy Notice or any objection to any revisions.

Last Update: November 17, 2020