# Control Arduino

**URL:** https://discourse.julialang.org/t/control-arduino/29982
**Category:** General Usage
**Tags:** arduino
**Created:** [October 16, 2019, 1:13pm UTC](https://discourse.julialang.org/t/control-arduino/29982 "2019-10-16T13:13:21Z")
**Posts on this page:** 14
**Page:** 2

<div class="post-metadata">

### Author: ![yakir12](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/yakir12/32/297_2.png) [@yakir12](https://discourse.julialang.org/u/yakir12)
#### Post date: [October 18, 2019, 10:54am UTC](https://discourse.julialang.org/t/control-arduino/29982/21 "2019-10-18T10:54:13Z")

</div>

OMG, solved…

I had a horrible time getting the fact the loop function loops but the state needs to be preserved between iterations. Following works:

```nohighlight
#include <Adafruit_DotStar.h>
#include <SPI.h>

#define NUMPIXELS 150

Adafruit_DotStar strip = Adafruit_DotStar(NUMPIXELS, DOTSTAR_BRG);

const byte numVar = 2;
uint8_t variables[numVar]; // an array to store the received data

static byte ndx = 0;

void setup() {
  strip.begin();
  strip.show();
  Serial.begin(115200);
}

void loop() {
  recvWithEndMarker();
  showNewData();
}

void recvWithEndMarker() {
  while (Serial.available() > 0 && ndx < numVar) {
    variables[ndx] = Serial.read();
    ndx++;
  }
}

void showNewData() {
  if (ndx == numVar) {
    strip.setPixelColor(variables[0], variables[1], 0, 0);
    strip.show();
    ndx = 0;
  }
}

```

THANKS!!!

---

<div class="post-metadata">

### Author: ![yakir12](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/yakir12/32/297_2.png) [@yakir12](https://discourse.julialang.org/u/yakir12)
#### Post date: [October 18, 2019, 2:12pm UTC](https://discourse.julialang.org/t/control-arduino/29982/22 "2019-10-18T14:12:00Z")

</div>

OK! I thought it would be good to post my complete solution, in case anyone finds it useful.

The following allows a user to control a DotStar 5 m LED strip with 30 LEDs per meter. The user can control the location, intensity, and size of the source of light from 3 Makie.sliders. The whole thing is pretty snappy!

For the Arduino:

```nohighlight
#include <Adafruit_DotStar.h>
#include <SPI.h>

#define NUMPIXELS 150

Adafruit_DotStar strip = Adafruit_DotStar(NUMPIXELS, DOTSTAR_BRG);

const byte numVar = 3;
uint8_t variables[numVar];
uint8_t oldp = 0;
uint8_t oldl = 1;
const uint32_t off = strip.Color(0, 0, 0);

static byte ndx = 0;

void setup() {
  strip.begin();
  strip.show();
  Serial.begin(115200);
}

void loop() {
  recInstructions();
  updateStrip();
}

void recInstructions() {
  while (Serial.available() > 0 && ndx < numVar) {
    variables[ndx] = Serial.read();
    ndx++;
  }
}

void updateStrip() {
  if (ndx == numVar) {
    strip.fill(off, oldp, oldl);
    uint32_t color = strip.Color(variables[1], 0, 0);
    strip.fill(color, variables[0], variables[2]);
    strip.show();
    ndx = 0;
    oldp = variables[0];
    oldl = variables[2];
  }
}

```

From Julia:

```julia
using LibSerialPort, Makie

n = 150

s = open("/dev/ttyACM0", 115200)
psl, pol = textslider(1:n, "Position", start = 1);
ssl, sol = textslider(1:2:21, "Size", start = 1);
isl, iol = textslider(0:255, "Intensity", start = 0);
sc = hbox(psl, ssl, isl)
msg = lift(pol, iol, sol) do p, i, s
    p = p - (s - 1)/2 - 1
    if p < 0
        s += p
        p = 0.0
    end
    pend = p + s
    if pend > n - 1
        s = n - 1
    end
    [UInt8(p), UInt8(i), UInt8(s)]
end
on(msg) do m
    write(s, m)
end

```

---

<div class="post-metadata">

### Author: ![ssfrr](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/ssfrr/32/3736_2.png) [@ssfrr](https://discourse.julialang.org/u/ssfrr)
#### Post date: [October 18, 2019, 2:44pm UTC](https://discourse.julialang.org/t/control-arduino/29982/23 "2019-10-18T14:44:58Z")

</div>

Nice! It’d be great to see a video of it in action.

One potential issue is that if your serial stream ever gets desynchronized there’s no way to recover - i.e. if the Arduino drops a byte or something then everything will be shifted over by a byte. One solution is to reserve a value (like 0xFF) that is never allowed to be part of your data and using that as a frame separator.

Might not be a problem in practice, but the strip ever starts acting wonky that might be what’s going on.

---

<div class="post-metadata">

### Author: ![yakir12](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/yakir12/32/297_2.png) [@yakir12](https://discourse.julialang.org/u/yakir12)
#### Post date: [October 18, 2019, 7:09pm UTC](https://discourse.julialang.org/t/control-arduino/29982/24 "2019-10-18T19:09:36Z")

</div>

I’m trying to think if I should:

1. read “infinitely” until I get the frame separator byte.
2. read the `n` bytes I know are in one frame, and test if the last byte is indeed my separator byte. If it is not, then and only then keep reading bytes (and tossing them) until I get to the next separator byte.

Methods #1 is simple, but then I’m testing for the separator every loop. In method #2 I’m checking for the separator byte only once a frame. On the other hand I think I miss one extra frame, which is fine.

I suspect I’m fretting over virtually nothing…

@ssfrr, one more question: I need to operate 4 strips. Each has 150 LEDs. I’m considering connecting the 4 strips serially, to the one Arduino. I’ll then need to have a `location` of more than 255 (==256).  
I’m trying to figure out how to do that on the Julia and the Adruino sides…  
In Julia, something like this:

```julia
n = rand(0:600)
b1 = UInt8(n ÷ 255)
b2 = UInt8(mod(n, 255))
@assert 255b1 + b2 == n

```

and in the Arduino, like that?

```nohighlight
position = 255*Serial.read() + Serial.read() 

```

---

<div class="post-metadata">

### Author: ![yakir12](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/yakir12/32/297_2.png) [@yakir12](https://discourse.julialang.org/u/yakir12)
#### Post date: [October 18, 2019, 7:10pm UTC](https://discourse.julialang.org/t/control-arduino/29982/25 "2019-10-18T19:10:03Z")

</div>

> [@ssfrr](#):
>
> Nice! It’d be great to see a video of it in action.

Thanks! I’ll be sure to upload a video of it tomorrow!

---

<div class="post-metadata">

### Author: ![Daniel\_Berge](https://avatars.discourse-cdn.com/v4/letter/d/eb9ed0/32.png) [@Daniel\_Berge](https://discourse.julialang.org/u/Daniel_Berge)
#### Post date: [October 18, 2019, 7:16pm UTC](https://discourse.julialang.org/t/control-arduino/29982/26 "2019-10-18T19:16:40Z")

</div>

It’s more involved, but you find something similar in other UART protocols. This example is from the u-blox GPS chipset. A message header, register, length, payload, and finally a checksum. It’s a bit more work to read, as you have to validate parts of the message as it comes in, and have a timeout to make sure it doesn’t get stuck at a partial frame.

 ![image](https://global.discourse-cdn.com/julialang/original/3X/2/7/27c6fcaf0119d5421b7756cb0e89c04cb2ad7714.jpeg)

---

<div class="post-metadata">

### Author: ![KajWiik](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/kajwiik/32/199_2.png) [@KajWiik](https://discourse.julialang.org/u/KajWiik)
#### Post date: [October 18, 2019, 7:27pm UTC](https://discourse.julialang.org/t/control-arduino/29982/27 "2019-10-18T19:27:35Z")

</div>

COBS is my favorite to solve the framing problem:

> **[Consistent Overhead Byte Stuffing](https://en.wikipedia.org/wiki/Consistent_Overhead_Byte_Stuffing)**
>
> Consistent Overhead Byte Stuffing (COBS) is an algorithm for encoding data bytes that results in efficient, reliable, unambiguous packet framing regardless of packet content, thus making it easy for receiving applications to recover from malformed packets. It employs a particular byte value, typically zero, to serve as a packet delimiter (a special value that indicates the boundary between packets). When zero is used as a delimiter, the algorithm replaces each zero data byte with a non-zero value...

In Arduino, e.g.:

> **[GitHub - bakercp/PacketSerial: An Arduino Library that facilitates...](https://github.com/bakercp/PacketSerial)**
>
> An Arduino Library that facilitates packet-based serial communication using COBS or SLIP encoding. - GitHub - bakercp/PacketSerial: An Arduino Library that facilitates packet-based serial communica...

---

<div class="post-metadata">

### Author: ![yakir12](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/yakir12/32/297_2.png) [@yakir12](https://discourse.julialang.org/u/yakir12)
#### Post date: [October 18, 2019, 8:23pm UTC](https://discourse.julialang.org/t/control-arduino/29982/28 "2019-10-18T20:23:41Z")

</div>

Wow, COBS looks really cool. How would I encode my payload COBS-like? Also, wow, didn’t know there were libraries for stuff like this. I feel I should explore some more, maybe I’ll find other useful libraries for the Arduino…

---

<div class="post-metadata">

### Author: ![yakir12](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/yakir12/32/297_2.png) [@yakir12](https://discourse.julialang.org/u/yakir12)
#### Post date: [October 19, 2019, 1:40pm UTC](https://discourse.julialang.org/t/control-arduino/29982/29 "2019-10-19T13:40:42Z")

</div>

> [@yakir12](#):
>
> I need to operate 4 strips. Each has 150 LEDs. I’m considering connecting the 4 strips serially, to the one Arduino. I’ll then need to have a `location` of more than 255 (==256).  
> I’m trying to figure out how to do that on the Julia and the Adruino sides…

Just to answer my own question:  
In Julia, where `p2` is a `UInt16`:

```julia
low = UInt8(p2 & 0xFF)
high = UInt8((p2 >> 8) & 0xFF)

```

and then in the Arduino, where `frame` contains the payload with the two bytes:

```C++
uint16_t p = frame[1] | (frame[0] << 8);

```

---

<div class="post-metadata">

### Author: ![yakir12](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/yakir12/32/297_2.png) [@yakir12](https://discourse.julialang.org/u/yakir12)
#### Post date: [October 20, 2019, 2:06pm UTC](https://discourse.julialang.org/t/control-arduino/29982/30 "2019-10-20T14:06:50Z")

</div>

> [@ssfrr](#):
>
> Nice! It’d be great to see a video of it in action.

Sorry for the poopy quality, holding phone at the same time…

> **[New video by Yakir Gagnon](https://photos.app.goo.gl/qaGCAUTSXauyiUT3A)**

---

<div class="post-metadata">

### Author: ![ssfrr](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/ssfrr/32/3736_2.png) [@ssfrr](https://discourse.julialang.org/u/ssfrr)
#### Post date: [October 21, 2019, 12:11pm UTC](https://discourse.julialang.org/t/control-arduino/29982/31 "2019-10-21T12:11:23Z")

</div>

That’s awesome! Looks like you got it to be quite snappy.

---

<div class="post-metadata">

### Author: ![oschulz](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/oschulz/32/2998_2.png) [@oschulz](https://discourse.julialang.org/u/oschulz)
#### Post date: [October 21, 2019, 12:23pm UTC](https://discourse.julialang.org/t/control-arduino/29982/32 "2019-10-21T12:23:05Z")

</div>

> [@yakir12](#):
>
> how and what do I send to a serial port in Julia?

On Linux, I’ve been using Julia code like this, to access serial ports:

```julia
serial_dev_name = "/dev/serial/by-id/usb-[...]"
run(`stty -F $serial_dev_name speed 115200`)
serial_io = open(serial_dev_name, read = true, write = true)

```

---

<div class="post-metadata">

### Author: ![yakir12](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/yakir12/32/297_2.png) [@yakir12](https://discourse.julialang.org/u/yakir12)
#### Post date: [October 21, 2019, 12:23pm UTC](https://discourse.julialang.org/t/control-arduino/29982/33 "2019-10-21T12:23:59Z")

</div>

I’ve settled on `LibSerialPort.jl`, works great for me.

---

<div class="post-metadata">

### Author: ![GregMcC](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/gregmcc/32/14827_2.png) [@GregMcC](https://discourse.julialang.org/u/GregMcC)
#### Post date: [July 15, 2020, 9:12am UTC](https://discourse.julialang.org/t/control-arduino/29982/34 "2020-07-15T09:12:43Z")

</div>

I suggest you use the millis() function which keeps a track of the number of milliseconds since the last restart of the board.  
now = millis() - where now is an unsigned long integer ( you also need to assign ‘prev’ ( previous )

if (( now - prev ) \> 200 )  
{  
…  
prev = now ; }

This is a way of doing something every 200mS but not holding up the processing of other routines.

[Previous page](https://discourse.julialang.org/t/control-arduino/29982.md?page=1)
