Changeset 80
- Timestamp:
- 05/09/10 10:00:01 (2 years ago)
- Location:
- trunk/arduino/libraries
- Files:
-
- 19 modified
-
Ethernet/Client.cpp (modified) (1 diff)
-
Firmata/Firmata.cpp (modified) (14 diffs)
-
Firmata/Firmata.h (modified) (10 diffs)
-
Firmata/examples/AnalogFirmata/AnalogFirmata.pde (modified) (1 diff)
-
Firmata/examples/EchoString/EchoString.pde (modified) (1 diff)
-
Firmata/examples/ServoFirmata/ServoFirmata.pde (modified) (1 diff)
-
Firmata/examples/SimpleAnalogFirmata/SimpleAnalogFirmata.pde (modified) (1 diff)
-
Firmata/examples/SimpleDigitalFirmata/SimpleDigitalFirmata.pde (modified) (2 diffs)
-
Firmata/examples/StandardFirmata/Makefile (modified) (5 diffs)
-
Firmata/examples/StandardFirmata/StandardFirmata.pde (modified) (7 diffs)
-
LiquidCrystal/LiquidCrystal.cpp (modified) (2 diffs)
-
LiquidCrystal/LiquidCrystal.h (modified) (1 diff)
-
LiquidCrystal/examples/HelloWorld/HelloWorld.pde (modified) (1 diff)
-
LiquidCrystal/examples/SerialDisplay/SerialDisplay.pde (modified) (1 diff)
-
LiquidCrystal/keywords.txt (modified) (1 diff)
-
Servo/Servo.cpp (modified) (1 diff)
-
Servo/Servo.h (modified) (2 diffs)
-
Servo/keywords.txt (modified) (1 diff)
-
Wire/utility/twi.c (modified) (5 diffs)
Legend:
- Unmodified
- Added
- Removed
-
trunk/arduino/libraries/Ethernet/Client.cpp
r46 r80 114 114 115 115 uint8_t Client::connected() { 116 uint8_t s = status(); 117 return !(s == SOCK_LISTEN || s == SOCK_CLOSED || s == SOCK_FIN_WAIT || 118 (s == SOCK_CLOSE_WAIT && !available())); 116 if (_sock == 255) { 117 return 0; 118 } else { 119 uint8_t s = status(); 120 return !(s == SOCK_LISTEN || s == SOCK_CLOSED || s == SOCK_FIN_WAIT || 121 (s == SOCK_CLOSE_WAIT && !available())); 122 } 119 123 } 120 124 121 125 uint8_t Client::status() { 122 return getSn_SR(_sock); 126 if (_sock == 255) { 127 return SOCK_CLOSED; 128 } else { 129 return getSn_SR(_sock); 130 } 123 131 } 124 132 -
trunk/arduino/libraries/Firmata/Firmata.cpp
r46 r80 30 30 void sendValueAsTwo7bitBytes(int value) 31 31 { 32 Serial.print(value & B01111111, BYTE); // LSB33 Serial.print(value >> 7 & B01111111, BYTE); // MSB32 Serial.print(value & B01111111, BYTE); // LSB 33 Serial.print(value >> 7 & B01111111, BYTE); // MSB 34 34 } 35 35 36 36 void startSysex(void) 37 37 { 38 Serial.print(START_SYSEX, BYTE);38 Serial.print(START_SYSEX, BYTE); 39 39 } 40 40 41 41 void endSysex(void) 42 42 { 43 Serial.print(END_SYSEX, BYTE);43 Serial.print(END_SYSEX, BYTE); 44 44 } 45 45 … … 50 50 FirmataClass::FirmataClass(void) 51 51 { 52 firmwareVersionCount = 0;53 systemReset();52 firmwareVersionCount = 0; 53 systemReset(); 54 54 } 55 55 … … 61 61 void FirmataClass::begin(void) 62 62 { 63 Serial.begin(115200); 64 blinkVersion(); 65 delay(300); 66 printVersion(); 63 begin(57600); 67 64 } 68 65 … … 70 67 void FirmataClass::begin(long speed) 71 68 { 72 blinkVersion();73 69 #if defined(__AVR_ATmega128__) // Wiring 74 Serial.begin((uint32_t)speed);70 Serial.begin((uint32_t)speed); 75 71 #else 76 Serial.begin(speed);72 Serial.begin(speed); 77 73 #endif 78 delay(300); 79 printVersion(); 80 printFirmwareVersion(); 74 blinkVersion(); 75 delay(300); 76 printVersion(); 77 printFirmwareVersion(); 81 78 } 82 79 83 80 // output the protocol version message to the serial port 84 81 void FirmataClass::printVersion(void) { 85 Serial.print(REPORT_VERSION, BYTE);86 Serial.print(FIRMATA_MAJOR_VERSION, BYTE);87 Serial.print(FIRMATA_MINOR_VERSION, BYTE);82 Serial.print(REPORT_VERSION, BYTE); 83 Serial.print(FIRMATA_MAJOR_VERSION, BYTE); 84 Serial.print(FIRMATA_MINOR_VERSION, BYTE); 88 85 } 89 86 90 87 void FirmataClass::blinkVersion(void) 91 88 { 92 // flash the pin with the protocol version93 pinMode(VERSION_BLINK_PIN,OUTPUT);94 pin13strobe(FIRMATA_MAJOR_VERSION, 200, 400);95 delay(300);96 pin13strobe(2,1,4); // separator, a quick burst97 delay(300);98 pin13strobe(FIRMATA_MINOR_VERSION, 200, 400);89 // flash the pin with the protocol version 90 pinMode(VERSION_BLINK_PIN,OUTPUT); 91 pin13strobe(FIRMATA_MAJOR_VERSION, 200, 400); 92 delay(300); 93 pin13strobe(2,1,4); // separator, a quick burst 94 delay(300); 95 pin13strobe(FIRMATA_MINOR_VERSION, 200, 400); 99 96 } 100 97 101 98 void FirmataClass::printFirmwareVersion(void) 102 99 { 103 byte i; 104 105 if(firmwareVersionCount) { // make sure that the name has been set before reporting 106 startSysex(); 107 Serial.print(REPORT_FIRMWARE, BYTE); 108 Serial.print(firmwareVersionVector[0]); // major version number 109 Serial.print(firmwareVersionVector[1]); // minor version number 110 for(i=2; i<firmwareVersionCount; ++i) { 111 sendValueAsTwo7bitBytes(firmwareVersionVector[i]); 112 } 113 endSysex(); 100 byte i; 101 102 if(firmwareVersionCount) { // make sure that the name has been set before reporting 103 startSysex(); 104 Serial.print(REPORT_FIRMWARE, BYTE); 105 Serial.print(firmwareVersionVector[0]); // major version number 106 Serial.print(firmwareVersionVector[1]); // minor version number 107 for(i=2; i<firmwareVersionCount; ++i) { 108 sendValueAsTwo7bitBytes(firmwareVersionVector[i]); 114 109 } 110 endSysex(); 111 } 115 112 } 116 113 117 114 void FirmataClass::setFirmwareNameAndVersion(const char *name, byte major, byte minor) 118 115 { 119 const char *filename;120 char *extension;121 122 // parse out ".cpp" and "applet/" that comes from using __FILE__123 extension = strstr(name, ".cpp");124 filename = strrchr(name, '/') + 1; //points to slash, +1 gets to start of filename125 // add two bytes for version numbers126 if(extension && filename) {127 firmwareVersionCount = extension - filename + 2;128 } else {129 firmwareVersionCount = strlen(name) + 2;130 filename = name;131 }132 firmwareVersionVector = (byte *) malloc(firmwareVersionCount);133 firmwareVersionVector[firmwareVersionCount] = 0;134 firmwareVersionVector[0] = major;135 firmwareVersionVector[1] = minor;136 strncpy((char*)firmwareVersionVector + 2, filename, firmwareVersionCount - 2);137 // alas, no snprintf on Arduino138 // snprintf(firmwareVersionVector, MAX_DATA_BYTES, "%c%c%s",139 // (char)major, (char)minor, firmwareVersionVector);116 const char *filename; 117 char *extension; 118 119 // parse out ".cpp" and "applet/" that comes from using __FILE__ 120 extension = strstr(name, ".cpp"); 121 filename = strrchr(name, '/') + 1; //points to slash, +1 gets to start of filename 122 // add two bytes for version numbers 123 if(extension && filename) { 124 firmwareVersionCount = extension - filename + 2; 125 } else { 126 firmwareVersionCount = strlen(name) + 2; 127 filename = name; 128 } 129 firmwareVersionVector = (byte *) malloc(firmwareVersionCount); 130 firmwareVersionVector[firmwareVersionCount] = 0; 131 firmwareVersionVector[0] = major; 132 firmwareVersionVector[1] = minor; 133 strncpy((char*)firmwareVersionVector + 2, filename, firmwareVersionCount - 2); 134 // alas, no snprintf on Arduino 135 // snprintf(firmwareVersionVector, MAX_DATA_BYTES, "%c%c%s", 136 // (char)major, (char)minor, firmwareVersionVector); 140 137 } 141 138 … … 145 142 int FirmataClass::available(void) 146 143 { 147 return Serial.available();144 return Serial.available(); 148 145 } 149 146 … … 151 148 void FirmataClass::processSysexMessage(void) 152 149 { 153 switch(storedInputData[0]) { //first byte in buffer is command 154 case REPORT_FIRMWARE: 155 printFirmwareVersion(); 156 break; 157 case FIRMATA_STRING: 158 if(currentStringCallback) { 159 byte bufferLength = (sysexBytesRead - 1) / 2; 160 char *buffer = (char*)malloc(bufferLength * sizeof(char)); 161 byte i = 1; 162 byte j = 0; 163 while(j < bufferLength) { 164 buffer[j] = (char)storedInputData[i]; 165 i++; 166 buffer[j] += (char)(storedInputData[i] << 7); 167 i++; 168 j++; 169 } 170 (*currentStringCallback)(buffer); 150 switch(storedInputData[0]) { //first byte in buffer is command 151 case REPORT_FIRMWARE: 152 printFirmwareVersion(); 153 break; 154 case STRING_DATA: 155 if(currentStringCallback) { 156 byte bufferLength = (sysexBytesRead - 1) / 2; 157 char *buffer = (char*)malloc(bufferLength * sizeof(char)); 158 byte i = 1; 159 byte j = 0; 160 while(j < bufferLength) { 161 buffer[j] = (char)storedInputData[i]; 162 i++; 163 buffer[j] += (char)(storedInputData[i] << 7); 164 i++; 165 j++; 166 } 167 (*currentStringCallback)(buffer); 168 } 169 break; 170 default: 171 if(currentSysexCallback) 172 (*currentSysexCallback)(storedInputData[0], sysexBytesRead - 1, storedInputData + 1); 173 } 174 } 175 176 void FirmataClass::processInput(void) 177 { 178 int inputData = Serial.read(); // this is 'int' to handle -1 when no data 179 int command; 180 181 // TODO make sure it handles -1 properly 182 183 if (parsingSysex) { 184 if(inputData == END_SYSEX) { 185 //stop sysex byte 186 parsingSysex = false; 187 //fire off handler function 188 processSysexMessage(); 189 } else { 190 //normal data byte - add to buffer 191 storedInputData[sysexBytesRead] = inputData; 192 sysexBytesRead++; 193 } 194 } else if( (waitForData > 0) && (inputData < 128) ) { 195 waitForData--; 196 storedInputData[waitForData] = inputData; 197 if( (waitForData==0) && executeMultiByteCommand ) { // got the whole message 198 switch(executeMultiByteCommand) { 199 case ANALOG_MESSAGE: 200 if(currentAnalogCallback) { 201 (*currentAnalogCallback)(multiByteChannel, 202 (storedInputData[0] << 7) 203 + storedInputData[1]); 171 204 } 172 205 break; 173 default: 174 if(currentSysexCallback) 175 (*currentSysexCallback)(storedInputData[0], sysexBytesRead - 1, storedInputData + 1); 206 case DIGITAL_MESSAGE: 207 if(currentDigitalCallback) { 208 (*currentDigitalCallback)(multiByteChannel, 209 (storedInputData[0] << 7) 210 + storedInputData[1]); 211 } 212 break; 213 case SET_PIN_MODE: 214 if(currentPinModeCallback) 215 (*currentPinModeCallback)(storedInputData[1], storedInputData[0]); 216 break; 217 case REPORT_ANALOG: 218 if(currentReportAnalogCallback) 219 (*currentReportAnalogCallback)(multiByteChannel,storedInputData[0]); 220 break; 221 case REPORT_DIGITAL: 222 if(currentReportDigitalCallback) 223 (*currentReportDigitalCallback)(multiByteChannel,storedInputData[0]); 224 break; 225 } 226 executeMultiByteCommand = 0; 227 } 228 } else { 229 // remove channel info from command byte if less than 0xF0 230 if(inputData < 0xF0) { 231 command = inputData & 0xF0; 232 multiByteChannel = inputData & 0x0F; 233 } else { 234 command = inputData; 235 // commands in the 0xF* range don't use channel data 176 236 } 177 } 178 179 void FirmataClass::processInput(void) 180 { 181 int inputData = Serial.read(); // this is 'int' to handle -1 when no data 182 int command; 183 184 // TODO make sure it handles -1 properly 185 186 if (parsingSysex) { 187 if(inputData == END_SYSEX) { 188 //stop sysex byte 189 parsingSysex = false; 190 //fire off handler function 191 processSysexMessage(); 192 } else { 193 //normal data byte - add to buffer 194 storedInputData[sysexBytesRead] = inputData; 195 sysexBytesRead++; 196 } 197 } else if( (waitForData > 0) && (inputData < 128) ) { 198 waitForData--; 199 storedInputData[waitForData] = inputData; 200 if( (waitForData==0) && executeMultiByteCommand ) { // got the whole message 201 switch(executeMultiByteCommand) { 202 case ANALOG_MESSAGE: 203 if(currentAnalogCallback) { 204 (*currentAnalogCallback)(multiByteChannel, 205 (storedInputData[0] << 7) 206 + storedInputData[1]); 207 } 208 break; 209 case DIGITAL_MESSAGE: 210 if(currentDigitalCallback) { 211 (*currentDigitalCallback)(multiByteChannel, 212 (storedInputData[0] << 7) 213 + storedInputData[1]); 214 } 215 break; 216 case SET_PIN_MODE: 217 if(currentPinModeCallback) 218 (*currentPinModeCallback)(storedInputData[1], storedInputData[0]); 219 break; 220 case REPORT_ANALOG: 221 if(currentReportAnalogCallback) 222 (*currentReportAnalogCallback)(multiByteChannel,storedInputData[0]); 223 break; 224 case REPORT_DIGITAL: 225 if(currentReportDigitalCallback) 226 (*currentReportDigitalCallback)(multiByteChannel,storedInputData[0]); 227 break; 228 } 229 executeMultiByteCommand = 0; 230 } 231 } else { 232 // remove channel info from command byte if less than 0xF0 233 if(inputData < 0xF0) { 234 command = inputData & 0xF0; 235 multiByteChannel = inputData & 0x0F; 236 } else { 237 command = inputData; 238 // commands in the 0xF* range don't use channel data 239 } 240 switch (command) { 241 case ANALOG_MESSAGE: 242 case DIGITAL_MESSAGE: 243 case SET_PIN_MODE: 244 waitForData = 2; // two data bytes needed 245 executeMultiByteCommand = command; 246 break; 247 case REPORT_ANALOG: 248 case REPORT_DIGITAL: 249 waitForData = 1; // two data bytes needed 250 executeMultiByteCommand = command; 251 break; 252 case START_SYSEX: 253 parsingSysex = true; 254 sysexBytesRead = 0; 255 break; 256 case SYSTEM_RESET: 257 systemReset(); 258 break; 259 case REPORT_VERSION: 260 Firmata.printVersion(); 261 break; 262 } 237 switch (command) { 238 case ANALOG_MESSAGE: 239 case DIGITAL_MESSAGE: 240 case SET_PIN_MODE: 241 waitForData = 2; // two data bytes needed 242 executeMultiByteCommand = command; 243 break; 244 case REPORT_ANALOG: 245 case REPORT_DIGITAL: 246 waitForData = 1; // two data bytes needed 247 executeMultiByteCommand = command; 248 break; 249 case START_SYSEX: 250 parsingSysex = true; 251 sysexBytesRead = 0; 252 break; 253 case SYSTEM_RESET: 254 systemReset(); 255 break; 256 case REPORT_VERSION: 257 Firmata.printVersion(); 258 break; 263 259 } 260 } 264 261 } 265 262 … … 270 267 void FirmataClass::sendAnalog(byte pin, int value) 271 268 { 272 // pin can only be 0-15, so chop higher bits273 Serial.print(ANALOG_MESSAGE | (pin & 0xF), BYTE);274 sendValueAsTwo7bitBytes(value);269 // pin can only be 0-15, so chop higher bits 270 Serial.print(ANALOG_MESSAGE | (pin & 0xF), BYTE); 271 sendValueAsTwo7bitBytes(value); 275 272 } 276 273 … … 278 275 void FirmataClass::sendDigital(byte pin, int value) 279 276 { 280 /* TODO add single pin digital messages to the protocol, this needs to281 * track the last digital data sent so that it can be sure to change just282 * one bit in the packet. This is complicated by the fact that the283 * numbering of the pins will probably differ on Arduino, Wiring, and284 * other boards. The DIGITAL_MESSAGE sends 14 bits at a time, but it is285 * probably easier to send 8 bit ports for any board with more than 14286 * digital pins.287 */288 289 // TODO: the digital message should not be sent on the serial port every290 // time sendDigital() is called. Instead, it should add it to an int291 // which will be sent on a schedule. If a pin changes more than once292 // before the digital message is sent on the serial port, it should send a293 // digital message for each change.294 295 // if(value == 0)296 // sendDigitalPortPair();277 /* TODO add single pin digital messages to the protocol, this needs to 278 * track the last digital data sent so that it can be sure to change just 279 * one bit in the packet. This is complicated by the fact that the 280 * numbering of the pins will probably differ on Arduino, Wiring, and 281 * other boards. The DIGITAL_MESSAGE sends 14 bits at a time, but it is 282 * probably easier to send 8 bit ports for any board with more than 14 283 * digital pins. 284 */ 285 286 // TODO: the digital message should not be sent on the serial port every 287 // time sendDigital() is called. Instead, it should add it to an int 288 // which will be sent on a schedule. If a pin changes more than once 289 // before the digital message is sent on the serial port, it should send a 290 // digital message for each change. 291 292 // if(value == 0) 293 // sendDigitalPortPair(); 297 294 } 298 295 … … 302 299 void FirmataClass::sendDigitalPort(byte portNumber, int portData) 303 300 { 304 Serial.print(DIGITAL_MESSAGE | (portNumber & 0xF),BYTE);305 Serial.print(portData % 128, BYTE); // Tx bits 0-6306 Serial.print(portData >> 7, BYTE); // Tx bits 7-13301 Serial.print(DIGITAL_MESSAGE | (portNumber & 0xF),BYTE); 302 Serial.print((byte)portData % 128, BYTE); // Tx bits 0-6 303 Serial.print(portData >> 7, BYTE); // Tx bits 7-13 307 304 } 308 305 … … 310 307 void FirmataClass::sendSysex(byte command, byte bytec, byte* bytev) 311 308 { 312 byte i;313 startSysex();314 Serial.print(command, BYTE);315 for(i=0; i<bytec; i++) {316 sendValueAsTwo7bitBytes(bytev[i]);317 }318 endSysex();309 byte i; 310 startSysex(); 311 Serial.print(command, BYTE); 312 for(i=0; i<bytec; i++) { 313 sendValueAsTwo7bitBytes(bytev[i]); 314 } 315 endSysex(); 319 316 } 320 317 321 318 void FirmataClass::sendString(byte command, const char* string) 322 319 { 323 sendSysex(command, strlen(string), (byte *)string);320 sendSysex(command, strlen(string), (byte *)string); 324 321 } 325 322 … … 328 325 void FirmataClass::sendString(const char* string) 329 326 { 330 sendString(FIRMATA_STRING, string);327 sendString(STRING_DATA, string); 331 328 } 332 329 … … 337 334 void FirmataClass::attach(byte command, callbackFunction newFunction) 338 335 { 339 switch(command) {340 case ANALOG_MESSAGE: currentAnalogCallback = newFunction; break;341 case DIGITAL_MESSAGE: currentDigitalCallback = newFunction; break;342 case REPORT_ANALOG: currentReportAnalogCallback = newFunction; break;343 case REPORT_DIGITAL: currentReportDigitalCallback = newFunction; break;344 case SET_PIN_MODE: currentPinModeCallback = newFunction; break;345 }336 switch(command) { 337 case ANALOG_MESSAGE: currentAnalogCallback = newFunction; break; 338 case DIGITAL_MESSAGE: currentDigitalCallback = newFunction; break; 339 case REPORT_ANALOG: currentReportAnalogCallback = newFunction; break; 340 case REPORT_DIGITAL: currentReportDigitalCallback = newFunction; break; 341 case SET_PIN_MODE: currentPinModeCallback = newFunction; break; 342 } 346 343 } 347 344 348 345 void FirmataClass::attach(byte command, systemResetCallbackFunction newFunction) 349 346 { 350 switch(command) {351 case SYSTEM_RESET: currentSystemResetCallback = newFunction; break;352 }347 switch(command) { 348 case SYSTEM_RESET: currentSystemResetCallback = newFunction; break; 349 } 353 350 } 354 351 355 352 void FirmataClass::attach(byte command, stringCallbackFunction newFunction) 356 353 { 357 switch(command) {358 case FIRMATA_STRING: currentStringCallback = newFunction; break;359 }354 switch(command) { 355 case STRING_DATA: currentStringCallback = newFunction; break; 356 } 360 357 } 361 358 362 359 void FirmataClass::attach(byte command, sysexCallbackFunction newFunction) 363 360 { 364 currentSysexCallback = newFunction;361 currentSysexCallback = newFunction; 365 362 } 366 363 367 364 void FirmataClass::detach(byte command) 368 365 { 369 switch(command) {370 case SYSTEM_RESET: currentSystemResetCallback = NULL; break;371 case FIRMATA_STRING: currentStringCallback = NULL; break;372 case START_SYSEX: currentSysexCallback = NULL; break;373 default:374 attach(command, (callbackFunction)NULL);375 }366 switch(command) { 367 case SYSTEM_RESET: currentSystemResetCallback = NULL; break; 368 case STRING_DATA: currentStringCallback = NULL; break; 369 case START_SYSEX: currentSysexCallback = NULL; break; 370 default: 371 attach(command, (callbackFunction)NULL); 372 } 376 373 } 377 374 … … 403 400 void FirmataClass::systemReset(void) 404 401 { 405 byte i;406 407 waitForData = 0; // this flag says the next serial input will be data408 executeMultiByteCommand = 0; // execute this after getting multi-byte data409 multiByteChannel = 0; // channel data for multiByteCommands410 411 412 for(i=0; i<MAX_DATA_BYTES; i++) {413 storedInputData[i] = 0;414 }415 416 parsingSysex = false;417 sysexBytesRead = 0;418 419 if(currentSystemResetCallback)420 (*currentSystemResetCallback)();421 422 //flush(); //TODO uncomment when Firmata is a subclass of HardwareSerial402 byte i; 403 404 waitForData = 0; // this flag says the next serial input will be data 405 executeMultiByteCommand = 0; // execute this after getting multi-byte data 406 multiByteChannel = 0; // channel data for multiByteCommands 407 408 409 for(i=0; i<MAX_DATA_BYTES; i++) { 410 storedInputData[i] = 0; 411 } 412 413 parsingSysex = false; 414 sysexBytesRead = 0; 415 416 if(currentSystemResetCallback) 417 (*currentSystemResetCallback)(); 418 419 //flush(); //TODO uncomment when Firmata is a subclass of HardwareSerial 423 420 } 424 421 … … 429 426 void FirmataClass::pin13strobe(int count, int onInterval, int offInterval) 430 427 { 431 byte i;432 pinMode(VERSION_BLINK_PIN, OUTPUT);433 for(i=0; i<count; i++) {434 delay(offInterval);435 digitalWrite(VERSION_BLINK_PIN, HIGH);436 delay(onInterval);437 digitalWrite(VERSION_BLINK_PIN, LOW);438 }428 byte i; 429 pinMode(VERSION_BLINK_PIN, OUTPUT); 430 for(i=0; i<count; i++) { 431 delay(offInterval); 432 digitalWrite(VERSION_BLINK_PIN, HIGH); 433 delay(onInterval); 434 digitalWrite(VERSION_BLINK_PIN, LOW); 435 } 439 436 } 440 437 -
trunk/arduino/libraries/Firmata/Firmata.h
r46 r80 23 23 * installed firmware. */ 24 24 #define FIRMATA_MAJOR_VERSION 2 // for non-compatible changes 25 #define FIRMATA_MINOR_VERSION 0 // for backwards compatible changes 26 #define VERSION_BLINK_PIN 13 // digital pin to blink version on 25 #define FIRMATA_MINOR_VERSION 1 // for backwards compatible changes 27 26 28 27 #define MAX_DATA_BYTES 32 // max number of data bytes in non-Sysex messages … … 43 42 44 43 // extended command set using sysex (0-127/0x00-0x7F) 45 /* 0x00-0x0F reserved for customcommands */44 /* 0x00-0x0F reserved for user-defined commands */ 46 45 #define SERVO_CONFIG 0x70 // set max angle, minPulse, maxPulse, freq 47 #define FIRMATA_STRING 0x71 // a string message with 14-bits per char 46 #define STRING_DATA 0x71 // a string message with 14-bits per char 47 #define SHIFT_DATA 0x75 // a bitstream to/from a shift register 48 #define I2C_REQUEST 0x76 // send an I2C read/write request 49 #define I2C_REPLY 0x77 // a reply to an I2C read request 50 #define I2C_CONFIG 0x78 // config I2C settings such as delay times and power pins 48 51 #define REPORT_FIRMWARE 0x79 // report name and version of the firmware 52 #define SAMPLING_INTERVAL 0x7A // set the poll rate of the main loop 49 53 #define SYSEX_NON_REALTIME 0x7E // MIDI Reserved for non-realtime messages 50 54 #define SYSEX_REALTIME 0x7F // MIDI Reserved for realtime messages 55 // these are DEPRECATED to make the naming more consistent 56 #define FIRMATA_STRING 0x71 // same as STRING_DATA 57 #define SYSEX_I2C_REQUEST 0x76 // same as I2C_REQUEST 58 #define SYSEX_I2C_REPLY 0x77 // same as I2C_REPLY 59 #define SYSEX_SAMPLING_INTERVAL 0x7A // same as SAMPLING_INTERVAL 51 60 52 61 // pin modes … … 56 65 #define PWM 0x03 // digital pin in PWM output mode 57 66 #define SERVO 0x04 // digital pin in Servo output mode 58 67 #define SHIFT 0x05 // shiftIn/shiftOut mode 68 #define I2C 0x06 // pin included in I2C setup 59 69 60 70 extern "C" { … … 67 77 68 78 69 // TODO make it a subclass of HardwareSerial79 // TODO make it a subclass of a generic Serial/Stream base class 70 80 class FirmataClass 71 81 { … … 79 89 void blinkVersion(void); 80 90 void printFirmwareVersion(void); 81 //void setFirmwareVersion(byte major, byte minor); // see macro below91 //void setFirmwareVersion(byte major, byte minor); // see macro below 82 92 void setFirmwareNameAndVersion(const char *name, byte major, byte minor); 83 93 /* serial receive handling */ … … 86 96 /* serial send handling */ 87 97 void sendAnalog(byte pin, int value); 88 void sendDigital(byte pin, int value); 98 void sendDigital(byte pin, int value); // TODO implement this 89 99 void sendDigitalPort(byte portNumber, int portData); 90 100 void sendString(const char* string); 91 101 void sendString(byte command, const char* string); 92 102 void sendSysex(byte command, byte bytec, byte* bytev); 93 // void print(); // TODO implement so it's compatible to Serial94 // void println(); // TODO implement so it's compatible to Serial95 103 /* attach & detach callback functions to messages */ 96 104 void attach(byte command, callbackFunction newFunction); … … 99 107 void attach(byte command, sysexCallbackFunction newFunction); 100 108 void detach(byte command); 101 // void flush(); // TODO implement flush, probably by subclassing102 109 103 110 private: … … 147 154 #define TOTAL_PORTS 3 // total number of ports for the board 148 155 #define ANALOG_PORT 2 // port# of analog used as digital 156 #define FIRST_ANALOG_PIN 14 // pin# corresponding to analog 0 157 #define VERSION_BLINK_PIN 13 // digital pin to blink version on 158 #define FIRST_SERVO_PIN 2 // pin# of the first servo pin 149 159 #elif defined(__AVR_ATmega8__) // old Arduinos 150 160 #define TOTAL_ANALOG_PINS 6 … … 152 162 #define TOTAL_PORTS 3 // total number of ports for the board 153 163 #define ANALOG_PORT 2 // port# of analog used as digital 164 #define FIRST_ANALOG_PIN 14 // pin# corresponding to analog 0 165 #define VERSION_BLINK_PIN 13 // digital pin to blink version on 166 #define FIRST_SERVO_PIN 2 // pin# of the first servo pin 167 #elif defined(__AVR_ATmega1280__)// Arduino Mega 168 #define TOTAL_ANALOG_PINS 16 169 #define TOTAL_DIGITAL_PINS 70 // 54 digital + 16 analog 170 #define TOTAL_PORTS 9 // total number of ports for the board 171 #define ANALOG_PORT 8 // port# of analog used as digital 172 #define FIRST_ANALOG_PIN 54 // pin# corresponding to analog 0 173 #define VERSION_BLINK_PIN 13 // digital pin to blink version on 174 #define FIRST_SERVO_PIN 2 // pin# of the first servo pin 154 175 #elif defined(__AVR_ATmega128__)// Wiring 155 176 #define TOTAL_ANALOG_PINS 8 156 177 #define TOTAL_DIGITAL_PINS 51 178 #define TOTAL_PORTS 7 // total number of ports for the board 179 #define ANALOG_PORT 5 // port# of analog used as digital 180 #define FIRST_ANALOG_PIN 40 // pin# corresponding to analog 0 181 #define VERSION_BLINK_PIN 48 // digital pin to blink version on 182 #define FIRST_SERVO_PIN 8 // pin# of the first servo pin 183 #elif defined(__AVR_AT90USB162__) // Teensy 184 #define TOTAL_ANALOG_PINS 0 185 #define TOTAL_DIGITAL_PINS 21 // 21 digital + no analog 186 #define TOTAL_PORTS 4 // total number of ports for the board 187 #define ANALOG_PORT 3 // port# of analog used as digital 188 #define FIRST_ANALOG_PIN 21 // pin# corresponding to analog 0 189 #define VERSION_BLINK_PIN 6 // digital pin to blink version on 190 #elif defined(__AVR_ATmega32U4__) // Teensy 191 #define TOTAL_ANALOG_PINS 12 192 #define TOTAL_DIGITAL_PINS 25 // 11 digital + 12 analog 193 #define TOTAL_PORTS 4 // total number of ports for the board 194 #define ANALOG_PORT 3 // port# of analog used as digital 195 #define FIRST_ANALOG_PIN 11 // pin# corresponding to analog 0 196 #define VERSION_BLINK_PIN 11 // digital pin to blink version on 197 #elif defined(__AVR_AT90USB646__) || defined(__AVR_AT90USB1286__) // Teensy++ 198 #define TOTAL_ANALOG_PINS 8 199 #define TOTAL_DIGITAL_PINS 46 // 38 digital + 8 analog 157 200 #define TOTAL_PORTS 6 // total number of ports for the board 158 #define ANALOG_PORT 2 // port# of analog used as digital 201 #define ANALOG_PORT 5 // port# of analog used as digital 202 #define FIRST_ANALOG_PIN 38 // pin# corresponding to analog 0 203 #define VERSION_BLINK_PIN 6 // digital pin to blink version on 204 #elif defined(__AVR_ATmega644P__) || defined(__AVR_ATmega644__) // Sanguino 205 #define TOTAL_ANALOG_PINS 8 206 #define TOTAL_DIGITAL_PINS 32 // 24 digital + 8 analog 207 #define TOTAL_PORTS 4 // total number of ports for the board 208 #define ANALOG_PORT 3 // port# of analog used as digital 209 #define FIRST_ANALOG_PIN 24 // pin# corresponding to analog 0 210 #define VERSION_BLINK_PIN 0 // digital pin to blink version on 211 #elif defined(__AVR_ATmega645__) // Illuminato 212 #define TOTAL_ANALOG_PINS 6 213 #define TOTAL_DIGITAL_PINS 42 // 36 digital + 6 analog 214 #define TOTAL_PORTS 6 // total number of ports for the board 215 #define ANALOG_PORT 4 // port# of analog used as digital 216 #define FIRST_ANALOG_PIN 36 // pin# corresponding to analog 0 217 #define VERSION_BLINK_PIN 13 // digital pin to blink version on 159 218 #else // anything else 160 219 #define TOTAL_ANALOG_PINS 6 … … 162 221 #define TOTAL_PORTS 3 // total number of ports for the board 163 222 #define ANALOG_PORT 2 // port# of analog used as digital 223 #define FIRST_ANALOG_PIN 14 // pin# corresponding to analog 0 224 #define VERSION_BLINK_PIN 13 // digital pin to blink version on 164 225 #endif 165 226 -
trunk/arduino/libraries/Firmata/examples/AnalogFirmata/AnalogFirmata.pde
r46 r80 62 62 servo9.attach(9); 63 63 servo10.attach(10); 64 Firmata.begin( );64 Firmata.begin(57600); 65 65 } 66 66 -
trunk/arduino/libraries/Firmata/examples/EchoString/EchoString.pde
r46 r80 26 26 { 27 27 Firmata.setFirmwareVersion(0, 1); 28 Firmata.attach( FIRMATA_STRING, stringCallback);28 Firmata.attach(STRING_DATA, stringCallback); 29 29 Firmata.attach(START_SYSEX, sysexCallback); 30 Firmata.begin( );30 Firmata.begin(57600); 31 31 } 32 32 -
trunk/arduino/libraries/Firmata/examples/ServoFirmata/ServoFirmata.pde
r46 r80 29 29 servo10.attach(10); 30 30 31 Firmata.begin( );31 Firmata.begin(57600); 32 32 } 33 33 -
trunk/arduino/libraries/Firmata/examples/SimpleAnalogFirmata/SimpleAnalogFirmata.pde
r46 r80 17 17 Firmata.setFirmwareVersion(0, 1); 18 18 Firmata.attach(ANALOG_MESSAGE, analogWriteCallback); 19 Firmata.begin( );19 Firmata.begin(57600); 20 20 } 21 21 -
trunk/arduino/libraries/Firmata/examples/SimpleDigitalFirmata/SimpleDigitalFirmata.pde
r46 r80 14 14 Firmata.sendDigitalPort(portNumber, portValue); 15 15 previousPIN[portNumber] = portValue; 16 Firmata.sendDigitalPort(portNumber, portValue);17 16 } 18 17 } … … 46 45 Firmata.attach(DIGITAL_MESSAGE, digitalWriteCallback); 47 46 Firmata.attach(SET_PIN_MODE, setPinModeCallback); 48 Firmata.begin( );47 Firmata.begin(57600); 49 48 } 50 49 -
trunk/arduino/libraries/Firmata/examples/StandardFirmata/Makefile
r46 r80 51 51 ARDUINO_SRC = $(ARDUINO)/hardware/cores/arduino 52 52 ARDUINO_LIB_SRC = $(ARDUINO)/hardware/libraries 53 ARDUINO_TOOLS = $(ARDUINO)/hardware/tools 53 54 INCLUDE = -I$(ARDUINO_SRC) -I$(ARDUINO)/hardware/tools/avr/avr/include \ 54 55 -I$(ARDUINO_LIB_SRC)/EEPROM \ 55 56 -I$(ARDUINO_LIB_SRC)/Firmata \ 57 -I$(ARDUINO_LIB_SRC)/Matrix \ 58 -I$(ARDUINO_LIB_SRC)/Servo \ 59 -I$(ARDUINO_LIB_SRC)/Wire \ 56 60 -I$(ARDUINO_LIB_SRC) 57 61 SRC = $(wildcard $(ARDUINO_SRC)/*.c) … … 59 63 $(ARDUINO_LIB_SRC)/EEPROM/EEPROM.cpp \ 60 64 $(ARDUINO_LIB_SRC)/Firmata/Firmata.cpp \ 65 $(ARDUINO_LIB_SRC)/Servo/Servo.cpp \ 66 $(ARDUINO_SRC)/Print.cpp \ 61 67 $(ARDUINO_SRC)/WMath.cpp 62 68 HEADERS = $(wildcard $(ARDUINO_SRC)/*.h) $(wildcard $(ARDUINO_LIB_SRC)/*/*.h) … … 107 113 108 114 # Program settings 109 CC = avr-gcc 110 CXX = avr-g++ 111 OBJCOPY = avr-objcopy 112 OBJDUMP = avr-objdump 113 SIZE = avr-size 114 NM = avr-nm 115 ARDUINO_AVR_BIN = $(ARDUINO_TOOLS)/avr/bin 116 CC = $(ARDUINO_AVR_BIN)/avr-gcc 117 CXX = $(ARDUINO_AVR_BIN)/avr-g++ 118 OBJCOPY = $(ARDUINO_AVR_BIN)/avr-objcopy 119 OBJDUMP = $(ARDUINO_AVR_BIN)/avr-objdump 120 SIZE = $(ARDUINO_AVR_BIN)/avr-size 121 NM = $(ARDUINO_AVR_BIN)/avr-nm 122 #AVRDUDE = $(ARDUINO_AVR_BIN)/avrdude 115 123 AVRDUDE = avrdude 116 124 REMOVE = rm -f … … 205 213 # Link: create ELF output file from object files. 206 214 applet/$(TARGET).elf: applet/$(TARGET).cpp $(OBJ) 207 $(CC) $(ALL_CFLAGS) $(OBJ) --output $@ $(LDFLAGS) 215 $(CC) $(ALL_CFLAGS) $(OBJ) -lm --output $@ $(LDFLAGS) 216 # $(CC) $(ALL_CFLAGS) $(OBJ) $(ARDUINO_TOOLS)/avr/avr/lib/avr5/crtm168.o --output $@ $(LDFLAGS) 208 217 209 218 pd_close_serial: … … 259 268 260 269 261 270 path: 271 echo $(PATH) 272 echo $$PATH 273 -
trunk/arduino/libraries/Firmata/examples/StandardFirmata/StandardFirmata.pde
r46 r80 1 1 /* 2 2 Copyright (C) 2006-2008 Hans-Christoph Steiner. All rights reserved. 3 3 4 4 This library is free software; you can redistribute it and/or 5 5 modify it under the terms of the GNU Lesser General Public … … 8 8 9 9 See file LICENSE.txt for further informations on licensing terms. 10 */ 10 11 formatted using the GNU C formatting and indenting 12 */ 11 13 12 14 /* 13 * TODO: add Servo support using setPinMode(pin, SERVO);14 15 * TODO: use Program Control to load stored profiles from EEPROM 15 16 */ 16 17 17 #include <EEPROM.h>18 18 #include <Firmata.h> 19 #include <Servo.h> 19 20 20 21 /*============================================================================== … … 35 36 unsigned long currentMillis; // store the current value from millis() 36 37 unsigned long nextExecuteMillis; // for comparison with currentMillis 37 38 39 /*============================================================================== 40 * FUNCTIONS 38 int samplingInterval = 19; // how often to run the main loop (in ms) 39 40 Servo servos[MAX_SERVOS]; 41 42 /*============================================================================== 43 * FUNCTIONS 41 44 *============================================================================*/ 42 45 … … 45 48 portValue = portValue &~ portStatus[portNumber]; 46 49 if(previousPINs[portNumber] != portValue) { 47 Firmata.sendDigitalPort(portNumber, portValue); 48 previousPINs[portNumber] = portValue; 49 Firmata.sendDigitalPort(portNumber, portValue); 50 } 50 Firmata.sendDigitalPort(portNumber, portValue); 51 previousPINs[portNumber] = portValue; 52 } 51 53 } 52 54 … … 54 56 * check all the active digital inputs for change of state, then add any events 55 57 * to the Serial output queue using Serial.print() */ 56 void checkDigitalInputs(void) 57 { 58 byte i, tmp; 59 for(i=0; i < TOTAL_PORTS; i++) { 60 if(reportPINs[i]) { 61 switch(i) { 62 case 0: outputPort(0, PIND &~ B00000011); break; // ignore Rx/Tx 0/1 63 case 1: outputPort(1, PINB); break; 64 case ANALOG_PORT: outputPort(ANALOG_PORT, PINC); break; 65 } 66 } 58 void checkDigitalInputs(void) 59 { 60 byte i, tmp; 61 for(i=0; i < TOTAL_PORTS; i++) { 62 if(reportPINs[i]) { 63 switch(i) { 64 case 0: 65 outputPort(0, PIND &~ B00000011); // ignore Rx/Tx 0/1 66 break; 67 case 1: 68 outputPort(1, PINB); 69 break; 70 case ANALOG_PORT: 71 outputPort(ANALOG_PORT, PINC); 72 break; 73 } 67 74 } 75 } 68 76 } 69 77 … … 73 81 */ 74 82 void setPinModeCallback(byte pin, int mode) { 75 byte port = 0; 76 byte offset = 0; 77 78 if (pin < 8) { 79 port = 0; 80 offset = 0; 81 } else if (pin < 14) { 82 port = 1; 83 offset = 8; 84 } else if (pin < 22) { 85 port = 2; 86 offset = 14; 83 byte port = 0; 84 byte offset = 0; 85 86 // TODO: abstract for different boards 87 if (pin < 8) { 88 port = 0; 89 offset = 0; 90 } else if (pin < 14) { 91 port = 1; 92 offset = 8; 93 } else if (pin < 22) { 94 port = 2; 95 offset = 14; 96 } 97 98 if(pin > 1) { // ignore RxTx (pins 0 and 1) 99 if (isServoSupportedPin(pin) && mode != SERVO) 100 if (servos[pin - FIRST_SERVO_PIN].attached()) 101 servos[pin - FIRST_SERVO_PIN].detach(); 102 if(pin > 13) 103 reportAnalogCallback(pin - 14, mode == ANALOG ? 1 : 0); // turn on/off reporting 104 switch(mode) { 105 case ANALOG: 106 digitalWrite(pin, LOW); // disable internal pull-ups and fall thru to 'case INPUT:' 107 case INPUT: 108 pinStatus[pin] = mode; 109 pinMode(pin, INPUT); 110 portStatus[port] = portStatus[port] &~ (1 << (pin - offset)); 111 break; 112 case OUTPUT: 113 digitalWrite(pin, LOW); // disable PWM and fall thru to 'case PWM:' 114 case PWM: 115 pinStatus[pin] = mode; 116 pinMode(pin, OUTPUT); 117 portStatus[port] = portStatus[port] | (1 << (pin - offset)); 118 break; 119 case SERVO: 120 // TODO: Support Arduino Mega 121 if (isServoSupportedPin(pin)) { 122 pinStatus[pin] = mode; 123 if (!servos[pin - FIRST_SERVO_PIN].attached()) 124 servos[pin - FIRST_SERVO_PIN].attach(pin); 125 } else 126 Firmata.sendString("Servo only on pins from 2 to 13"); 127 break; 128 case I2C: 129 pinStatus[pin] = mode; 130 Firmata.sendString("I2C mode not yet supported"); 131 break; 132 default: 133 Firmata.sendString("Unknown pin mode"); // TODO: put error msgs in EEPROM 87 134 } 88 89 if(pin > 1) { // ignore RxTx (pins 0 and 1) 90 pinStatus[pin] = mode; 91 switch(mode) { 92 case INPUT: 93 pinMode(pin, INPUT); 94 portStatus[port] = portStatus[port] &~ (1 << (pin - offset)); 95 break; 96 case OUTPUT: 97 digitalWrite(pin, LOW); // disable PWM 98 case PWM: 99 pinMode(pin, OUTPUT); 100 portStatus[port] = portStatus[port] | (1 << (pin - offset)); 101 break; 102 //case ANALOG: // TODO figure this out 103 default: 104 Firmata.sendString(""); 105 } 106 // TODO: save status to EEPROM here, if changed 107 } 135 // TODO: save status to EEPROM here, if changed 136 } 108 137 } 109 138 110 139 void analogWriteCallback(byte pin, int value) 111 140 { 112 setPinModeCallback(pin,PWM); 141 switch(pinStatus[pin]) { 142 case SERVO: 143 if (isServoSupportedPin(pin)) 144 servos[pin - FIRST_SERVO_PIN].write(value); 145 break; 146 case PWM: 113 147 analogWrite(pin, value); 148 break; 149 } 114 150 } 115 151 116 152 void digitalWriteCallback(byte port, int value) 117 153 { 118 switch(port) { 119 case 0: // pins 2-7 (don't change Rx/Tx, pins 0 and 1) 120 // 0xFF03 == B1111111100000011 0x03 == B00000011 121 PORTD = (value &~ 0xFF03) | (PORTD & 0x03); 122 break; 123 case 1: // pins 8-13 (14,15 are disabled for the crystal) 124 PORTB = (byte)value; 125 break; 126 case 2: // analog pins used as digital 127 PORTC = (byte)value; 128 break; 129 } 154 switch(port) { 155 case 0: // pins 2-7 (don't change Rx/Tx, pins 0 and 1) 156 // 0xFF03 == B1111111100000011 0x03 == B00000011 157 PORTD = (value &~ 0xFF03) | (PORTD & 0x03); 158 break; 159 case 1: // pins 8-13 (14,15 are disabled for the crystal) 160 PORTB = (byte)value; 161 break; 162 case 2: // analog pins used as digital 163 byte pin; 164 byte pinModeMask; 165 for(pin=0; pin<8; pin++) 166 if(pinStatus[pin] == OUTPUT) 167 pinModeMask += 1 << pin; 168 PORTC = (byte)value & pinModeMask; 169 break; 170 } 130 171 } 131 172 … … 137 178 void reportAnalogCallback(byte pin, int value) 138 179 { 139 if(value == 0) { 140 analogInputsToReport = analogInputsToReport &~ (1 << pin); 180 if(value == 0) { 181 analogInputsToReport = analogInputsToReport &~ (1 << pin); 182 } 183 else { // everything but 0 enables reporting of that pin 184 analogInputsToReport = analogInputsToReport | (1 << pin); 185 } 186 // TODO: save status to EEPROM here, if changed 187 } 188 189 void reportDigitalCallback(byte port, int value) 190 { 191 reportPINs[port] = (byte)value; 192 if(port == ANALOG_PORT) // turn off analog reporting when used as digital 193 analogInputsToReport = 0; 194 } 195 196 /*============================================================================== 197 * SYSEX-BASED commands 198 *============================================================================*/ 199 200 void sysexCallback(byte command, byte argc, byte *argv) 201 { 202 switch(command) { 203 case SERVO_CONFIG: 204 if(argc > 4) { 205 // these vars are here for clarity, they'll optimized away by the compiler 206 byte pin = argv[0]; 207 int minPulse = argv[1] + (argv[2] << 7); 208 int maxPulse = argv[3] + (argv[4] << 7); 209 210 if (isServoSupportedPin(pin)) { 211 // servos are pins from 2 to 13, so offset for array 212 if (servos[pin - FIRST_SERVO_PIN].attached()) 213 servos[pin - FIRST_SERVO_PIN].detach(); 214 servos[pin - FIRST_SERVO_PIN].attach(pin, minPulse, maxPulse); 215 setPinModeCallback(pin, SERVO); 216 } 141 217 } 142 else { // everything but 0 enables reporting of that pin 143 analogInputsToReport = analogInputsToReport | (1 << pin); 218 break; 219 case SAMPLING_INTERVAL: 220 if (argc > 1) 221 samplingInterval = argv[0] + (argv[1] << 7); 222 else 223 Firmata.sendString("Not enough data"); 224 break; 225 } 226 } 227 228 boolean isServoSupportedPin(byte pin) 229 { 230 return ((FIRST_SERVO_PIN <= pin) && (pin <= (FIRST_SERVO_PIN + MAX_SERVOS))); 231 } 232 233 /*============================================================================== 234 * SETUP() 235 *============================================================================*/ 236 void setup() 237 { 238 byte i; 239 240 Firmata.setFirmwareVersion(2, 1); 241 242 Firmata.attach(ANALOG_MESSAGE, analogWriteCallback); 243 Firmata.attach(DIGITAL_MESSAGE, digitalWriteCallback); 244 Firmata.attach(REPORT_ANALOG, reportAnalogCallback); 245 Firmata.attach(REPORT_DIGITAL, reportDigitalCallback); 246 Firmata.attach(SET_PIN_MODE, setPinModeCallback); 247 Firmata.attach(START_SYSEX, sysexCallback); 248 249 portStatus[0] = B00000011; // ignore Tx/RX pins 250 portStatus[1] = B11000000; // ignore 14/15 pins 251 portStatus[2] = B00000000; 252 253 for(i=0; i < FIRST_ANALOG_PIN; ++i) { 254 setPinModeCallback(i,OUTPUT); 255 } 256 // set all outputs to 0 to make sure internal pull-up resistors are off 257 PORTB = 0; // pins 8-15 258 PORTC = 0; // analog port 259 PORTD = 0; // pins 0-7 260 261 // TODO rethink the init, perhaps it should report analog on default 262 for(i=0; i<TOTAL_PORTS; ++i) { 263 reportPINs[i] = false; 264 } 265 // TODO: load state from EEPROM here 266 267 /* send digital inputs here, if enabled, to set the initial state on the 268 * host computer, since once in the loop(), this firmware will only send 269 * digital data on change. */ 270 if(reportPINs[0]) outputPort(0, PIND &~ B00000011); // ignore Rx/Tx 0/1 271 if(reportPINs[1]) outputPort(1, PINB); 272 if(reportPINs[ANALOG_PORT]) outputPort(ANALOG_PORT, PINC); 273 274 Firmata.begin(57600); 275 } 276 277 /*============================================================================== 278 * LOOP() 279 *============================================================================*/ 280 void loop() 281 { 282 /* DIGITALREAD - as fast as possible, check for changes and output them */ 283 checkDigitalInputs(); 284 currentMillis = millis(); 285 if(currentMillis > nextExecuteMillis) { 286 nextExecuteMillis = currentMillis + samplingInterval; 287 /* SERIALREAD - Serial.read() uses a 128 byte circular buffer, so handle 288 * all serialReads at once, i.e. empty the buffer */ 289 while(Firmata.available()) 290 Firmata.processInput(); 291 /* SEND FTDI WRITE BUFFER - make sure that the FTDI buffer doesn't go over 292 * 60 bytes. Ideally this could send an "event character" every 4 ms to 293 * trigger the buffer to dump. */ 294 295 /* ANALOGREAD - do all of the analogReads() once per poll cycle */ 296 for(analogPin=0;analogPin<TOTAL_ANALOG_PINS;analogPin++) { 297 if( analogInputsToReport & (1 << analogPin) ) { 298 Firmata.sendAnalog(analogPin, analogRead(analogPin)); 299 } 144 300 } 145 // TODO: save status to EEPROM here, if changed 146 } 147 148 void reportDigitalCallback(byte port, int value) 149 { 150 reportPINs[port] = (byte)value; 151 if(port == ANALOG_PORT) // turn off analog reporting when used as digital 152 analogInputsToReport = 0; 153 } 154 155 /*============================================================================== 156 * SETUP() 157 *============================================================================*/ 158 void setup() 159 { 160 byte i; 161 162 Firmata.setFirmwareVersion(2, 0); 163 164 Firmata.attach(ANALOG_MESSAGE, analogWriteCallback); 165 Firmata.attach(DIGITAL_MESSAGE, digitalWriteCallback); 166 Firmata.attach(REPORT_ANALOG, reportAnalogCallback); 167 Firmata.attach(REPORT_DIGITAL, reportDigitalCallback); 168 Firmata.attach(SET_PIN_MODE, setPinModeCallback); 169 170 portStatus[0] = B00000011; // ignore Tx/RX pins 171 portStatus[1] = B11000000; // ignore 14/15 pins 172 portStatus[2] = B00000000; 173 174 // for(i=0; i<TOTAL_DIGITAL_PINS; ++i) { // TODO make this work with analogs 175 for(i=0; i<14; ++i) { 176 setPinModeCallback(i,OUTPUT); 177 } 178 // set all outputs to 0 to make sure internal pull-up resistors are off 179 PORTB = 0; // pins 8-15 180 PORTC = 0; // analog port 181 PORTD = 0; // pins 0-7 182 183 // TODO rethink the init, perhaps it should report analog on default 184 for(i=0; i<TOTAL_PORTS; ++i) { 185 reportPINs[i] = false; 186 } 187 // TODO: load state from EEPROM here 188 189 /* send digital inputs here, if enabled, to set the initial state on the 190 * host computer, since once in the loop(), this firmware will only send 191 * digital data on change. */ 192 if(reportPINs[0]) outputPort(0, PIND &~ B00000011); // ignore Rx/Tx 0/1 193 if(reportPINs[1]) outputPort(1, PINB); 194 if(reportPINs[ANALOG_PORT]) outputPort(ANALOG_PORT, PINC); 195 196 Firmata.begin(); 197 } 198 199 /*============================================================================== 200 * LOOP() 201 *============================================================================*/ 202 void loop() 203 { 204 /* DIGITALREAD - as fast as possible, check for changes and output them to the 205 * FTDI buffer using Serial.print() */ 206 checkDigitalInputs(); 207 currentMillis = millis(); 208 if(currentMillis > nextExecuteMillis) { 209 nextExecuteMillis = currentMillis + 19; // run this every 20ms 210 /* SERIALREAD - Serial.read() uses a 128 byte circular buffer, so handle 211 * all serialReads at once, i.e. empty the buffer */ 212 while(Firmata.available()) 213 Firmata.processInput(); 214 /* SEND FTDI WRITE BUFFER - make sure that the FTDI buffer doesn't go over 215 * 60 bytes. use a timer to sending an event character every 4 ms to 216 * trigger the buffer to dump. */ 217 218 /* ANALOGREAD - right after the event character, do all of the 219 * analogReads(). These only need to be done every 4ms. */ 220 for(analogPin=0;analogPin<TOTAL_ANALOG_PINS;analogPin++) { 221 if( analogInputsToReport & (1 << analogPin) ) { 222 Firmata.sendAnalog(analogPin, analogRead(analogPin)); 223 } 224 } 225 } 226 } 301 } 302 } -
trunk/arduino/libraries/LiquidCrystal/LiquidCrystal.cpp
r46 r80 26 26 27 27 LiquidCrystal::LiquidCrystal(uint8_t rs, uint8_t rw, uint8_t enable, 28 uint8_t d0, uint8_t d1, uint8_t d2, uint8_t d3, 29 uint8_t d4, uint8_t d5, uint8_t d6, uint8_t d7) : 30 _four_bit_mode(0), _rs_pin(rs), _rw_pin(rw), _enable_pin(enable) 31 { 28 uint8_t d0, uint8_t d1, uint8_t d2, uint8_t d3, 29 uint8_t d4, uint8_t d5, uint8_t d6, uint8_t d7) 30 { 31 init(0, rs, rw, enable, d0, d1, d2, d3, d4, d5, d6, d7); 32 } 33 34 LiquidCrystal::LiquidCrystal(uint8_t rs, uint8_t enable, 35 uint8_t d0, uint8_t d1, uint8_t d2, uint8_t d3, 36 uint8_t d4, uint8_t d5, uint8_t d6, uint8_t d7) 37 { 38 init(0, rs, 255, enable, d0, d1, d2, d3, d4, d5, d6, d7); 39 } 40 41 LiquidCrystal::LiquidCrystal(uint8_t rs, uint8_t rw, uint8_t enable, 42 uint8_t d0, uint8_t d1, uint8_t d2, uint8_t d3) 43 { 44 init(1, rs, rw, enable, d0, d1, d2, d3, 0, 0, 0, 0); 45 } 46 47 LiquidCrystal::LiquidCrystal(uint8_t rs, uint8_t enable, 48 uint8_t d0, uint8_t d1, uint8_t d2, uint8_t d3) 49 { 50 init(1, rs, 255, enable, d0, d1, d2, d3, 0, 0, 0, 0); 51 } 52 53 void LiquidCrystal::init(uint8_t fourbitmode, uint8_t rs, uint8_t rw, uint8_t enable, 54 uint8_t d0, uint8_t d1, uint8_t d2, uint8_t d3, 55 uint8_t d4, uint8_t d5, uint8_t d6, uint8_t d7) 56 { 57 _rs_pin = rs; 58 _rw_pin = rw; 59 _enable_pin = enable; 60 32 61 _data_pins[0] = d0; 33 62 _data_pins[1] = d1; … … 38 67 _data_pins[6] = d6; 39 68 _data_pins[7] = d7; 40 69 41 70 pinMode(_rs_pin, OUTPUT); 42 pinMode(_rw_pin, OUTPUT); 71 // we can save 1 pin by not using RW. Indicate by passing 255 instead of pin# 72 if (_rw_pin != 255) { 73 pinMode(_rw_pin, OUTPUT); 74 } 43 75 pinMode(_enable_pin, OUTPUT); 44 76 45 for (int i = 0; i < 8; i++) 46 pinMode(_data_pins[i], OUTPUT); 47 48 command(0x38); // function set: 8 bits, 1 line, 5x8 dots 49 command(0x0C); // display control: turn display on, cursor off, no blinking 50 command(0x06); // entry mode set: increment automatically, display shift, right shift 77 if (fourbitmode) 78 _displayfunction = LCD_4BITMODE | LCD_1LINE | LCD_5x8DOTS; 79 else 80 _displayfunction = LCD_8BITMODE | LCD_1LINE | LCD_5x8DOTS; 81 82 begin(16, 1); 83 } 84 85 void LiquidCrystal::begin(uint8_t cols, uint8_t lines, uint8_t dotsize) { 86 if (lines > 1) { 87 _displayfunction |= LCD_2LINE; 88 } 89 _numlines = lines; 90 _currline = 0; 91 92 // for some 1 line displays you can select a 10 pixel high font 93 if ((dotsize != 0) && (lines == 1)) { 94 _displayfunction |= LCD_5x10DOTS; 95 } 96 97 // SEE PAGE 45/46 FOR INITIALIZATION SPECIFICATION! 98 // according to datasheet, we need at least 40ms after power rises above 2.7V 99 // before sending commands. Arduino can turn on way befer 4.5V so we'll wait 50 100 delayMicroseconds(50000); 101 // Now we pull both RS and R/W low to begin commands 102 digitalWrite(_rs_pin, LOW); 103 digitalWrite(_enable_pin, LOW); 104 if (_rw_pin != 255) { 105 digitalWrite(_rw_pin, LOW); 106 } 107 108 //put the LCD into 4 bit or 8 bit mode 109 if (! (_displayfunction & LCD_8BITMODE)) { 110 // this is according to the hitachi HD44780 datasheet 111 // figure 24, pg 46 112 113 // we start in 8bit mode, try to set 4 bit mode 114 write4bits(0x03); 115 delayMicroseconds(4500); // wait min 4.1ms 116 117 // second try 118 write4bits(0x03); 119 delayMicroseconds(4500); // wait min 4.1ms 120 121 // third go! 122 write4bits(0x03); 123 delayMicroseconds(150); 124 125 // finally, set to 8-bit interface 126 write4bits(0x02); 127 } else { 128 // this is according to the hitachi HD44780 datasheet 129 // page 45 figure 23 130 131 // Send function set command sequence 132 command(LCD_FUNCTIONSET | _displayfunction); 133 delayMicroseconds(4500); // wait more than 4.1ms 134 135 // second try 136 command(LCD_FUNCTIONSET | _displayfunction); 137 delayMicroseconds(150); 138 139 // third go 140 command(LCD_FUNCTIONSET | _displayfunction); 141 } 142 143 // finally, set # lines, font size, etc. 144 command(LCD_FUNCTIONSET | _displayfunction); 145 146 // turn the display on with no cursor or blinking default 147 _displaycontrol = LCD_DISPLAYON | LCD_CURSOROFF | LCD_BLINKOFF; 148 display(); 149 150 // clear it off 51 151 clear(); 52 } 53 54 LiquidCrystal::LiquidCrystal(uint8_t rs, uint8_t rw, uint8_t enable, 55 uint8_t d0, uint8_t d1, uint8_t d2, uint8_t d3) : 56 _four_bit_mode(1), _rs_pin(rs), _rw_pin(rw), _enable_pin(enable) 57 { 58 _data_pins[0] = d0; 59 _data_pins[1] = d1; 60 _data_pins[2] = d2; 61 _data_pins[3] = d3; 62 63 pinMode(_rs_pin, OUTPUT); 64 pinMode(_rw_pin, OUTPUT); 65 pinMode(_enable_pin, OUTPUT); 66 67 for (int i = 0; i < 4; i++) 68 pinMode(_data_pins[i], OUTPUT); 69 70 command(0x28); // function set: 4 bits, 1 line, 5x8 dots 71 command(0x0C); // display control: turn display on, cursor off, no blinking 72 command(0x06); // entry mode set: increment automatically, display shift, right shift 73 clear(); 74 } 75 152 153 // Initialize to default text direction (for romance languages) 154 _displaymode = LCD_ENTRYLEFT | LCD_ENTRYSHIFTDECREMENT; 155 // set the entry mode 156 command(LCD_ENTRYMODESET | _displaymode); 157 158 } 159 160 /********** high level commands, for the user! */ 76 161 void LiquidCrystal::clear() 77 162 { 78 command( 0x01); // clear display, set cursor position to zero79 delayMicroseconds(2000); 163 command(LCD_CLEARDISPLAY); // clear display, set cursor position to zero 164 delayMicroseconds(2000); // this command takes a long time! 80 165 } 81 166 82 167 void LiquidCrystal::home() 83 168 { 84 command( 0x02); // set cursor position to zero85 delayMicroseconds(2000); 86 } 87 88 void LiquidCrystal::setCursor( int col, int row)169 command(LCD_RETURNHOME); // set cursor position to zero 170 delayMicroseconds(2000); // this command takes a long time! 171 } 172 173 void LiquidCrystal::setCursor(uint8_t col, uint8_t row) 89 174 { 90 175 int row_offsets[] = { 0x00, 0x40, 0x14, 0x54 }; 91 command(0x80 | (col + row_offsets[row])); 92 } 93 94 void LiquidCrystal::command(uint8_t value) { 176 if ( row > _numlines ) { 177 row = _numlines-1; // we count rows starting w/0 178 } 179 180 command(LCD_SETDDRAMADDR | (col + row_offsets[row])); 181 } 182 183 // Turn the display on/off (quickly) 184 void LiquidCrystal::noDisplay() { 185 _displaycontrol &= ~LCD_DISPLAYON; 186 command(LCD_DISPLAYCONTROL | _displaycontrol); 187 } 188 void LiquidCrystal::display() { 189 _displaycontrol |= LCD_DISPLAYON; 190 command(LCD_DISPLAYCONTROL | _displaycontrol); 191 } 192 193 // Turns the underline cursor on/off 194 void LiquidCrystal::noCursor() { 195 _displaycontrol &= ~LCD_CURSORON; 196 command(LCD_DISPLAYCONTROL | _displaycontrol); 197 } 198 void LiquidCrystal::cursor() { 199 _displaycontrol |= LCD_CURSORON; 200 command(LCD_DISPLAYCONTROL | _displaycontrol); 201 } 202 203 // Turn on and off the blinking cursor 204 void LiquidCrystal::noBlink() { 205 _displaycontrol &= ~LCD_BLINKON; 206 command(LCD_DISPLAYCONTROL | _displaycontrol); 207 } 208 void LiquidCrystal::blink() { 209 _displaycontrol |= LCD_BLINKON; 210 command(LCD_DISPLAYCONTROL | _displaycontrol); 211 } 212 213 // These commands scroll the display without changing the RAM 214 void LiquidCrystal::scrollDisplayLeft(void) { 215 command(LCD_CURSORSHIFT | LCD_DISPLAYMOVE | LCD_MOVELEFT); 216 } 217 void LiquidCrystal::scrollDisplayRight(void) { 218 command(LCD_CURSORSHIFT | LCD_DISPLAYMOVE | LCD_MOVERIGHT); 219 } 220 221 // This is for text that flows Left to Right 222 void LiquidCrystal::leftToRight(void) { 223 _displaymode |= LCD_ENTRYLEFT; 224 command(LCD_ENTRYMODESET | _displaymode); 225 } 226 227 // This is for text that flows Right to Left 228 void LiquidCrystal::rightToLeft(void) { 229 _displaymode &= ~LCD_ENTRYLEFT; 230 command(LCD_ENTRYMODESET | _displaymode); 231 } 232 233 // This will 'right justify' text from the cursor 234 void LiquidCrystal::autoscroll(void) { 235 _displaymode |= LCD_ENTRYSHIFTINCREMENT; 236 command(LCD_ENTRYMODESET | _displaymode); 237 } 238 239 // This will 'left justify' text from the cursor 240 void LiquidCrystal::noAutoscroll(void) { 241 _displaymode &= ~LCD_ENTRYSHIFTINCREMENT; 242 command(LCD_ENTRYMODESET | _displaymode); 243 } 244 245 // Allows us to fill the first 8 CGRAM locations 246 // with custom characters 247 void LiquidCrystal::createChar(uint8_t location, uint8_t charmap[]) { 248 location &= 0x7; // we only have 8 locations 0-7 249 command(LCD_SETCGRAMADDR | (location << 3)); 250 for (int i=0; i<8; i++) { 251 write(charmap[i]); 252 } 253 } 254 255 /*********** mid level commands, for sending data/cmds */ 256 257 inline void LiquidCrystal::command(uint8_t value) { 95 258 send(value, LOW); 96 259 } 97 260 98 void LiquidCrystal::write(uint8_t value) {261 inline void LiquidCrystal::write(uint8_t value) { 99 262 send(value, HIGH); 100 263 } 101 264 265 /************ low level data pushing commands **********/ 266 267 // write either command or data, with automatic 4/8-bit selection 102 268 void LiquidCrystal::send(uint8_t value, uint8_t mode) { 103 269 digitalWrite(_rs_pin, mode); 104 digitalWrite(_rw_pin, LOW); 105 106 if (_four_bit_mode) { 107 for (int i = 0; i < 4; i++) { 108 digitalWrite(_data_pins[i], (value >> (i + 4)) & 0x01); 109 } 110 111 digitalWrite(_enable_pin, HIGH); 112 digitalWrite(_enable_pin, LOW); 113 114 for (int i = 0; i < 4; i++) { 115 digitalWrite(_data_pins[i], (value >> i) & 0x01); 116 } 117 118 digitalWrite(_enable_pin, HIGH); 119 digitalWrite(_enable_pin, LOW); 270 271 // if there is a RW pin indicated, set it low to Write 272 if (_rw_pin != 255) { 273 digitalWrite(_rw_pin, LOW); 274 } 275 276 if (_displayfunction & LCD_8BITMODE) { 277 write8bits(value); 120 278 } else { 121 for (int i = 0; i < 8; i++) { 122 digitalWrite(_data_pins[i], (value >> i) & 0x01); 123 } 124 125 digitalWrite(_enable_pin, HIGH); 126 digitalWrite(_enable_pin, LOW); 127 } 128 } 279 write4bits(value>>4); 280 write4bits(value); 281 } 282 } 283 284 void LiquidCrystal::pulseEnable(void) { 285 digitalWrite(_enable_pin, LOW); 286 delayMicroseconds(1); 287 digitalWrite(_enable_pin, HIGH); 288 delayMicroseconds(1); // enable pulse must be >450ns 289 digitalWrite(_enable_pin, LOW); 290 delayMicroseconds(100); // commands need > 37us to settle 291 } 292 293 void LiquidCrystal::write4bits(uint8_t value) { 294 for (int i = 0; i < 4; i++) { 295 pinMode(_data_pins[i], OUTPUT); 296 digitalWrite(_data_pins[i], (value >> i) & 0x01); 297 } 298 299 pulseEnable(); 300 } 301 302 void LiquidCrystal::write8bits(uint8_t value) { 303 for (int i = 0; i < 8; i++) { 304 pinMode(_data_pins[i], OUTPUT); 305 digitalWrite(_data_pins[i], (value >> i) & 0x01); 306 } 307 308 pulseEnable(); 309 } -
trunk/arduino/libraries/LiquidCrystal/LiquidCrystal.h
r46 r80 5 5 #include "Print.h" 6 6 7 // commands 8 #define LCD_CLEARDISPLAY 0x01 9 #define LCD_RETURNHOME 0x02 10 #define LCD_ENTRYMODESET 0x04 11 #define LCD_DISPLAYCONTROL 0x08 12 #define LCD_CURSORSHIFT 0x10 13 #define LCD_FUNCTIONSET 0x20 14 #define LCD_SETCGRAMADDR 0x40 15 #define LCD_SETDDRAMADDR 0x80 16 17 // flags for display entry mode 18 #define LCD_ENTRYRIGHT 0x00 19 #define LCD_ENTRYLEFT 0x02 20 #define LCD_ENTRYSHIFTINCREMENT 0x01 21 #define LCD_ENTRYSHIFTDECREMENT 0x00 22 23 // flags for display on/off control 24 #define LCD_DISPLAYON 0x04 25 #define LCD_DISPLAYOFF 0x00 26 #define LCD_CURSORON 0x02 27 #define LCD_CURSOROFF 0x00 28 #define LCD_BLINKON 0x01 29 #define LCD_BLINKOFF 0x00 30 31 // flags for display/cursor shift 32 #define LCD_DISPLAYMOVE 0x08 33 #define LCD_CURSORMOVE 0x00 34 #define LCD_MOVERIGHT 0x04 35 #define LCD_MOVELEFT 0x00 36 37 // flags for function set 38 #define LCD_8BITMODE 0x10 39 #define LCD_4BITMODE 0x00 40 #define LCD_2LINE 0x08 41 #define LCD_1LINE 0x00 42 #define LCD_5x10DOTS 0x04 43 #define LCD_5x8DOTS 0x00 44 7 45 class LiquidCrystal : public Print { 8 46 public: 9 LiquidCrystal(uint8_t, uint8_t, uint8_t, uint8_t, uint8_t, uint8_t, uint8_t); 10 LiquidCrystal(uint8_t, uint8_t, uint8_t, uint8_t, uint8_t, uint8_t, uint8_t, 11 uint8_t, uint8_t, uint8_t, uint8_t); 47 LiquidCrystal(uint8_t rs, uint8_t enable, 48 uint8_t d0, uint8_t d1, uint8_t d2, uint8_t d3, 49 uint8_t d4, uint8_t d5, uint8_t d6, uint8_t d7); 50 LiquidCrystal(uint8_t rs, uint8_t rw, uint8_t enable, 51 uint8_t d0, uint8_t d1, uint8_t d2, uint8_t d3, 52 uint8_t d4, uint8_t d5, uint8_t d6, uint8_t d7); 53 LiquidCrystal(uint8_t rs, uint8_t rw, uint8_t enable, 54 uint8_t d0, uint8_t d1, uint8_t d2, uint8_t d3); 55 LiquidCrystal(uint8_t rs, uint8_t enable, 56 uint8_t d0, uint8_t d1, uint8_t d2, uint8_t d3); 57 58 void init(uint8_t fourbitmode, uint8_t rs, uint8_t rw, uint8_t enable, 59 uint8_t d0, uint8_t d1, uint8_t d2, uint8_t d3, 60 uint8_t d4, uint8_t d5, uint8_t d6, uint8_t d7); 61 62 void begin(uint8_t cols, uint8_t rows, uint8_t charsize = LCD_5x8DOTS); 63 12 64 void clear(); 13 65 void home(); 14 void setCursor(int, int); 15 /* 16 void shiftDisplayLeft(); 17 void shiftDisplayRight(); 18 */ 66 67 void noDisplay(); 68 void display(); 69 void noBlink(); 70 void blink(); 71 void noCursor(); 72 void cursor(); 73 void scrollDisplayLeft(); 74 void scrollDisplayRight(); 75 void leftToRight(); 76 void rightToLeft(); 77 void autoscroll(); 78 void noAutoscroll(); 79 80 void createChar(uint8_t, uint8_t[]); 81 void setCursor(uint8_t, uint8_t); 19 82 virtual void write(uint8_t); 20 83 void command(uint8_t); 21 84 private: 22 85 void send(uint8_t, uint8_t); 23 24 uint8_t _four_bit_mode; 86 void write4bits(uint8_t); 87 void write8bits(uint8_t); 88 void pulseEnable(); 89 25 90 uint8_t _rs_pin; // LOW: command. HIGH: character. 26 91 uint8_t _rw_pin; // LOW: write to LCD. HIGH: read from LCD. 27 92 uint8_t _enable_pin; // activated by a HIGH pulse. 28 93 uint8_t _data_pins[8]; 94 95 uint8_t _displayfunction; 96 uint8_t _displaycontrol; 97 uint8_t _displaymode; 98 99 uint8_t _initialized; 100 101 uint8_t _numlines,_currline; 29 102 }; 30 103 -
trunk/arduino/libraries/LiquidCrystal/examples/HelloWorld/HelloWorld.pde
r46 r80 1 /* 2 LiquidCrystal Library - Hello World 3 4 Demonstrates the use a 16x2 LCD display. The LiquidCrystal 5 library works with all LCD displays that are compatible with the 6 Hitachi HD44780 driver. There are many of them out there, and you 7 can usually tell them by the 16-pin interface. 8 9 This sketch prints "Hello World!" to the LCD 10 and shows the time. 11 12 The circuit: 13 * LCD RS pin to digital pin 12 14 * LCD Enable pin to digital pin 11 15 * LCD D4 pin to digital pin 5 16 * LCD D5 pin to digital pin 4 17 * LCD D6 pin to digital pin 3 18 * LCD D7 pin to digital pin 2 19 * 10K resistor: 20 * ends to +5V and ground 21 * wiper to LCD VO pin (pin 3) 22 23 Library originally added 18 Apr 2008 24 by David A. Mellis 25 library modified 5 Jul 2009 26 by Limor Fried (http://www.ladyada.net) 27 example added 9 Jul 2009 28 by Tom Igoe 29 modified 25 July 2009 30 by David A. Mellis 31 32 33 http://www.arduino.cc/en/Tutorial/LiquidCrystal 34 */ 35 36 // include the library code: 1 37 #include <LiquidCrystal.h> 2 38 3 // LiquidCrystal display with: 4 // rs on pin 12 5 // rw on pin 11 6 // enable on pin 10 7 // d4, d5, d6, d7 on pins 5, 4, 3, 2 8 LiquidCrystal lcd(12, 11, 10, 5, 4, 3, 2); 39 // initialize the library with the numbers of the interface pins 40 LiquidCrystal lcd(12, 11, 5, 4, 3, 2); 9 41 10 void setup() 11 { 42 void setup() { 43 // set up the LCD's number of rows and columns: 44 lcd.begin(16, 2); 12 45 // Print a message to the LCD. 13 46 lcd.print("hello, world!"); 14 47 } 15 48 16 void loop() 17 { 49 void loop() { 50 // set the cursor to column 0, line 1 51 // (note: line 1 is the second row, since counting begins with 0): 52 lcd.setCursor(0, 1); 53 // print the number of seconds since reset: 54 lcd.print(millis()/1000); 18 55 } 56 -
trunk/arduino/libraries/LiquidCrystal/examples/SerialDisplay/SerialDisplay.pde
r46 r80 1 1 /* 2 * Displays text sent over the serial port (e.g. from the Serial Monitor) on 3 * an attached LCD. 2 LiquidCrystal Library - Serial Input 3 4 Demonstrates the use a 16x2 LCD display. The LiquidCrystal 5 library works with all LCD displays that are compatible with the 6 Hitachi HD44780 driver. There are many of them out there, and you 7 can usually tell them by the 16-pin interface. 8 9 This sketch displays text sent over the serial port 10 (e.g. from the Serial Monitor) on an attached LCD. 11 12 The circuit: 13 * LCD RS pin to digital pin 12 14 * LCD Enable pin to digital pin 11 15 * LCD D4 pin to digital pin 5 16 * LCD D5 pin to digital pin 4 17 * LCD D6 pin to digital pin 3 18 * LCD D7 pin to digital pin 2 19 * 10K resistor: 20 * ends to +5V and ground 21 * wiper to LCD VO pin (pin 3) 22 23 Library originally added 18 Apr 2008 24 by David A. Mellis 25 library modified 5 Jul 2009 26 by Limor Fried (http://www.ladyada.net) 27 example added 9 Jul 2009 28 by Tom Igoe 29 modified 25 July 2009 30 by David A. Mellis 31 32 http://www.arduino.cc/en/Tutorial/LiquidCrystal 4 33 */ 5 34 35 // include the library code: 6 36 #include <LiquidCrystal.h> 7 37 8 // LiquidCrystal display with: 9 // rs on pin 12 10 // rw on pin 11 11 // enable on pin 10 12 // d4, d5, d6, d7 on pins 5, 4, 3, 2 13 LiquidCrystal lcd(12, 11, 10, 5, 4, 3, 2); 38 // initialize the library with the numbers of the interface pins 39 LiquidCrystal lcd(12, 11, 5, 4, 3, 2); 14 40 15 void setup() 16 { 41 void setup(){ 42 // set up the LCD's number of rows and columns: 43 lcd.begin(16, 2); 44 // initialize the serial communications: 17 45 Serial.begin(9600); 18 46 } -
trunk/arduino/libraries/LiquidCrystal/keywords.txt
r46 r80 13 13 ####################################### 14 14 15 begin KEYWORD2 15 16 clear KEYWORD2 16 17 home KEYWORD2 17 18 print KEYWORD2 18 19 setCursor KEYWORD2 20 cursor KEYWORD2 21 noCursor KEYWORD2 22 blink KEYWORD2 23 noBlink KEYWORD2 24 display KEYWORD2 25 noDisplay KEYWORD2 26 autoscroll KEYWORD2 27 noAutoscroll KEYWORD2 28 leftToRight KEYWORD2 29 rightToLeft KEYWORD2 30 scrollDisplayLeft KEYWORD2 31 scrollDisplayRight KEYWORD2 32 createChar KEYWORD2 19 33 20 34 ####################################### -
trunk/arduino/libraries/Servo/Servo.cpp
r46 r80 1 /* 2 Servo.cpp - Interrupt driven Servo library for Arduino using 16 bit timers- Version 2 3 Copyright (c) 2009 Michael Margolis. All right reserved. 4 5 This library is free software; you can redistribute it and/or 6 modify it under the terms of the GNU Lesser General Public 7 License as published by the Free Software Foundation; either 8 version 2.1 of the License, or (at your option) any later version. 9 10 This library is distributed in the hope that it will be useful, 11 but WITHOUT ANY WARRANTY; without even the implied warranty of 12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 13 Lesser General Public License for more details. 14 15 You should have received a copy of the GNU Lesser General Public 16 License along with this library; if not, write to the Free Software 17 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA 18 */ 19 20 /* 21 22 A servo is activated by creating an instance of the Servo class passing the desired pin to the attach() method. 23 The servos are pulsed in the background using the value most recently written using the write() method 24 25 Note that analogWrite of PWM on pins associated with the timer are disabled when the first servo is attached. 26 Timers are seized as needed in groups of 12 servos - 24 servos use two timers, 48 servos will use four. 27 28 The methods are: 29 30 Servo - Class for manipulating servo motors connected to Arduino pins. 31 32 attach(pin ) - Attaches a servo motor to an i/o pin. 33 attach(pin, min, max ) - Attaches to a pin setting min and max values in microseconds 34 default min is 544, max is 2400 35 36 write() - Sets the servo angle in degrees. (invalid angle that is valid as pulse in microseconds is treated as microseconds) 37 writeMicroseconds() - Sets the servo pulse width in microseconds 38 read() - Gets the last written servo pulse width as an angle between 0 and 180. 39 readMicroseconds() - Gets the last written servo pulse width in microseconds. (was read_us() in first release) 40 attached() - Returns true if there is a servo attached. 41 detach() - Stops an attached servos from pulsing its i/o pin. 42 43 */ 44 1 45 #include <avr/interrupt.h> 2 #include <wiring.h> 3 #include <Servo.h> 4 5 /* 6 Servo.h - Hardware Servo Timer Library 7 Author: Jim Studt, jim@federated.com 8 Copyright (c) 2007 David A. Mellis. All right reserved. 9 10 This library is free software; you can redistribute it and/or 11 modify it under the terms of the GNU Lesser General Public 12 License as published by the Free Software Foundation; either 13 version 2.1 of the License, or (at your option) any later version. 14 15 This library is distributed in the hope that it will be useful, 16 but WITHOUT ANY WARRANTY; without even the implied warranty of 17 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 18 Lesser General Public License for more details. 19 20 You should have received a copy of the GNU Lesser General Public 21 License along with this library; if not, write to the Free Software 22 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA 23 */ 24 25 26 uint8_t Servo::attached9 = 0; 27 uint8_t Servo::attached10 = 0; 28 29 void Servo::seizeTimer1() 30 { 31 uint8_t oldSREG = SREG; 32 33 cli(); 34 TCCR1A = _BV(WGM11); /* Fast PWM, ICR1 is top */ 35 TCCR1B = _BV(WGM13) | _BV(WGM12) /* Fast PWM, ICR1 is top */ 36 | _BV(CS11) /* div 8 clock prescaler */ 37 ; 38 OCR1A = 3000; 39 OCR1B = 3000; 40 ICR1 = clockCyclesPerMicrosecond()*(20000L/8); // 20000 uS is a bit fast for the refresh, 20ms, but 41 // it keeps us from overflowing ICR1 at 20MHz clocks 42 // That "/8" at the end is the prescaler. 43 #if defined(__AVR_ATmega8__) 44 TIMSK &= ~(_BV(TICIE1) | _BV(OCIE1A) | _BV(OCIE1B) | _BV(TOIE1) ); 46 #include <WProgram.h> 47 48 #include "Servo.h" 49 50 #define usToTicks(_us) (( clockCyclesPerMicrosecond()* _us) / 8) // converts microseconds to tick (assumes prescale of 8) // 12 Aug 2009 51 #define ticksToUs(_ticks) (( (unsigned)_ticks * 8)/ clockCyclesPerMicrosecond() ) // converts from ticks back to microseconds 52 53 54 #define TRIM_DURATION 2 // compensation ticks to trim adjust for digitalWrite delays // 12 August 2009 55 56 //#define NBR_TIMERS (MAX_SERVOS / SERVOS_PER_TIMER) 57 58 static servo_t servos[MAX_SERVOS]; // static array of servo structures 59 static volatile int8_t Channel[_Nbr_16timers ]; // counter for the servo being pulsed for each timer (or -1 if refresh interval) 60 61 uint8_t ServoCount = 0; // the total number of attached servos 62 63 64 // convenience macros 65 #define SERVO_INDEX_TO_TIMER(_servo_nbr) ((timer16_Sequence_t)(_servo_nbr / SERVOS_PER_TIMER)) // returns the timer controlling this servo 66 #define SERVO_INDEX_TO_CHANNEL(_servo_nbr) (_servo_nbr % SERVOS_PER_TIMER) // returns the index of the servo on this timer 67 #define SERVO_INDEX(_timer,_channel) ((_timer*SERVOS_PER_TIMER) + _channel) // macro to access servo index by timer and channel 68 #define SERVO(_timer,_channel) (servos[SERVO_INDEX(_timer,_channel)]) // macro to access servo class by timer and channel 69 70 #define SERVO_MIN() (MIN_PULSE_WIDTH - this->min * 4) // minimum value in uS for this servo 71 #define SERVO_MAX() (MAX_PULSE_WIDTH - this->max * 4) // maximum value in uS for this servo 72 73 /************ static functions common to all instances ***********************/ 74 75 static inline void handle_interrupts(timer16_Sequence_t timer, volatile uint16_t *TCNTn, volatile uint16_t* OCRnA) 76 { 77 if( Channel[timer] < 0 ) 78 *TCNTn = 0; // channel set to -1 indicated that refresh interval completed so reset the timer 79 else{ 80 if( SERVO_INDEX(timer,Channel[timer]) < ServoCount && SERVO(timer,Channel[timer]).Pin.isActive == true ) 81 digitalWrite( SERVO(timer,Channel[timer]).Pin.nbr,LOW); // pulse this channel low if activated 82 } 83 84 Channel[timer]++; // increment to the next channel 85 if( SERVO_INDEX(timer,Channel[timer]) < ServoCount && Channel[timer] < SERVOS_PER_TIMER) { 86 *OCRnA = *TCNTn + SERVO(timer,Channel[timer]).ticks; 87 if(SERVO(timer,Channel[timer]).Pin.isActive == true) // check if activated 88 digitalWrite( SERVO(timer,Channel[timer]).Pin.nbr,HIGH); // its an active channel so pulse it high 89 } 90 else { 91 // finished all channels so wait for the refresh period to expire before starting over 92 if( (unsigned)*TCNTn < (usToTicks(REFRESH_INTERVAL) + 4) ) // allow a few ticks to ensure the next OCR1A not missed 93 *OCRnA = (unsigned int)usToTicks(REFRESH_INTERVAL); 94 else 95 *OCRnA = *TCNTn + 4; // at least REFRESH_INTERVAL has elapsed 96 Channel[timer] = -1; // this will get incremented at the end of the refresh period to start again at the first channel 97 } 98 } 99 100 #ifndef WIRING // Wiring pre-defines signal handlers so don't define any if compiling for the Wiring platform 101 // Interrupt handlers for Arduino 102 #if defined(_useTimer1) 103 SIGNAL (TIMER1_COMPA_vect) 104 { 105 handle_interrupts(_timer1, &TCNT1, &OCR1A); 106 } 107 #endif 108 109 #if defined(_useTimer3) 110 SIGNAL (TIMER3_COMPA_vect) 111 { 112 handle_interrupts(_timer3, &TCNT3, &OCR3A); 113 } 114 #endif 115 116 #if defined(_useTimer4) 117 SIGNAL (TIMER4_COMPA_vect) 118 { 119 handle_interrupts(_timer4, &TCNT4, &OCR4A); 120 } 121 #endif 122 123 #if defined(_useTimer5) 124 SIGNAL (TIMER5_COMPA_vect) 125 { 126 handle_interrupts(_timer5, &TCNT5, &OCR5A); 127 } 128 #endif 129 130 #elif defined WIRING 131 // Interrupt handlers for Wiring 132 #if defined(_useTimer1) 133 void Timer1Service() 134 { 135 handle_interrupts(_timer1, &TCNT1, &OCR1A); 136 } 137 #endif 138 #if defined(_useTimer3) 139 void Timer3Service() 140 { 141 handle_interrupts(_timer3, &TCNT3, &OCR3A); 142 } 143 #endif 144 #endif 145 146 147 static void initISR(timer16_Sequence_t timer) 148 { 149 #if defined (_useTimer1) 150 if(timer == _timer1) { 151 TCCR1A = 0; // normal counting mode 152 TCCR1B = _BV(CS11); // set prescaler of 8 153 TCNT1 = 0; // clear the timer count 154 #if defined(__AVR_ATmega8__)|| defined(__AVR_ATmega128__) 155 TIFR |= _BV(OCF1A); // clear any pending interrupts; 156 TIMSK |= _BV(OCIE1A) ; // enable the output compare interrupt 45 157 #else 46 TIMSK1 &= ~(_BV(OCIE1A) | _BV(OCIE1B) | _BV(TOIE1) ); 47 #endif 48 49 SREG = oldSREG; // undo cli() 50 } 51 52 void Servo::releaseTimer1() {} 53 54 #define NO_ANGLE (0xff) 55 56 Servo::Servo() : pin(0), angle(NO_ANGLE) {} 57 58 uint8_t Servo::attach(int pinArg) 59 { 60 return attach(pinArg, 544, 2400); 61 } 62 63 uint8_t Servo::attach(int pinArg, int min, int max) 64 { 65 if (pinArg != 9 && pinArg != 10) return 0; 66 67 min16 = min / 16; 68 max16 = max / 16; 69 70 pin = pinArg; 71 angle = NO_ANGLE; 72 digitalWrite(pin, LOW); 73 pinMode(pin, OUTPUT); 74 75 if (!attached9 && !attached10) seizeTimer1(); 76 77 if (pin == 9) { 78 attached9 = 1; 79 TCCR1A = (TCCR1A & ~_BV(COM1A0)) | _BV(COM1A1); 80 } 81 82 if (pin == 10) { 83 attached10 = 1; 84 TCCR1A = (TCCR1A & ~_BV(COM1B0)) | _BV(COM1B1); 85 } 86 return 1; 87 } 88 89 void Servo::detach() 90 { 91 // muck with timer flags 92 if (pin == 9) { 93 attached9 = 0; 94 TCCR1A = TCCR1A & ~_BV(COM1A0) & ~_BV(COM1A1); 95 pinMode(pin, INPUT); 158 // here if not ATmega8 or ATmega128 159 TIFR1 |= _BV(OCF1A); // clear any pending interrupts; 160 TIMSK1 |= _BV(OCIE1A) ; // enable the output compare interrupt 161 #endif 162 #if defined(WIRING) 163 timerAttach(TIMER1OUTCOMPAREA_INT, Timer1Service); 164 #endif 96 165 } 97 98 if (pin == 10) { 99 attached10 = 0; 100 TCCR1A = TCCR1A & ~_BV(COM1B0) & ~_BV(COM1B1); 101 pinMode(pin, INPUT); 102 } 103 104 if (!attached9 && !attached10) releaseTimer1(); 105 } 106 107 void Servo::write(int angleArg) 108 { 109 uint16_t p; 110 111 if (angleArg < 0) angleArg = 0; 112 if (angleArg > 180) angleArg = 180; 113 angle = angleArg; 114 115 // bleh, have to use longs to prevent overflow, could be tricky if always a 16MHz clock, but not true 116 // That 8L on the end is the TCNT1 prescaler, it will need to change if the clock's prescaler changes, 117 // but then there will likely be an overflow problem, so it will have to be handled by a human. 118 p = (min16*16L*clockCyclesPerMicrosecond() + (max16-min16)*(16L*clockCyclesPerMicrosecond())*angle/180L)/8L; 119 if (pin == 9) OCR1A = p; 120 if (pin == 10) OCR1B = p; 121 } 122 123 uint8_t Servo::read() 124 { 125 return angle; 126 } 127 128 uint8_t Servo::attached() 129 { 130 if (pin == 9 && attached9) return 1; 131 if (pin == 10 && attached10) return 1; 132 return 0; 133 } 166 #endif 167 168 #if defined (_useTimer3) 169 if(timer == _timer3) { 170 TCCR3A = 0; // normal counting mode 171 TCCR3B = _BV(CS31); // set prescaler of 8 172 TCNT3 = 0; // clear the timer count 173 #if defined(__AVR_ATmega128__) 174 TIFR |= _BV(OCF3A); // clear any pending interrupts; 175 ETIMSK |= _BV(OCIE3A); // enable the output compare interrupt 176 #else 177 TIFR3 = _BV(OCF3A); // clear any pending interrupts; 178 TIMSK3 = _BV(OCIE3A) ; // enable the output compare interrupt 179 #endif 180 #if defined(WIRING) 181 timerAttach(TIMER3OUTCOMPAREA_INT, Timer3Service); // for Wiring platform only 182 #endif 183 } 184 #endif 185 186 #if defined (_useTimer4) 187 if(timer == _timer4) { 188 TCCR4A = 0; // normal counting mode 189 TCCR4B = _BV(CS41); // set prescaler of 8 190 TCNT4 = 0; // clear the timer count 191 TIFR4 = _BV(OCF4A); // clear any pending interrupts; 192 TIMSK4 = _BV(OCIE4A) ; // enable the output compare interrupt 193 } 194 #endif 195 196 #if defined (_useTimer5) 197 if(timer == _timer5) { 198 TCCR5A = 0; // normal counting mode 199 TCCR5B = _BV(CS51); // set prescaler of 8 200 TCNT5 = 0; // clear the timer count 201 TIFR5 = _BV(OCF5A); // clear any pending interrupts; 202 TIMSK5 = _BV(OCIE5A) ; // enable the output compare interrupt 203 } 204 #endif 205 } 206 207 static void finISR(timer16_Sequence_t timer) 208 { 209 //disable use of the given timer 210 #if defined WIRING // Wiring 211 if(timer == _timer1) { 212 #if defined(__AVR_ATmega1281__)||defined(__AVR_ATmega2561__) 213 TIMSK1 &= ~_BV(OCIE1A) ; // disable timer 1 output compare interrupt 214 #else 215 TIMSK &= ~_BV(OCIE1A) ; // disable timer 1 output compare interrupt 216 #endif 217 timerDetach(TIMER1OUTCOMPAREA_INT); 218 } 219 else if(timer == _timer3) { 220 #if defined(__AVR_ATmega1281__)||defined(__AVR_ATmega2561__) 221 TIMSK3 &= ~_BV(OCIE3A); // disable the timer3 output compare A interrupt 222 #else 223 ETIMSK &= ~_BV(OCIE3A); // disable the timer3 output compare A interrupt 224 #endif 225 timerDetach(TIMER3OUTCOMPAREA_INT); 226 } 227 #else 228 //For arduino - in future: call here to a currently undefined function to reset the timer 229 #endif 230 } 231 232 static boolean isTimerActive(timer16_Sequence_t timer) 233 { 234 // returns true if any servo is active on this timer 235 for(uint8_t channel=0; channel < SERVOS_PER_TIMER; channel++) { 236 if(SERVO(timer,channel).Pin.isActive == true) 237 return true; 238 } 239 return false; 240 } 241 242 243 /****************** end of static functions ******************************/ 244 245 Servo::Servo() 246 { 247 if( ServoCount < MAX_SERVOS) { 248 this->servoIndex = ServoCount++; // assign a servo index to this instance 249 servos[this->servoIndex].ticks = usToTicks(DEFAULT_PULSE_WIDTH); // store default values - 12 Aug 2009 250 } 251 else 252 this->servoIndex = INVALID_SERVO ; // too many servos 253 } 254 255 uint8_t Servo::attach(int pin) 256 { 257 return this->attach(pin, MIN_PULSE_WIDTH, MAX_PULSE_WIDTH); 258 } 259 260 uint8_t Servo::attach(int pin, int min, int max) 261 { 262 if(this->servoIndex < MAX_SERVOS ) { 263 pinMode( pin, OUTPUT) ; // set servo pin to output 264 servos[this->servoIndex].Pin.nbr = pin; 265 // todo min/max check: abs(min - MIN_PULSE_WIDTH) /4 < 128 266 this->min = (MIN_PULSE_WIDTH - min)/4; //resolution of min/max is 4 uS 267 this->max = (MAX_PULSE_WIDTH - max)/4; 268 // initialize the timer if it has not already been initialized 269 timer16_Sequence_t timer = SERVO_INDEX_TO_TIMER(servoIndex); 270 if(isTimerActive(timer) == false) 271 initISR(timer); 272 servos[this->servoIndex].Pin.isActive = true; // this must be set after the check for isTimerActive 273 } 274 return this->servoIndex ; 275 } 276 277 void Servo::detach() 278 { 279 servos[this->servoIndex].Pin.isActive = false; 280 timer16_Sequence_t timer = SERVO_INDEX_TO_TIMER(servoIndex); 281 if(isTimerActive(timer) == false) { 282 finISR(timer); 283 } 284 } 285 286 void Servo::write(int value) 287 { 288 if(value < MIN_PULSE_WIDTH) 289 { // treat values less than 544 as angles in degrees (valid values in microseconds are handled as microseconds) 290 if(value < 0) value = 0; 291 if(value > 180) value = 180; 292 value = map(value, 0, 180, SERVO_MIN(), SERVO_MAX()); 293 } 294 this->writeMicroseconds(value); 295 } 296 297 void Servo::writeMicroseconds(int value) 298 { 299 // calculate and store the values for the given channel 300 byte channel = this->servoIndex; 301 if( (channel >= 0) && (channel < MAX_SERVOS) ) // ensure channel is valid 302 { 303 if( value < SERVO_MIN() ) // ensure pulse width is valid 304 value = SERVO_MIN(); 305 else if( value > SERVO_MAX() ) 306 value = SERVO_MAX(); 307 308 value = value - TRIM_DURATION; 309 value = usToTicks(value); // convert to ticks after compensating for interrupt overhead - 12 Aug 2009 310 311 uint8_t oldSREG = SREG; 312 cli(); 313 servos[channel].ticks = value; 314 SREG = oldSREG; 315 } 316 } 317 318 int Servo::read() // return the value as degrees 319 { 320 return map( this->readMicroseconds()+1, SERVO_MIN(), SERVO_MAX(), 0, 180); 321 } 322 323 int Servo::readMicroseconds() 324 { 325 unsigned int pulsewidth; 326 if( this->servoIndex != INVALID_SERVO ) 327 pulsewidth = ticksToUs(servos[this->servoIndex].ticks) + TRIM_DURATION ; // 12 aug 2009 328 else 329 pulsewidth = 0; 330 331 return pulsewidth; 332 } 333 334 bool Servo::attached() 335 { 336 return servos[this->servoIndex].Pin.isActive ; 337 } -
trunk/arduino/libraries/Servo/Servo.h
r46 r80 1 #ifndef Servo_h2 #define Servo_h3 4 1 /* 5 Servo.h - Hardware Servo Timer Library 6 Author: Jim Studt, jim@federated.com 7 Copyright (c) 2007 David A. Mellis. All right reserved. 2 Servo.h - Interrupt driven Servo library for Arduino using 16 bit timers- Version 2 3 Copyright (c) 2009 Michael Margolis. All right reserved. 8 4 9 5 This library is free software; you can redistribute it and/or … … 22 18 */ 23 19 20 /* 21 22 A servo is activated by creating an instance of the Servo class passing the desired pin to the attach() method. 23 The servos are pulsed in the background using the value most recently written using the write() method 24 25 Note that analogWrite of PWM on pins associated with the timer are disabled when the first servo is attached. 26 Timers are seized as needed in groups of 12 servos - 24 servos use two timers, 48 servos will use four. 27 The sequence used to sieze timers is defined in timers.h 28 29 The methods are: 30 31 Servo - Class for manipulating servo motors connected to Arduino pins. 32 33 attach(pin ) - Attaches a servo motor to an i/o pin. 34 attach(pin, min, max ) - Attaches to a pin setting min and max values in microseconds 35 default min is 544, max is 2400 36 37 write() - Sets the servo angle in degrees. (invalid angle that is valid as pulse in microseconds is treated as microseconds) 38 writeMicroseconds() - Sets the servo pulse width in microseconds 39 read() - Gets the last written servo pulse width as an angle between 0 and 180. 40 readMicroseconds() - Gets the last written servo pulse width in microseconds. (was read_us() in first release) 41 attached() - Returns true if there is a servo attached. 42 detach() - Stops an attached servos from pulsing its i/o pin. 43 */ 44 45 #ifndef Servo_h 46 #define Servo_h 47 24 48 #include <inttypes.h> 49 50 /* 51 * Defines for 16 bit timers used with Servo library 52 * 53 * If _useTimerX is defined then TimerX is a 16 bit timer on the curent board 54 * timer16_Sequence_t enumerates the sequence that the timers should be allocated 55 * _Nbr_16timers indicates how many 16 bit timers are available. 56 * 57 */ 58 59 // Say which 16 bit timers can be used and in what order 60 #if defined(__AVR_ATmega1280__) 61 #define _useTimer5 62 #define _useTimer1 63 #define _useTimer3 64 #define _useTimer4 65 typedef enum { _timer5, _timer1, _timer3, _timer4, _Nbr_16timers } timer16_Sequence_t ; 66 67 #elif defined(__AVR_ATmega32U4__) 68 #define _useTimer3 69 #define _useTimer1 70 typedef enum { _timer3, _timer1, _Nbr_16timers } timer16_Sequence_t ; 71 72 #elif defined(__AVR_AT90USB646__) || defined(__AVR_AT90USB1286__) 73 #define _useTimer3 74 #define _useTimer1 75 typedef enum { _timer3, _timer1, _Nbr_16timers } timer16_Sequence_t ; 76 77 #elif defined(__AVR_ATmega128__) ||defined(__AVR_ATmega1281__)||defined(__AVR_ATmega2561__) 78 #define _useTimer3 79 #define _useTimer1 80 typedef enum { _timer3, _timer1, _Nbr_16timers } timer16_Sequence_t ; 81 82 #else // everything else 83 #define _useTimer1 84 typedef enum { _timer1, _Nbr_16timers } timer16_Sequence_t ; 85 #endif 86 87 #define Servo_VERSION 2 // software version of this library 88 89 #define MIN_PULSE_WIDTH 544 // the shortest pulse sent to a servo 90 #define MAX_PULSE_WIDTH 2400 // the longest pulse sent to a servo 91 #define DEFAULT_PULSE_WIDTH 1500 // default pulse width when servo is attached 92 #define REFRESH_INTERVAL 20000 // minumim time to refresh servos in microseconds 93 94 #define SERVOS_PER_TIMER 12 // the maximum number of servos controlled by one timer 95 #define MAX_SERVOS (_Nbr_16timers * SERVOS_PER_TIMER) 96 97 #define INVALID_SERVO 255 // flag indicating an invalid servo index 98 99 typedef struct { 100 uint8_t nbr :6 ; // a pin number from 0 to 63 101 uint8_t isActive :1 ; // true if this channel is enabled, pin not pulsed if false 102 } ServoPin_t ; 103 104 typedef struct { 105 ServoPin_t Pin; 106 unsigned int ticks; 107 } servo_t; 25 108 26 109 class Servo 27 110 { 28 private: 29 uint8_t pin; 30 uint8_t angle; // in degrees 31 uint8_t min16; // minimum pulse, 16uS units (default is 34) 32 uint8_t max16; // maximum pulse, 16uS units, 0-4ms range (default is 150) 33 static void seizeTimer1(); 34 static void releaseTimer1(); 35 static uint8_t attached9; 36 static uint8_t attached10; 37 public: 38 Servo(); 39 uint8_t attach(int); 40 // pulse length for 0 degrees in microseconds, 544uS default 41 // pulse length for 180 degrees in microseconds, 2400uS default 42 uint8_t attach(int, int, int); 43 // attach to a pin, sets pinMode, returns 0 on failure, won't 44 // position the servo until a subsequent write() happens 45 // Only works for 9 and 10. 46 void detach(); 47 void write(int); // specify the angle in degrees, 0 to 180 48 uint8_t read(); 49 uint8_t attached(); 111 public: 112 Servo(); 113 uint8_t attach(int pin); // attach the given pin to the next free channel, sets pinMode, returns channel number or 0 if failure 114 uint8_t attach(int pin, int min, int max); // as above but also sets min and max values for writes. 115 void detach(); 116 void write(int value); // if value is < 200 its treated as an angle, otherwise as pulse width in microseconds 117 void writeMicroseconds(int value); // Write pulse width in microseconds 118 int read(); // returns current pulse width as an angle between 0 and 180 degrees 119 int readMicroseconds(); // returns current pulse width in microseconds for this servo (was read_us() in first release) 120 bool attached(); // return true if this servo is attached, otherwise false 121 private: 122 uint8_t servoIndex; // index into the channel data for this servo 123 int8_t min; // minimum is this value times 4 added to MIN_PULSE_WIDTH 124 int8_t max; // maximum is this value times 4 added to MAX_PULSE_WIDTH 50 125 }; 51 126 -
trunk/arduino/libraries/Servo/keywords.txt
r46 r80 7 7 ####################################### 8 8 9 Servo KEYWORD19 Servo KEYWORD1 10 10 11 11 ####################################### 12 12 # Methods and Functions (KEYWORD2) 13 13 ####################################### 14 attach KEYWORD2 15 detach KEYWORD2 16 write KEYWORD2 17 read KEYWORD2 18 attached KEYWORD2 14 attach KEYWORD2 15 detach KEYWORD2 16 write KEYWORD2 17 read KEYWORD2 18 attached KEYWORD2 19 writeMicroseconds KEYWORD2 20 readMicroseconds KEYWORD2 19 21 20 22 ####################################### -
trunk/arduino/libraries/Wire/utility/twi.c
r46 r80 88 88 89 89 // enable twi module, acks, and twi interrupt 90 TWCR = _BV(TWEN) | _BV(TWIE) | _BV(TWEA);90 TWCR = _BV(TWEN) | _BV(TWIE) | _BV(TWEA); 91 91 92 // allocate buffers92 // allocate buffers 93 93 twi_masterBuffer = (uint8_t*) calloc(TWI_BUFFER_LENGTH, sizeof(uint8_t)); 94 94 twi_txBuffer = (uint8_t*) calloc(TWI_BUFFER_LENGTH, sizeof(uint8_t)); … … 136 136 // initialize buffer iteration vars 137 137 twi_masterBufferIndex = 0; 138 twi_masterBufferLength = length; 138 twi_masterBufferLength = length-1; // This is not intuitive, read on... 139 // On receive, the previously configured ACK/NACK setting is transmitted in 140 // response to the received byte before the interrupt is signalled. 141 // Therefor we must actually set NACK when the _next_ to last byte is 142 // received, causing that NACK to be sent in response to receiving the last 143 // expected byte of data. 139 144 140 145 // build sla+w, slave device address + w bit 141 146 twi_slarw = TW_READ; 142 twi_slarw |= address << 1;147 twi_slarw |= address << 1; 143 148 144 149 // send start condition 145 TWCR = _BV(TWEN) | _BV(TWIE) | _BV(TWEA) | _BV(TWINT) | _BV(TWSTA);146 147 // wait for read operation to complete148 while(TWI_MRX == twi_state){149 continue;150 }150 TWCR = _BV(TWEN) | _BV(TWIE) | _BV(TWEA) | _BV(TWINT) | _BV(TWSTA); 151 152 // wait for read operation to complete 153 while(TWI_MRX == twi_state){ 154 continue; 155 } 151 156 152 157 if (twi_masterBufferIndex < length) 153 length = twi_masterBufferIndex;158 length = twi_masterBufferIndex; 154 159 155 160 // copy twi buffer to data … … 158 163 } 159 164 160 return length;165 return length; 161 166 } 162 167 … … 203 208 // build sla+w, slave device address + w bit 204 209 twi_slarw = TW_WRITE; 205 twi_slarw |= address << 1;210 twi_slarw |= address << 1; 206 211 207 212 // send start condition 208 TWCR = _BV(TWEN) | _BV(TWIE) | _BV(TWEA) | _BV(TWINT) | _BV(TWSTA);209 210 // wait for write operation to complete211 while(wait && (TWI_MTX == twi_state)){212 continue;213 }214 215 if (twi_error == 0xFF)216 return 0; // success217 else if (twi_error == TW_MT_SLA_NACK)218 return 2; // error: address send, nack received219 else if (twi_error == TW_MT_DATA_NACK)220 return 3; // error: data send, nack received221 else222 return 4; // other twi error213 TWCR = _BV(TWEN) | _BV(TWIE) | _BV(TWEA) | _BV(TWINT) | _BV(TWSTA); 214 215 // wait for write operation to complete 216 while(wait && (TWI_MTX == twi_state)){ 217 continue; 218 } 219 220 if (twi_error == 0xFF) 221 return 0; // success 222 else if (twi_error == TW_MT_SLA_NACK) 223 return 2; // error: address send, nack received 224 else if (twi_error == TW_MT_DATA_NACK) 225 return 3; // error: data send, nack received 226 else 227 return 4; // other twi error 223 228 } 224 229 … … 286 291 void twi_reply(uint8_t ack) 287 292 { 288 // transmit master read ready signal, with or without ack289 if(ack){290 TWCR = _BV(TWEN) | _BV(TWIE) | _BV(TWINT) | _BV(TWEA);293 // transmit master read ready signal, with or without ack 294 if(ack){ 295 TWCR = _BV(TWEN) | _BV(TWIE) | _BV(TWINT) | _BV(TWEA); 291 296 }else{ 292 297 TWCR = _BV(TWEN) | _BV(TWIE) | _BV(TWINT);
