objective c - Arduino State Machine -
this cross-post answered original question here.
i'm not sure how go executing 3 functions i'm after (as introducing more 3 in future).
i trying fade/blink selected colour of rgb led (and perhaps introduce more functions in future) rgb data coming ios , sent rfduino ble module.
sends "fade" string module picked rfduinoble_onreceive (char *data, int len)
on arduino end.
- (ibaction)fadebuttonpressed:(id)sender { [rfduino send:[@"fade" datausingencoding:nsutf8stringencoding]]; } - (ibaction)blinkbuttonpressed:(id)sender { [rfduino send:[@"blink" datausingencoding:nsutf8stringencoding]]; }
selected color:
- (void)setcolor { nslog(@"colors: rgb %f %f %f", red, green, blue); uicolor *color = [uicolor colorwithred:red green:green blue:blue alpha:1.0]; [colorswatch sethighlighted:yes]; [colorswatch settintcolor:color]; uint8_t tx[3] = { red * 255, green * 255, blue * 255 }; nsdata *data = [nsdata datawithbytes:(void*)&tx length:3]; [rfduino send:data]; }
this how set rgb colour:
void rfduinoble_onreceive (char *data, int len) { if (len >= 3) { // rgb values. uint8_t red = data[0]; uint8_t green = data[1]; uint8_t blue = data[2]; // set pwm each led. analogwrite(rgb2_pin, red); analogwrite(rgb3_pin, green); analogwrite(rgb4_pin, blue); } }
this provided answer compiles on arduino, have no idea how execute functions , where?
#include <rfduinoble.h> int state; char command; string hexstring; // rgb pins. int redpin = 2; int grnpin = 3; int blupin = 4; void setup () { state = 1; pinmode(redpin, output); pinmode(grnpin, output); pinmode(blupin, output); // data want appear in advertisement // (the devicename length plus advertisement length must <= 18 bytes. rfduinoble.devicename = "ios"; rfduinoble.advertisementinterval = milliseconds(300); rfduinoble.txpowerlevel = -20; rfduinoble.advertisementdata = "rgb"; // start ble stack. rfduinoble.begin(); } void loop () { //rfduino_ulpdelay(infinite); } void processcommand (int command, string hex) { // hex ? // command ? } void rfduinoble_onreceive (char *data, int len) { (int = 0; < len; i++) { statemachine(data[i]); } } void statemachine (char data) { switch (state) { case 1: if (data == 1) { state = 2; } break; case 2: if (data == 'b' || data == 'f' || data == 'c') { command = data; hexstring = ""; state = 3; } else if (data != 1) { // stay in state 2 if received 0x01. state = 1; } break; case 3: if ((data >= 'a' && data <= 'z') || (data >= '0' && data <= '9')) { hexstring = hexstring + data; if (hexstring.length() == 6) { state = 4; } } else if (data == 1) { state = 2; } else { state = 1; } break; case 4: if (data == 3) { processcommand(command, hexstring); state = 1; } else if (data == 1) { state = 2; } else { state = 1; } break; } }
edit: final code
#include <rfduinoble.h> // state properties. int state = 1; char command; string hexstring; // rgb pins. int redpin = 2; int grnpin = 3; int blupin = 4; // setup function set rgb pins output pins. void setup () { pinmode(redpin, output); pinmode(grnpin, output); pinmode(blupin, output); // data want appear in advertisement // (the devicename length plus advertisement length must <= 18 bytes. rfduinoble.devicename = "ios"; rfduinoble.advertisementinterval = milliseconds(300); rfduinoble.txpowerlevel = -20; rfduinoble.advertisementdata = "rgb"; // start ble stack. rfduinoble.begin(); } void loop () { switch (command) { case 1: // blink. break; case 2: // fade. break; } //rfduino_ulpdelay(infinite); } // converts hex string actual hex values. // needed convert ascii value hex // value of each character. byte getval (char c) { if (c >= '0' && c <= '9') return (byte)(c - '0'); else return (byte)(c - 'a' + 10); } // process each function/command. void processcommand (int command, string hex) { switch (command) { case 'b': command = 1; // set blink mode. break; case 'f': command = 2; // set fade mode. break; case 'c': // put 2 characters // done hex notation , set color. byte red = getval(hex.charat(1)) + (getval(hex.charat(0)) << 4); byte green = getval(hex.charat(3)) + (getval(hex.charat(2)) << 4); byte blue = getval(hex.charat(5)) + (getval(hex.charat(4)) << 4); // set color. setcolor (red, green, blue); break; } } // sets color of each rgb pin. void setcolor (byte red, byte green, byte blue) { analogwrite(redpin, red); analogwrite(grnpin, green); analogwrite(blupin, blue); } // function returns data radio. void rfduinoble_onreceive (char *data, int len) { (int = 0; < len; i++) { statemachine(data[i]); } } // main state machine function, processes // data depending on bytes received. void statemachine (char data) { switch (state) { case 1: if (data == 1) { state = 2; } break; case 2: if (data == 'b' || data == 'f' || data == 'c') { command = data; hexstring = ""; state = 3; } else if (data != 1) { // stay in state 2 if received 0x01. state = 1; } break; case 3: if ((data >= 'a' && data <= 'z') || (data >= '0' && data <= '9')) { hexstring = hexstring + data; if (hexstring.length() == 6) { state = 4; } } else if (data == 1) { state = 2; } else { state = 1; } break; case 4: if (data == 3) { processcommand(command, hexstring); state = 1; } else if (data == 1) { state = 2; } else { state = 1; } break; } }
there code here can use convert hex characters byte.
so, can add existing code -
byte getval(char c) { if (c >= '0' && c <= '9') return (byte)(c - '0'); else return (byte)(c-'a'+10) } void processcommand (int command, string hex) { switch (command) { case 'b': command = 1; // set blink mode break; case 'f': command=2; // set fade mode break; case 'c': byte red=getval(hex.charat(1)) + (getval(hex.charat(0)) << 4); byte green=getval(hex.charat(3)) + (getval(hex.charat(2)) << 4); byte blue=getval(hex.charat(5)) + (getval(hex.charat(4)) << 4); setcolor(red,green,blue); } } void setcolor(byte red,byte green,byte blue) { // set pwm each led. analogwrite(rgb2_pin, red); analogwrite(rgb3_pin, green); analogwrite(rgb4_pin, blue); }
on ios side can use -
-(void) sendcommand:(char)command arg1:(byte)arg1 arg2:(byte)arg2 arg3:(byte) arg3 { nsstring *commandstring=[nsstring stringwithformat:@"\001%c%02x%02x%02x\003",command,arg1,arg2,arg3]; nsdata *commanddata=[commandstring datausingencoding:nsasciistringencoding]; [rfduino send:data]; } - (ibaction)fadebuttonpressed:(id)sender { [self sendcommand:'f' arg1:0 arg2:0 arg3:0]; } - (ibaction)blinkbuttonpressed:(id)sender { [self sendcommand:'b' arg1:0 arg2:0 arg3:0]; } - (void)setcolor { nslog(@"colors: rgb %f %f %f", red, green, blue); uicolor *color = [uicolor colorwithred:red green:green blue:blue alpha:1.0]; [colorswatch sethighlighted:yes]; [colorswatch settintcolor:color]; [self sendcommand:c arg1:red*255 arg2:green*255 arg3:blue*255]; }
Comments
Post a Comment