Today I worked on making my NXT communicate with my laptop over Bluetooth. This is great because you can untether your projects and control your robots programmatically.
- Set up the NXT Bluetooth with your mac as shown here, http://tonybuser.com/bluetooth-serial-port-to-nxt-in-osx
- Open a terminal and type: screen /dev/tty.NXT-DevB
- Start the sample code listed below in RobotC.
- In the mac terminal, type ‘S’ and verify that it is echo’d back to the terminal and a start message displayed on the NXT Brick LCD.
See the code for explanation of how to set up the motors and control them remotely.
Sample code is as follows, it is shameless stolen from the RobotC sample code BT Lowlevel.c:
<span class="Apple-style-span" style="font-size: 16px; color: #444444; font-family: Georgia, 'Bitstream Charter', serif; line-height: 24px; white-space: normal;">////////////////////////////////////////////////////////////////////////////////////////////////////////</span> // // Simple Bluetooth "Echo" Terminal Server // // The NXT Bluecore module supports connects using the SPP (Serial Port Profile) defined in the Bluetooth // protocol specifications. There may be occasion when it is desirable to connect the NXT to another // Bluetooth device in a "raw" format where the end user application program has direct control over // every byte transmitted and received via the Bluecore module. For example, connecting to a BT enabled // GPS receiver or connecting to a BT enabled cell phone or PDA. // // This sample program contains a short program demonstrating raw access to the Bluetooth data stream. // // NOTE: Normally the data transmission uses a higher level protocol that LEGO has defined for sending // messages back and forth between NXT devices. This protocol is bypassed by this programs. // // There are only three functions and one variable that are needed to operate the NXT Blucecore in "raw" // // setBluetoothRawDataMode() This function initiates Bluecore module to switch to "raw" mode. // // bBTRawMode Read only boolean variable that can be tested to confirm when Blucore // has entered "raw" mode. // // nxtReadRawBluetooth(pData, nMaxBufferSize) // Reads one or more "raw" bytes from Bluecore. Returned value is the // number of bytes read. // // nxtWriteRawBluetooth(pData, nLength) // Writes 'nLength' bytes in raw mode from buffer 'pData' // //////////////////////////////////////////////////////////////////////////////////////////////////////// #pragma platform(NXT) short nMsgXmit = 0; short nLastCharReceived = 0; const int kPacketSize = 8; // Number of hex digits that can be displayed on one line // // Function and task prototypes // void checkBTLinkConnected(); //////////////////////////////////////////////////////////////////////////////////////////////////////// // // Main Task // //////////////////////////////////////////////////////////////////////////////////////////////////////// task main() { const int kSendSize = 1; static ubyte BytesToSend[kSendSize]; int nNumbBytesRead; const int kHexDigitsPerLine = 1; int nIndex = 0; ubyte BytesRead[kHexDigitsPerLine]; // Circular buffer of last bytes read. // // Test Ability to Turn Bluetooth On or Off // checkBTLinkConnected(); // // Initialize Bluecore to "raw data" mode. This will be automatically reset when application terminates // setBluetoothRawDataMode(); while (!bBTRawMode) { // Wait for Bluecore to enter raw data mode wait1Msec(1); } // // Start separate tasks to read and write raw data over BT. The link operates in full-duplex mode. // eraseDisplay(); bNxtLCDStatusDisplay = true; // Enable top status line display //StartTask(sendRawData); //StartTask(readRawData); while (true) { // // Display progress results on the NXT LCD screen. // //nxtDisplayBigStringAt(0, 31, "Xmit Rcv"); //nxtDisplayBigStringAt(0, 15, " %02X %02X", nMsgXmit, nLastCharReceived & 0x00FF); // // Loop continuously, reading one byte at a time. The interface will support larger reads. // nNumbBytesRead = nxtReadRawBluetooth(BytesRead[nIndex], 1); if (nNumbBytesRead == 0) { wait1Msec(10); continue; } else if (nNumbBytesRead == 1 && BytesRead[0] == 'S') { nxtDisplayString(1, "Received Start"); } else if (nNumbBytesRead == 1 && BytesRead[0] == 'w') { nxtDisplayString(4, "Forward Signal"); motor[motorA] = 25; motor[motorB] = 25; } else if (nNumbBytesRead == 1 && BytesRead[0] == 's') { nxtDisplayString(4, "Backward Signal"); motor[motorA] = -25; motor[motorB] = -25; } else if (nNumbBytesRead == 1 && BytesRead[0] == 'd') { nxtDisplayString(4, "Right Turn Signal"); motor[motorA] = 25; motor[motorB] = -25; } else if (nNumbBytesRead == 1 && BytesRead[0] == 'a') { nxtDisplayString(4, "Left Turn Signal"); motor[motorA] = -25; motor[motorB] = 25; } else if (nNumbBytesRead == 1 && BytesRead[0] == 'z') { nxtDisplayString(4, "ALL STOP Signal"); motor[motorA] = 0; motor[motorB] = 0; } memset(BytesToSend, BytesRead[nIndex], sizeof(BytesToSend)); nxtWriteRawBluetooth(BytesToSend, sizeof(BytesToSend)); } return; } //////////////////////////////////////////////////////////////////////////////////////////////////////// // // checkBTLinkConnected // // Utility function to check whether Bluetooth link is set up. It should be manually set up before // launching this program. [You can also set it up within an application program; there's a separate // sample program for this. // //////////////////////////////////////////////////////////////////////////////////////////////////////// void checkBTLinkConnected() { if (nBTCurrentStreamIndex >= 0) return; // An existing Bluetooth connection is present. // // Not connected. Audible notification and LCD error display // PlaySound(soundLowBuzz); PlaySound(soundLowBuzz); eraseDisplay(); nxtDisplayCenteredTextLine(3, "BT not"); nxtDisplayCenteredTextLine(4, "Connected"); wait1Msec(3000); StopAllTasks(); }