UArmProtocol.ino
#include <uarm_library.h>
#include <EEPROM.h>
#define MAX_DATA_BYTES 64 // max number of data bytes in incoming messages
#define UARM_FIRMATA_MAJOR_VERSION 1
#define UARM_FIRMATA_MINOR_VERSION 3
#define UARM_FIRMATA_BUGFIX 2
#define UARM_FIRMWARE_MAJOR_VERSION 1
#define UARM_FIRMWARE_MINOR_VERSION 7
#define UARM_FIRMWARE_BUGFIX 2
#define START_SYSEX 0xF0 // start a MIDI Sysex message
#define END_SYSEX 0xF7 // end a MIDI Sysex message
#define UARM_CODE (0XAA)
#define READ_ANGLE (0X10)
#define WRITE_ANGLE (0X11)
#define READ_COORDS (0X12)
#define WRITE_COORDS (0X13)
#define READ_DIGITAL (0X14)
#define WRITE_DIGITAL (0X15)
#define READ_ANALOG (0X16)
#define WRITE_ANALOG (0X17)
#define READ_EEPROM (0X1A)
#define WRITE_EEPROM (0X1B)
#define SERVO_STATUS (0X1C)
#define PUMP_STATUS (0X1D)
#define WRITE_STRETCH (0X1E)
#define WRITE_LEFT_RIGHT_ANGLE (0X1F)
#define GRIPPER_STATUS (0X20)
#define READ_SERIAL_NUMBER (0x21)
#define WRITE_SERIAL_NUMBER (0x22)
#define REPORT_FIRMWARE_VERSION (0x23)
#define BUZZER_ALERT (0x24)
#define DATA_TYPE_BYTE 1
#define DATA_TYPE_INTEGER 2
#define DATA_TYPE_FLOAT 4
{
Serial.begin(57600);
}
{
while(Serial.available())
processInput();
}
{
{
byte uarmCommand;
uarmCommand = argv[0];
// CMD 10 Read Angle
{
byte servo_num = argv[1];
boolean withOffset = argv[2]; // if servo_offset = 0 there is offset inside
Serial.write(START_SYSEX);
Serial.write(UARM_CODE);
Serial.write(servo_num);
sendFloatAsThree7bitBytes(angle);
Serial.write(END_SYSEX);
return true;
}
// CMD 11 Write Angle
{
byte servo_num = argv[1];
double servo_angle = argv[2] + (argv[3] << 7) + float(argv[4])/100;
boolean writeWithOffset = argv[5];
return true;
}
// CMD 12 Read Coords
{
Serial.write(START_SYSEX);
Serial.write(UARM_CODE);
Serial.write(READ_COORDS);
Serial.write(END_SYSEX);
return true;
}
// CMD 13 Write Coords
{
float x = argv[2] + (argv[3] << 7) + float(argv[4])/100;
if(argv[1] == 1)
x = -x;
float y = argv[6] + (argv[7] << 7) + float(argv[8])/100;
if(argv[5] == 1)
y = -y;
float z = argv[10] + (argv[11] << 7) + float(argv[12])/100;
if(argv[9] == 1)
z = -z;
float hand_angle = argv[13] + (argv[14] << 7) + float(argv[15])/100;
byte relative_flags = argv[16];
float time_spend = argv[17] + (argv[18] << 7) + float(argv[19])/100;
byte path_type = argv[20];
byte ease_type = argv[21];
boolean enable_hand = false;
if (argv[22] == 1 || argv[22] ==0)
enable_hand = argv[22];
delay(5);
delay(10);
}
// CMD 14 Read Digital
{
byte pin_num = argv[1];
byte pin_mode = argv[2]; // 0 means input 1 means input_pullup
{
Serial.write(START_SYSEX);
Serial.write(UARM_CODE);
Serial.write(pin_num);
pin_mode == 1 ? pinMode(pin_num, INPUT_PULLUP) : pinMode(pin_num, INPUT);
Serial.write(digitalRead(pin_num));
Serial.write(END_SYSEX);
}
return true;
}
// CMD 15 Write Digital
{
byte pin_num= argv[1];
pinMode(pin_num, OUTPUT);
byte pin_mode = argv[2];
pin_mode == 1 ? digitalWrite(pin_num,HIGH) : digitalWrite(pin_num,LOW);
return true;
}
// CMD 16 Read Analog
{
byte pin_num = argv[1];
{
Serial.write(START_SYSEX);
Serial.write(UARM_CODE);
Serial.write(pin_num);
sendValueAsTwo7bitBytes(analogRead(pin_num));
Serial.write(END_SYSEX);
}
return true;
}
// CMD 17 Write Analog
{
byte pin_num= argv[1];
pinMode(pin_num, OUTPUT);
double analog_val = argv[2] + (argv[3] << 7);
analogWrite(pin_num,constrain(analog_val,0,255));
return true;
}
// CMD 1A Read EEPROM
{
byte data_type = argv[1];
int eeprom_add = argv[2] + (argv[3] << 7);
Serial.write(START_SYSEX);
Serial.write(UARM_CODE);
Serial.write(READ_EEPROM);
sendValueAsTwo7bitBytes(eeprom_add);
switch(data_type)
{
{
sendValueAsTwo7bitBytes(EEPROM.read(eeprom_add));
break;
}
{
int i_val = 0;
sendIntegerAsThree7bitBytes(EEPROM.get(eeprom_add, i_val));
break;
}
{
float f_val = 0.0f;
sendFloatAsFour7bitBytes(EEPROM.get(eeprom_add,f_val));
break;
}
}
Serial.write(END_SYSEX);
return true;
}
// CMD 1B Write EEPROM
{
byte data_type = argv[1];
byte eeprom_add = argv[2] + (argv[3] << 7);
// byte eeprom_val = argv[3] + (argv[4] << 7);
// EEPROM.write(eeprom_add,eeprom_val);
switch(data_type)
{
case DATA_TYPE_BYTE:
{
EEPROM.write(eeprom_add,argv[4] + (argv[5] << 7));
break;
}
case DATA_TYPE_INTEGER:
{
int int_val = 0;
int_val = argv[5] + (argv[6] << 7);
int_val = ((argv[4] == 1) ? -int_val : int_val);
EEPROM.put(eeprom_add, int_val);
break;
}
case DATA_TYPE_FLOAT:
{
float f_val = argv[5] + (argv[6] << 7) + float(argv[7])/100;
f_val = ((argv[4] == 1) ? -f_val : f_val);
EEPROM.put(eeprom_add, f_val);
break;
}
}
return true;
}
// CMD 1C Servo Attach or Detach
{
// uarm.detach_all_servos();
byte servo_num = argv[1];
boolean servo_status = argv[2] == 0 ? false : true;
return true;
}
// CMD 1D Pump Status
{
byte pump_status = argv[1];
return true;
}
// CMD 20 GRIPPER Status
{
byte gripper_status = argv[1];
return true;
}
//0X1E WRITE_STRETCH
{
double length = argv[2] + (argv[3] << 7) + float(argv[4])/100;
length = argv[1] == 1 ? -length : length;
double height = argv[6] + (argv[7] << 7) + float(argv[8])/100;
height = argv[5] == 1 ? -height : height;
return true;
}
//0X1F WRITE_LEFT_RIGHT_ANGLE
{
double left = argv[1] + (argv[2] << 7) + float(argv[3])/100;
double right = argv[4] + (argv[5] << 7) + float(argv[6])/100;
boolean withOffset = argv[7];
return true;
}
//0X22 WRITE_SERIAL_NUMBER
{
for(byte i=0; i<14; i++){
EEPROM.write(SERIAL_NUMBER_ADDRESS+i+1, argv[i+1]);
}
return true;
}
//0X21 READ_SERIAL_NUMBER
{
Serial.write(START_SYSEX);
Serial.write(UARM_CODE);
Serial.write(READ_SERIAL_NUMBER);
for(byte i=0; i<14; i++) {
byte c = EEPROM.read(SERIAL_NUMBER_ADDRESS+i+1);
Serial.write(c);
}
}
Serial.write(END_SYSEX);
return true;
}
//0X23 REPORT_FIRMWARE_VERSION
{
Serial.write(START_SYSEX);
Serial.write(UARM_CODE);
Serial.write(REPORT_FIRMWARE_VERSION);
Serial.write(UARM_FIRMWARE_MAJOR_VERSION);
Serial.write(UARM_FIRMWARE_MINOR_VERSION);
Serial.write(UARM_FIRMWARE_BUGFIX);
Serial.write(END_SYSEX);
return true;
}
{
byte times = argv[1];
byte run_time = argv[2];
byte stop_time = argv[3];
return true;
}
}
return false;
}
{
int inputData = Serial.read();
if (inputData != -1) {
parse(inputData);
}
}
void parse(byte inputData)
{
int command;
if (parsingSysex) {
if (inputData == END_SYSEX) {
//stop sysex byte
parsingSysex = false;
//fire off handler function
} else {
//normal data byte - add to buffer
storedInputData[sysexBytesRead] = inputData;
}
}
else {
// remove channel info from command byte if less than 0xF0
if (inputData < 0xF0) {
command = inputData & 0xF0;
} else {
command = inputData;
// commands in the 0xF* range don't use channel data
}
switch (command) {
case START_SYSEX:
parsingSysex = true;
sysexBytesRead = 0;
break;
}
}
}
{
switch (storedInputData[0]) {
default:
}
}
{
Serial.write(value & 0x7F);
Serial.write(value >> 7 & 0x7F);
}
int int_val = val;
int decimal_val = int(round((val - int_val)*100));
Serial.write(val > 0 ? 0 : 1);
Serial.write(abs(int_val) & B01111111 );
Serial.write(abs(int_val) >> 7 & B01111111);
Serial.write(abs(decimal_val) & 0x7F );
}
int int_val = val;
int decimal_val = int(round((val - int_val)*100));
Serial.write(abs(int_val) & B01111111 );
Serial.write(abs(int_val) >> 7 & B01111111);
Serial.write(abs(decimal_val) & 0x7F );
}
int symbol = val > 0 ? 0 : 1;
Serial.write(symbol);
Serial.write(abs(val) & B01111111 );
Serial.write(abs(val) >> 7 & B01111111);
}