Flash to Arduino using SerProxy - errors!

Hello,

I have 4 LEDs connected to PWM outputs on the Arduino and simply want a sine function running in Flash to drive the analogWrite in Arduino to fade the LEDs. It was working fine if I was pumping a number between 0-255 from flash using:

private function enterframer(e:Event):void {
  counter += 0.1;
  var res:Number = int((Math.sin( counter ) + 1) * 128);
  
  arduinoSocket.writeByte(res);
  arduinoSocket.flush();
}

…but I actually want to be able to control each LED individually. So I assumed I could get that by adding a signature byte before my sine value which I can use on the Arduino side to filter. Here’s the updated Flash (as3) code in the enterframe loop:

private var aLedIdentifiers:Array = new Array(144, 208, 192, 224); // just some unique numbers
private function enterframer(e:Event):void {

  counter += 0.1;
  var res:Number = int((Math.sin( counter ) + 1) * 128);

  var i:int;
  var len:int = 4;
  for (i = 0; i < len; i++) {
    arduinoSocket.writeByte(aLedIdentifiers[i]);
    arduinoSocket.writeByte(res);
    arduinoSocket.flush();
  }
}

and here’s the Arduino code:

const int LED_ONE = 11;        // Digital port 11
const int LED_TWO = 10;        // Digital port 10
const int LED_THREE = 9;       // Digital port 9
const int LED_FOUR = 6;        // Digital port 6

int leds[4];

void setup() 
{ 
  Serial.begin(9600);

  leds[0] = LED_ONE;
  leds[1] = LED_TWO;
  leds[2] = LED_THREE;
  leds[3] = LED_FOUR;

} 

void loop() 
{
  if (Serial.available() > 0)
  {
    while (Serial.available())
    {
      int command = Serial.read();
      int val = Serial.read();
      int i;
      for(i = 0; i < 4; i++)
      {
        analogWrite(leds[i], 0);      
      }
      switch (command)
      {
        case 144:
          analogWrite(leds[0], val); 
          break;
        case 208:
          analogWrite(leds[1], val); 
          break;
        case 192:
          analogWrite(leds[2], val); 
          break;
        case 224:
          analogWrite(leds[3], val); 
          break;
      }  
    }
    Serial.flush(); // superfluous, I guess.
  }
}

This would still have all 4 LEDs fading at the same speed and intensity, that’s allright for now.
The int ‘command’ is being filled with the correct value, I tested that by serial-printing it back to Flash and reading the value there. The problem I’m having is with the int ‘val’. The LEDs on the Arduino side are NOT being set to the correct sine value. So, I thought, that value must not be being received correctly… let’s pass that one on to Flash through serial.print too, see what it is.

Let’s look at this piece of Flash code which is on the receiving end of the Serial connection between Arduino and Flash:

var LedNumber:uint = arduinoSocket.readUnsignedByte();
var LedValue:uint = arduinoSocket.readUnsignedShort() & 0xFF;

After much fidgeting, I finally got the value of a LED back correctly. LedNumber was spitting out one of the above mentioned unique identifiers, but I couldn’t get a hold of LedValue correctly, at least not when I was reading it as an unsigned byte, which it should - in my opinion - be being sent as from Arduino… right?? Turns out I can get the value of the sine function back correctly if I read an unsigned short (16-bit value) from the serial stream. A sine value of 120 would then be 65120, value 240 would be 65240, 16 would be 65016 etc etc. So I chop off the two left-most characters and that leaves me with the desired sine value.
Still I don’t get it though… why is this happening? And how can I get the value of the sine function correctly in Arduino?

Sorry for the lengthy post, especially since I’m quite aware that it’s not rocket science what I’m attempting here :frowning: Any ideas/insights would be very welcome. Thanks in advance, I just don’t see what could be wrong anymore.

cheers,
Adriaan

ps → using WinXP SP3, SerProxy, Arduino0015

Does removing the calls to flush have any effect?

  • Brian

Thanks for the reply Brian.

Tried removing the flush command but that didn't change much. However, I've got it working today.

What I think the problem was was that I was sending data too often. What I'm doing now is dumping the identifier and according data of each LED after each other - so with my 4 LEDs that's 8 writeBytes in Flash - before doing the flush() command. Somehow that seemed to do the trick. Also, I added an additional if-statement to the Arduino code, within the loop in which I iterate over Serial.available():

if (Serial.available() % 2) {
  // code for driving the LEDs here
}

This just to filter out cases where there isn't a clean identifier&value pair available.

I added 2 LEDs to the Arduino - now using all the 6 PWM ports - changed the code to support that and presto, that also works!

I was curious what role the baudrate of the connection plays and I was surprised to learn that only 115200 gives me the results I want. 96000 results in crappy random blinking of the LEDs and anything below that, all the LEDs are on constantly. How is this? What does it mean to use a lower baudrate? Less data capacity per send command?

How is this?

I suspect there’s a bug in your code. The “if”…

if (Serial.available() > 0)

…is true when there is one or more bytes waiting. You then try to read two bytes…

int command = Serial.read();
int val = Serial.read();

If there is only one byte waiting, the second Serial.read returns -1. This might cause all the LEDs to be on constantly. I suspect the second byte arrives in time when you use the higher baud rate.

What does it mean to use a lower baudrate?

For serial ports, “baud rate” is the raw bits per second. Each byte consists of 1 start bit, 8 data bits, and 1 stop bit. I believe there also has to be a “pad” between bytes (one more bit). The bytes per second is baud rate / 11.

Less data capacity per send command?

Exactly.

  • Brian