title: MH-Z19 with Arduino null output

text:
# Question
Title: MH-Z19 with Arduino null output
I want to get CO2 value by using MH-Z19. I tried this code with Arduino uno R3 but I always get this result (CRC 0/0). I didn't understand where is the problem. I linked A0 with TX of sensor and A1 with RX, I powered the card with 3.3V/Vin to visualize the result on PC via USB port.

```
 #include <SoftwareSerial.h>;

 SoftwareSerial mySerial(A0, A1); // A0 - к TX сенсора, A1 - к RX

 byte cmd[9] = {0xFF,0x01,0x86,0x00,0x00,0x00,0x00,0x00,0x79};
  unsigned char response[9];

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

 void loop()
{
mySerial.write(cmd, 9);
 memset(response, 0, 9);
 mySerial.readBytes(response, 9);

  int i;
byte crc = 0;
 for (i = 1; i < 8; i++) crc+=response[i];
 crc = 255 - crc;
 crc++;

  if ( !(response[0] == 0xFF && response[1] == 0x86 && response[8] == crc) )
 {
Serial.println("CRC error: " + String(crc) + " / "+ String(response[8]));
  } else {
unsigned int responseHigh = (unsigned int) response[2];
unsigned int responseLow = (unsigned int) response[3];
unsigned int ppm = (256*responseHigh) + responseLow;
Serial.println(ppm);
}

```

# Answer
> 1 votes
From the datasheet, working voltage for MH-Z19 is 3.6V to 5.5V, so 3.3V is not enough. (Although the interface runs at 3.3V).

Also, the Uno might not run reliably at 16MHz and 3.3V.

Edited image from datasheet page 303.

---
Tags: sensors
---


title: About multiple void loops and functions

text:
# Question
Title: About multiple void loops and functions
I'm still a beginner at Arduino coding -- I've been researching on how to make functions using void instead of doing goto because reasons...

one thing I've noticed about void is that it has this `void loop() {...}` parenthesis, **what is it for?** (and can you provide an example of using it?)

say I make a void function `void function1()` to call the function I have to use `function1();` **can I make a function that loops?** like the ol' `void loop() {...}` command we all know and love or **do all void functions loop?** if not then what happens to a void function after it reaches the end of its function?

# Answer
The void in front of the function definition just tells what type the function returns. In the case of void it means the function returns nothing. If the function returned an int then it would be defined with int instead of void.

eg:

```
int addNumbers(int num1, int num2){
    int retval = num1 + num2;
    return retval;
}

int sum = addNumbers(3, 4);
Serial.print(sum);  // prints 7

```

No, the loop only loops because main (see main.cpp in the core) is the "real" program that is running on your micro and it calls loop over and over. It's not that the loop function on it's own repeats. It is literally being called repeatedly by the main function.

That example also gets to what the parenthesis are for. That's where the arguments that the function takes go. In the function definition you tell it what types they'll be and give them names. In the function call you put in whatever values you want to function to use. In the case of void loop(), it takes no arguments so the parenthesis are empty.

I would suggest you look at a basic tutorial on C++. There are many good ones on the web. The concept of functions isn't something that you can reason your way through by doing. Go read a little and you'll get it pretty quick.
> 2 votes

---
Tags: arduino-uno
---


# Question
Title: Arduino Mega - Multithreaded (run two loops simultaneously)
I am new to Arduino and I am not sure about how to get two loops run parallel to each other. I have tested the individual loops and both of them work perfectly before I combined them together.

One loop will take input from the LCD touchscreen. One loop will take input from vibration sensor which will determine the state (on/off) of LED. Once the LED is turned on, it has to stay at the ON state for 3 seconds before switching to OFF state.

The problem I am facing is that when the LED is triggered to ON state by vibration sensor, I have to wait 3 seconds for the input from LCD to get processed. Is there any way I can combine these two loops in such a fashion that I run them simultaneously, i.e. run two inputs together?

# Answer
You can combine the 2 programs into 1 program. But when you start wanting to do multiple things at once then you can't have any code that "blocks" and waits to finish before letting the next thing happen. The Arduino has a single core, it can't do multithreading. But if you write non-blocking code you can make things appear to happen at the same time. I imagine the problem with your code now is that you have probably used the delay function. That function blocks, so nothing else can happen while the delay is running. Instead you have to use millis to record the time and periodically check against that time to see if it is time to take the next step instead of calling a delay to wait for the next step. See the "Blink Without Delay" example that comes with the IDE and any of the multitude of tutorials about it on the web to see how it works.
> 3 votes

# Answer
I totally second Delta's answer. Make the two loops "non blocking", then run them one after the other.

Just wanted to add another solution, to be applied only when strictly needed. And only if the program really needs it. And only if other solutions are not enough. And... Well, you understood.

You can use FreeRTOS to have a sort of "multi-threading" environment. You have, IIRC, four "threads" which can jump from one loop to the other. You will have to carefully design it (particularly the shared memory) but in the end you will have even blocking "threads" running in parallel. Here are some more infos.
> 1 votes

---
Tags: arduino-mega
---


# Question
Title: In the AnalogRead example, would the thing work if I remove or short the A0 and the ground pin?
What I want to know is that how exactly does analogRead work because I have want to use it with a flex sensor and it has only two pins.I tried to find other examples on the internet, but this is the only example I find.If the middle pin of the 10k potentiometer and a0 pin are shorted or the gnd pin is removed altogether,then would this thing work?

# Answer
> 3 votes
I think you are confused because the ADC input measures voltage, not resistance.

To convert from resistance to voltage you need to pull in the opposite direction on the variable resistance with a fixed resistor. As in the following image from this tutorial.

---
Tags: arduino-uno, analogread, electronics
---


# Question
Title: Loop code without manually pressing the button
In a piece off code I am modifying I have a button connected to start the code and then it resets its self afterwards. Is they a way to make the arduino loop that code without manually pressing the button again?

This is a section off the code:

```
#include <Adafruit_NeoPixel.h>
#ifdef __AVR__
  #include <avr/power.h>
#endif
#define PIN 6
#define BUTTON_PIN 9

Adafruit_NeoPixel strip = Adafruit_NeoPixel(120, PIN, NEO_GRB + NEO_KHZ800);

bool oldState = HIGH;
int showType = 0;

void(* resetFunc) (void) = 0; //declare reset function @ address 0

void setup() {
  pinMode(BUTTON_PIN, INPUT_PULLUP);
  strip.begin();
  strip.show(); // Initialize all pixels to 'off'
}

void loop() {
  // Get current button state.
  bool newState = digitalRead(BUTTON_PIN);

  // Check if state changed from high to low (button press).
  if (newState == LOW && oldState == HIGH) {
    // Short delay to debounce button.
    delay(20);
    // Check if button is still low after debounce.
    newState = digitalRead(BUTTON_PIN);
    if (newState == LOW) {
      showType++;
      if (showType > 9)
        showType=0;
      startShow(showType);
    }
  }

  // Set the last button state to the old state.
  oldState = newState;
}

void startShow(int i) {
  colorWipe(strip.Color(75, 0, 0), 50); // Red
  colorWipe(strip.Color(0, 75, 0), 50); // Green
  colorWipe(strip.Color(0, 0, 75), 50); // Blue
  theaterChase(strip.Color(75, 75, 75), 50); // White
  theaterChase(strip.Color(75, 0, 0), 50); // Red
  theaterChase(strip.Color(0, 0, 75), 50); // Blue
  rainbow(20);
  rainbowCycle(20);
  theaterChaseRainbow(50);
  resetFunc();  //call reset
}

```

Thanks Reece

# Answer
As pointed out by Delta\_G, there is no point in resetting your program. What you should do is think your program in terms of the Arduino logic:

1. You put in `setup()` the code you want to run when your program starts.
2. You put in `loop()` the code you want to run over and over again.

In this case `loop()` is fairly simple, as the stuff you want to run over and over again is the animation, thus:

```
void loop() {
  colorWipe(strip.Color(75, 0, 0), 50); // Red
  colorWipe(strip.Color(0, 75, 0), 50); // Green
  colorWipe(strip.Color(0, 0, 75), 50); // Blue
  theaterChase(strip.Color(75, 75, 75), 50); // White
  theaterChase(strip.Color(75, 0, 0), 50); // Red
  theaterChase(strip.Color(0, 0, 75), 50); // Blue
  rainbow(20);
  rainbowCycle(20);
  theaterChaseRainbow(50);
}

```

Note that I removed the call to `resetFunc()`.

The stuff you want to do at startup is the initialization. Oh, wait. In a comment you wrote “I want to wait for the button press”. So this also has to be done before the program starts looping. Hence your `setup()` should initialize stuff, *then* wait for the button press:

```
void setup() {
  // Initialize the strip to all piwels off.
  strip.begin();
  strip.show();

  // Wait until the button is pressed.
  pinMode(BUTTON_PIN, INPUT_PULLUP);
  while (digitalRead(BUTTON_PIN) == HIGH)
      ; // do nothing
}

```
> 1 votes

---
Tags: button, neopixel
---


title: ESP8266 Library Method List

text:
# Question
Title: ESP8266 Library Method List
Is there a place that lists all the common methods used with the standard ESP8266 libraries in Arduino?

# Answer
Looking at the GitHub page, there is a document explaining how everything works, https://arduino-esp8266.readthedocs.io/en/latest/
> 2 votes

---
Tags: esp8266
---


title: LED fading effect using a push button

text:
# Question
Title: LED fading effect using a push button
Guys please help me out in verifying my program for my project -- led fading effect using a push button.

My project is simple, I want to start the LED fading effect (i.e., glowing and dimming one after another) at one click on the push button that is pushing and then leaving the push button and on my another click I want the effect to get off.

The main problem is coming in the programming part and rest all the circuit and components are fine.

THIS IS MY SKETCH :-

```
int ledpin = 9;
int buttonpin = 8;
boolean buttonpressed = false;   // to check whether the button was pressed //
int brightness = 0;
int fadeamount = 5;

void setup ()
{
pinMode (ledpin, OUTPUT);
pinMode (buttonpin,INPUT);
digitalWrite (ledpin,LOW);
}

void loop ()
{
if ( digitalRead (buttonpin) == HIGH)
 {
  buttonpressed = true;
 }

 else {
     if ( buttonpressed = true && digitalRead(ledpin) == LOW)
       {
           brightness = brightness + fadeamount;
           if ( brightness == 0 || brightness == 255)
            {
             fadeamount = -fadeamount;}
             analogWrite(ledpin, brightness);
             delay (30);
             buttonpressed = false;
        }
      if (buttonpressed == true && analogRead(ledpin) == brightness)
        {
          digitalWrite(ledpin,LOW);
          buttonpressed = false;
        }
   }
 }

```

**THIS IS THE CIRCUIT DIAGRAM**

# Answer
> 2 votes
I changed things a bit and got a solution

```
int led = 3;
int buttonpin = 8;
boolean waspressed = false;

int inertia = 10;

void setup (){
  pinMode(buttonpin,INPUT);
  pinMode(led,OUTPUT);
  analogWrite(led,0);
}

void loop(){
  if(digitalRead(buttonpin) == HIGH){
    waspressed = true;
  }else{
     if (waspressed == true){
       fadeLed(digitalRead(led), inertia);
       waspressed = false;
     }
  }
}

void fadeLed(boolean input, int inertia){
  for(int state=0;state<256;state++){
    if (input==LOW){
      analogWrite(led, state);
    }else{
      analogWrite(led, 255-state);
    }
    delay(inertia);
  }
}

```

I created a function called `fadeLed` that receives two arguments: The actual state of the led and the delay - in miliseconds - that is going to determine how long the fading is going to last.

You can see that the rest of the code is pretty much the one you got in the other question you asked. This is because we already got a good code to control the behavior of the button, so its a good practice to keep it and just change what you want to be changed: to fade instead of blink. So we just change a single line and create a function to be called by that line. Functions are a good way to keep a clean code and are a good programming practice. They make the code easy to read and maintain.

The function `fadeLed()` uses PWM to fade the led. In Arduino Uno, PWM is available in digital pins 3, 5, 6, 9, 10, and 11. This may change according to the model you are using. It's very important to understand PWM so you can know why `analogWrite()` is used in a digital pin.

If you check the documentation of analogWrite(), you are going to see that for most of the Arduino boards the default resolution is 8 bits, i.e, 0 to 255. To use all this 256 values to fade the led, a `for` loop is used. If you are not used to for loops, I strongly recommend you to read the documentation.

The for loop is programed to go through 256 iterations - the variable `state` going from 0 to 255. At each iteration, the value of `state` is incremented by 1. When `state` gets to be equal to 256, the loop ends itself. Every iteration verifies the value of `input`, which is just the state of the led when the button was released. **This value is passed to the function only when the button is released, but the function uses it internally at every iteration**. If `input` is `LOW`, it means that the led was off, so `analogWrite(led, state);` uses the value of `state` \- increasing at every iteration - to fade the led, turning it on. If `input` is `HIGH`, it means that the led was on, so `analogWrite(led, 255-state);` will fade the led turning it off. In this case, **`255-state` is just a way to set a range starting at 255 and ending at 0 while using a range that we already have - `state` \- that starts at 0 and ends at 255.**

The last line is just to set how long the fade action is going to last. To be more specific, `delay(inertia)` determine how long **each iteration** is going to last. So, when you set inertia to 10, will you see that fading will take 10(miliseconds)\*255(iterations) + execution times =~ 2,6 seconds. I chose this name when I was coding and I'm not sure now if it was the better one. Maybe something like duration will have a more clear meaning. If you want to set the duration of the fade on your code - instead of the duration of each iteration - you can to something like

```
int fadeDuration = 3000; //duration of fade in ms

...

void fadeLed(boolean input, int inertia){
  for(int state=0;state<256;state++){
    if (input==LOW){
      analogWrite(led, state);
    }else{
      analogWrite(led, 255-state);
    }
    // delay in every iteration to achieve 3 seconds in total.
    delay(fadeDuration/256); //=(total fading duration)/(number of iterations)
  }
}

```

Hope this is clear. Don't forget to check the links I placed, they are *all* VERY important.

# Answer
> 3 votes
The 1k (pulldown-)resistor must be placed at the other side of the button (the pin8 side, not the 5v side).

The led needs a resistor, to limit the current.

There is no need for the `buttonstate` variable, as you can just check the brightness to see if the PWM value must be changed.

```
int ledpin = 9;
int pushbutton = 8;

int brightness = 0;
int fadeamount = 1;

void setup ()
{
  pinMode (ledpin,OUTPUT);
  pinMode (pushbutton,INPUT);
}

void loop ()
{
  if( digitalRead(pushbutton)==HIGH && brightness<255 )
  {
    // fade in led
    brightness = brightness + fadeamount;// increase brightness
    if( brightness>255 ) // check that brightness doesn't exceed 255
      brightness = 255;
    analogWrite(ledpin,brightness);
    delay (1);
  }
  else if( digitalRead(pushbutton)==LOW && brightness>0 )
  {
    // fade out led
    brightness = brightness - fadeamount;// decrease brightness
    if( brightness<0 ) // check that brightness doesn't go below 0
      brightness = 0;
    analogWrite(ledpin,brightness);
    delay (1);
  }

}

```

# Answer
> 2 votes
try this, its simple and easy to understand,

```
int ledPin = 9;
int btnPin = 8;
int brightness = 0;
int btnState = LOW;
bool trigger = LOW;
void setup ()
{
  pinMode (ledPin, OUTPUT);
  pinMode (btnPin, INPUT);
}

void loop ()
{
  if ( digitalRead(btnState) && !btnState)
  {
    if (trigger)
    {
      for (int i = 0; i < 256; i++)
      {
        analogWrite(ledPin, i);
        // wait for 30 milliseconds to see the dimming effect
        delay(30);
      }
    }
    else
    {
      for (int i = 255; i >= 0; i--)
      {
        analogWrite(ledPin, i);
        // wait for 30 milliseconds to see the dimming effect
        delay(30);
      }
    }
    trigger = !trigger;
  }
  btnState = digitalRead(btnState);
}

```

# Answer
> 0 votes
There are basically two parts to your program and it's best if you deal with them completely separately:

1. Reading a push button to turn fading on or off
2. Fading if fading is turned on

Start by making an LED fade all the time. The Fade example can help you with that.

Then as a separate sketch program the button to turn an LED on or off each time you press it.

Once you have those working change the LED in the second sketch to setting a flag, and make the code from the first sketch look at that flag.

# Answer
> 0 votes
you should break down the code into two pieces, one to read the button and another to fade the led.

to fade an led, you just need to change its brightness and hold at that brightness for a short period of time. to drive the led at its brightness, use pwm.

that's all there is.

fancier ones will try to do a gamma correction but to just get started, the above is sufficient enough.

---
Tags: arduino-uno, electricity
---


# Question
Title: If else statement not mutually exclusive?
When I'm running some test on my encoder motors using the following provided code by Makeblock, it appears that the `if..else..` statement is not mutually exclusive ie. I can control Encoder\_1 and Encoder\_2 at the same time. How come?

```
case ENCODER_BOARD:
      if(port == 0)
      {
        uint8_t slot = readBuffer(7);
        int16_t speed_value = readShort(8);
        speed_value = -speed_value;`

        if(slot == SLOT_1)
        {
          Encoder_1.setTarPWM(speed_value);
        }
        else if(slot == SLOT_2)
        {
          Encoder_2.setTarPWM(speed_value);
        }
        else if(slot == SLOT_3)
        {
          Encoder_3.setTarPWM(speed_value);
        }
        else if(slot == SLOT_4)
        {
          Encoder_4.setTarPWM(speed_value);
        }
      }

int16_t readShort(int16_t idx)
{
  valShort.byteVal[0] = readBuffer(idx);
  valShort.byteVal[1] = readBuffer(idx+1);
  return valShort.shortVal;
}

uint8_t readBuffer(int16_t index)
{
  if(BluetoothSource == DATA_SERIAL)
  {
    return buffer[index];
  }
  else if(BluetoothSource == DATA_SERIAL2)
  {
    return bufferBt1[index];
  }
  else if(BluetoothSource == DATA_SERIAL3)
  {
    return bufferBt2[index];
  }
}

```

All the code are taken from here and I am not the owner. I myself still studying how these whole code works. I am hoping someone out there who have experience with these kind of implementations be able to help me out.

# Answer
> 7 votes
`if` and `else if` clauses are mutually exclusive. If the `if` is true then the `else if` *cannot* run.

Therefore it must be the case that the code you posted is being executed twice (at least) - once for SLOT\_1 and once for SLOT\_2. Just so fast that you *think* it's happening at the same time.

# Answer
> 2 votes
Exactly one of the blocks in `if{..} else {...}` will be executed. Your misunderstanding is elsewhere.

# Answer
> 1 votes
Yes they are mutually exclusive.

Note that the following construct is more appropriate:

```
switch (slot)
{
case SLOT_1:
     Encoder_1.setTarPWM(speed_value);
     break;

case SLOT_2:
     Encoder_2.setTarPWM(speed_value);
     break;

case SLOT_3:
     Encoder_3.setTarPWM(speed_value);
     break;

case SLOT_4:
     Encoder_4.setTarPWM(speed_value);
     break;

default: // other cases/error
     // Handle error situation
     break;
}

```

You can do the same with BluetoothSource.

Also you can do multiple commands within one case statement, like:

```
case SLOT_4:
     Encoder_4.setTarPWM(speed_value);
     Encoder_Extra.setTarPWM(speed_value);
     break;

```

Note that the switch/case only works where you compare one variable/expression.

# Answer
> 0 votes
> am hoping someone out there who have experience with these kind of implementations be able to help me out.

Match out the brackets (to your logic) and the issue will be clear.

Your inadvertently created a duffs machine

---
Tags: atmega2560
---


# Question
Title: Problem with measuring vibrations (Arduino UNO + step motor + accelerometer)
I'm trying to measure vibrations of the motor's shaft that is oscillating due to an eccentric load. For that, I am using the MPU 6050 6 axis accelerometer. The motor is a NEMA 17 stepper, connected to Arduino UNO via EasyDriver v4.4. I first uploaded my code for the stepper, where I have 2 buttons to control the rotation direction (if you press the left, it goes clockwise and if you press the right button it goes counter clockwise). This code works fine. Later I uploaded the code only for the accelerometer and it worked fine, however when I'm trying to combine both so that the vibrations could be measured while the motor is running, apparently, I'm losing steps of the motor. Here is the code:

```
#include<Wire.h>
const int MPU_addr = 0x68; // I2C address of the MPU-6050
int16_t AcX, AcY, AcZ, Tmp, GyX, GyY, GyZ;

#define RPMS                300.0
#define STEP_PIN                9
#define DIRECTION_PIN           8
#define GO_PIN_L                3
#define GO_PIN_R                4

#define STEPS_PER_REV         200
#define MICROSTEPS_PER_STEP     8
#define MICROSECONDS_PER_MICROSTEP   (1000000/(STEPS_PER_REV *
MICROSTEPS_PER_STEP)/(RPMS / 60))

uint32_t LastStepTime = 0;
uint32_t CurrentTime = 0;

int Distance = 0;

void setup() {
  Wire.begin();
  Wire.beginTransmission(MPU_addr);
  Wire.write(0x6B);  // PWR_MGMT_1 register
  Wire.write(0);     // set to zero (wakes up the MPU-6050)
  Wire.endTransmission(true);
  Serial.begin(9600);

  pinMode(STEP_PIN, OUTPUT);
  pinMode(DIRECTION_PIN, OUTPUT);
  digitalWrite(STEP_PIN, LOW);
  digitalWrite(DIRECTION_PIN, LOW);
  pinMode(GO_PIN_L, INPUT);
  pinMode(GO_PIN_R, INPUT);
}

void loop() {
  Distance = Distance + 1;   // record this step
  if (digitalRead(GO_PIN_L) == LOW)
  {
    CurrentTime = micros();
    digitalWrite(8, LOW);
    if ((CurrentTime - LastStepTime) > MICROSECONDS_PER_MICROSTEP)
    {
      LastStepTime = CurrentTime;
      digitalWrite(STEP_PIN, HIGH);
      delayMicroseconds((MICROSECONDS_PER_MICROSTEP * 0.9) / 2);
      digitalWrite(STEP_PIN, LOW);
      delayMicroseconds((MICROSECONDS_PER_MICROSTEP * 0.9) / 2);
    }
  }
  if (digitalRead(GO_PIN_R) == LOW)
  {
    CurrentTime = micros();
    digitalWrite(8, HIGH);
    if ((CurrentTime - LastStepTime) > MICROSECONDS_PER_MICROSTEP)
    {
       LastStepTime = CurrentTime;
      digitalWrite(STEP_PIN, HIGH);
      delayMicroseconds((MICROSECONDS_PER_MICROSTEP * 0.9) / 2);
      digitalWrite(STEP_PIN, LOW);
      delayMicroseconds((MICROSECONDS_PER_MICROSTEP * 0.9) / 2);
    }
  }
//  Wire.beginTransmission(MPU_addr);
//  Wire.write(0x3B);  // starting with register 0x3B (ACCEL_XOUT_H)
//  Wire.endTransmission(false);
//  Wire.requestFrom(MPU_addr, 14, true); // request a total of 14 registers
//  float AcX = Wire.read() << 8 | Wire.read(); // 0x3B (ACCEL_XOUT_H) & 0x3C (ACCEL_XOUT_L)
//  float AcY = Wire.read() << 8 | Wire.read(); // 0x3D (ACCEL_YOUT_H) & 0x3E (ACCEL_YOUT_L)
//  float AcZ = Wire.read() << 8 | Wire.read(); // 0x3F (ACCEL_ZOUT_H) & 0x40 (ACCEL_ZOUT_L)
//  Tmp = Wire.read() << 8 | Wire.read(); // 0x41 (TEMP_OUT_H) & 0x42 (TEMP_OUT_L)
//  // GyX=Wire.read()<<8|Wire.read();  // 0x43 (GYRO_XOUT_H) & 0x44 (GYRO_XOUT_L)
//  // GyY=Wire.read()<<8|Wire.read();  // 0x45 (GYRO_YOUT_H) & 0x46 (GYRO_YOUT_L)
//  // GyZ=Wire.read()<<8|Wire.read();  // 0x47 (GYRO_ZOUT_H) & 0x48 (GYRO_ZOUT_L)
//  Serial.print("AcX = "); Serial.println(AcX / 16384);
//  Serial.print(" AcY = "); Serial.println(AcY / 16384);
//  Serial.print(" AcZ = "); Serial.println(AcZ / 16384);
//  Serial.print(" Tmp = "); Serial.print(Tmp / 340.00 + 36.53);
//  Serial.println("");
//  // Serial.print(" | GyX = "); Serial.print(GyX);
//  // Serial.print(" | GyY = "); Serial.print(GyY);
//  // Serial.print(" | GyZ = "); Serial.println(GyZ);
//  delay(333);
}

```

So the commented portion of the code is used to read and print accelerations. Since this is in the same loop as the code for the motor, I'm sure that the delay(333) has a negative effect, but also when I tried step-by-step to include lines of code for accelerometer, the motor slowly started to losing speed and steps...

Does anyone of you have a clue how this could be done so that both devices (the motor with EasyDriver v 4.4 and the accelerometer) could run simultaneously since there can't be 2 void loops? I don't know how I could timewise separate their individual codes since I need to monitor the motor with the accelerometer... Kind regards,

Luka

# Answer
> 0 votes
Thank you **gilhad** and **Jot** for your time, I really appreciate it. However, my best friend who happens to be an electric guru as far as I am concerned, proposed an ever more elegant solution to this multi-tasking problem. He proposed to use timer settings in the void setup, like this:

```
#include<Wire.h>
const int MPU_addr = 0x68; // I2C address of the MPU-6050
int16_t AcX, AcY, AcZ, Tmp, GyX, GyY, GyZ;

#define RPMS                300.0
#define STEP_PIN                9
#define DIRECTION_PIN           8
#define GO_PIN_L                3
#define GO_PIN_R                4

#define STEPS_PER_REV         200
#define MICROSTEPS_PER_STEP     8
#define MICROSECONDS_PER_MICROSTEP   (1000000/(STEPS_PER_REV * MICROSTEPS_PER_STEP)/(RPMS / 60))

uint32_t LastStepTime = 0;
uint32_t CurrentTime = 0;

int Distance = 0;

void setup() {
  bitClear(SREG, 7);
  pinMode(10, OUTPUT);

  TCCR1A = 0;
  TCCR1B = 0;
  TCNT1 = 0;
  TCCR1A = _BV(COM1B1) | _BV(WGM10) | _BV(WGM11);
  TCCR1B = _BV(WGM12) | _BV(WGM13) | _BV(CS10); //prescaler 1, fast PWM, OCR1A as TOP
  OCR1A = 2423; //timer šteje do 444, tako dobim PWM frekvenco 36,363kHz
  OCR1B = int(OCR1A / 2); //prilagajam duty cyle, naj bo kar 50%

  bitSet(SREG, 7); //global interrupt enable

  Wire.begin();
  Wire.beginTransmission(MPU_addr);
  Wire.write(0x6B);  // PWR_MGMT_1 register
  Wire.write(0);     // set to zero (wakes up the MPU-6050)
  Wire.endTransmission(true);
  Serial.begin(9600);

  pinMode(DIRECTION_PIN, OUTPUT);
  digitalWrite(DIRECTION_PIN, LOW);
  pinMode(GO_PIN_L, INPUT);
  pinMode(GO_PIN_R, INPUT);
}

void loop() {
  Distance = Distance + 1;   // record this step
  if (digitalRead(GO_PIN_L) == LOW)
  { TCCR1A = 0;
    TCCR1B = 0;
    TCNT1 = 0;
    delay(100);
    TCCR1A = _BV(COM1B1) | _BV(WGM10) | _BV(WGM11);
    TCCR1B = _BV(WGM12) | _BV(WGM13) | _BV(CS10); //prescaler 1, fast PWM, OCR1A as TOP
    OCR1A = 2423; //timer šteje do 444, tako dobim PWM frekvenco 36,363kHz
    OCR1B = int(OCR1A / 2); //prilagajam duty cyle, naj bo kar 50%

    digitalWrite(8, LOW);
  }
  if (digitalRead(GO_PIN_R) == LOW)
  {
    TCCR1A = 0;
    TCCR1B = 0;
    TCNT1 = 0;
    delay(100);
    TCCR1A = _BV(COM1B1) | _BV(WGM10) | _BV(WGM11);
    TCCR1B = _BV(WGM12) | _BV(WGM13) | _BV(CS10); //prescaler 1, fast PWM, OCR1A as TOP
    OCR1A = 2423; //timer šteje do 444, tako dobim PWM frekvenco 36,363kHz
    OCR1B = int(OCR1A / 2); //prilagajam duty cyle, naj bo kar 50%

    digitalWrite(8, HIGH);
  }
  Wire.beginTransmission(MPU_addr);
  Wire.write(0x3B);  // starting with register 0x3B (ACCEL_XOUT_H)
  Wire.endTransmission(false);
  Wire.requestFrom(MPU_addr, 14, true); // request a total of 14 registers
  float AcX = Wire.read() << 8 | Wire.read(); // 0x3B (ACCEL_XOUT_H) & 0x3C (ACCEL_XOUT_L)
  float AcY = Wire.read() << 8 | Wire.read(); // 0x3D (ACCEL_YOUT_H) & 0x3E (ACCEL_YOUT_L)
  float AcZ = Wire.read() << 8 | Wire.read(); // 0x3F (ACCEL_ZOUT_H) & 0x40 (ACCEL_ZOUT_L)
  Tmp = Wire.read() << 8 | Wire.read(); // 0x41 (TEMP_OUT_H) & 0x42 (TEMP_OUT_L)
  // GyX=Wire.read()<<8|Wire.read();  // 0x43 (GYRO_XOUT_H) & 0x44 (GYRO_XOUT_L)
  // GyY=Wire.read()<<8|Wire.read();  // 0x45 (GYRO_YOUT_H) & 0x46 (GYRO_YOUT_L)
  // GyZ=Wire.read()<<8|Wire.read();  // 0x47 (GYRO_ZOUT_H) & 0x48 (GYRO_ZOUT_L)
  Serial.print("AcX = "); Serial.println(AcX / 16384);
  Serial.print(" AcY = "); Serial.println(AcY / 16384);
  Serial.print(" AcZ = "); Serial.println(AcZ / 16384);
  Serial.print(" Tmp = "); Serial.print(Tmp / 340.00 + 36.53);
  Serial.println("");
  // Serial.print(" | GyX = "); Serial.print(GyX);
  // Serial.print(" | GyY = "); Serial.print(GyY);
  // Serial.print(" | GyZ = "); Serial.println(GyZ);
  delay(333);
}

```

So the portion in void setup:

```
  bitClear(SREG, 7);
  pinMode(10, OUTPUT);

  TCCR1A = 0;
  TCCR1B = 0;
  TCNT1 = 0;
  TCCR1A = _BV(COM1B1) | _BV(WGM10) | _BV(WGM11);
  TCCR1B = _BV(WGM12) | _BV(WGM13) | _BV(CS10); //prescaler 1, fast PWM, OCR1A as TOP
  OCR1A = 2423; //timer counts to 444, PWM frequency is thereby 36,363kHz
  OCR1B = int(OCR1A / 2); //duty cyle is 50%

  bitSet(SREG, 7); //global interrupt enable

```

rotates the step motor WITHOUT any code in the void loop, void loop is only used to change the rotation direction of the motor by using the buttons that I incorporated (GO\_PIN\_L and GO\_PIN\_R) and to measure the acceleration with the accelerometer.

I hope this helps to anyone that might have similar problems. Kind regards,

Luka

# Answer
> 0 votes
This is common problem, how to do two (and more) things with waiting, without blocking `delay` (the simplest way is in example `BlinkWithoutDelay`)

* You wait for motor microsteps (with delayMicroseconds)
* You wait between reading MCU (with delay(333))
* You spend time sending Transmission over Wire (that is relatively slow) and getting answer `requestFrom` (also slow)
* You spend time sending prints over Serial

Each of this is blocking delay of some kind under Arduino (and writing the transmission in non-blocking way is not an easy task)

You should use some kind of `state automaton` (google that) for that (or more such automats - each for one task), to overcome the blocking nature of the steps.

basically you can have lot of loops running together in this manner:

```
long state1_micros,state2_micros,state3_micros; // last time it happened
long state1_delay,state2_delay,state3_delay; // how long wait for next step
#define LOOP1_STEP1 1
#define LOOP1_STEP2 2
#define LOOP1_STEP3 3
#define LOOP2_STEP1 1
#define LOOP2_STEP2 2
#define LOOP2_STEP3 3
#define LOOP2_STEP4 4
#define LOOP2_STEP5 5
#define LOOP2_STEP6 6
#define LOOP2_STEP7 7
void setup(){
...
 long current_micros=micros() ; or millis, if less precision needed
 state1=LOOP1_STEP1;
 state1_micros=current_micros;
 state1_delay=0;
 state2=LOOP2_STEP1;
 state2_micros=current_micros;
 state2_delay=0;
 // state3=LOOP3_STEP1;
 // state3_micros=current_micros;
 // state3_delay=0;
}

void loop(){
 long current_micros=micros() ; or millis, if less precision needed
 if (state1==LOOP1_STEP1 && current_micros-state1_micros>=state1_delay) {
   //state1 paused for at least state1_delay
   if (/*some condition for leave state1 step1  like (digitalRead(GO_PIN_L) == LOW)*/) {
     state1=LOOP1_STEP2;// next step
     state1_micros+=/*some delay like MICROSECONDS_PER_MICROSTEP */;
     /* do action for STEP1, like  digitalWrite(8, LOW); */
    }
  }
 if (state1==LOOP1_STEP2 && current_micros-state1_micros>=state1_delay) {
   //state1 paused for at least state1_delay
   if (/*some condition for leave state1 step2  like (True)*/) {
     state1=LOOP1_STEP3;//next step
     state1_micros =/*some delay like(MICROSECONDS_PER_MICROSTEP * 0.9) / 2) */;
     /* do action for STEP2, like  digitalWrite(STEP_PIN, HIGH); */
    }
  }
 if (state1==LOOP1_STEP3 && current_micros-state1_micros>=state1_delay) {
   //state1 paused for at least state1_delay
   if (/*some condition for leave state1 step3  like (True)*/) {
     state1=LOOP1_STEP1;//next step
     state1_micros =/*some delay like(MICROSECONDS_PER_MICROSTEP * 0.9) / 2) */;
     /* do action for STEP2, like  digitalWrite(STEP_PIN, LOW); */
    }
  }
////////
 if (state2==LOOP2_STEP1 && current_micros-state2_micros>=state2_delay) {
   //state2 paused for at least state2_delay
   if (/*some condition for leave state2 step1  like (digitalRead(GO_PIN_L) == LOW)*/) {
     state1=LOOP2_STEP2;// next step
     state1_micros+=/*some delay like 100*1000 (333/3) */;
     /* do action for STEP1, like
  Wire.beginTransmission(MPU_addr);
  Wire.write(0x3B);  // starting with register 0x3B (ACCEL_XOUT_H)
  Wire.endTransmission(false);
  Wire.requestFrom(MPU_addr, 14, true); // request a total of 14 registers
  float AcX = Wire.read() << 8 | Wire.read(); // 0x3B (ACCEL_XOUT_H) & 0x3C (ACCEL_XOUT_L)
  float AcY = Wire.read() << 8 | Wire.read(); // 0x3D (ACCEL_YOUT_H) & 0x3E (ACCEL_YOUT_L)
  float AcZ = Wire.read() << 8 | Wire.read(); // 0x3F (ACCEL_ZOUT_H) & 0x40 (ACCEL_ZOUT_L)
  Tmp = Wire.read() << 8 | Wire.read(); // 0x41 (TEMP_OUT_H) & 0x42 (TEMP_OUT_L)
  // GyX=Wire.read()<<8|Wire.read();  // 0x43 (GYRO_XOUT_H) & 0x44 (GYRO_XOUT_L)
  // GyY=Wire.read()<<8|Wire.read();  // 0x45 (GYRO_YOUT_H) & 0x46 (GYRO_YOUT_L)
  // GyZ=Wire.read()<<8|Wire.read();  // 0x47 (GYRO_ZOUT_H) & 0x48 (GYRO_ZOUT_L)
 */
    }
  }
 if (state2==LOOP2_STEP2 && current_micros-state2_micros>=state2_delay) {
   //state2 paused for at least state2_delay
   if (/*some condition for leave state1 step2  like (True)*/) {
     state2=LOOP2_STEP3;//next step
     state2_micros +=/*some delay like 10*1000 (10ms) */;
     /* do action for STEP2, like  Serial.print("AcX = "); Serial.println(AcX / 16384);  */
    }
  }
 if (state2==LOOP2_STEP3 && current_micros-state2_micros>=state2_delay) {
   //state2 paused for at least state2_delay
   if (/*some condition for leave state2 step3  like (True)*/) {
     state2=LOOP2_STEP4;//next step
     state2_micros +=/*some delay like 10*1000 (10ms) */;
     /* do action for STEP3, like Serial.print(" AcY = "); Serial.println(AcY / 16384); */
    }
  }
 if (state2==LOOP2_STEP4 && current_micros-state2_micros>=state2_delay) {
   //state2 paused for at least state2_delay
   if (/*some condition for leave state2 step4  like (True)*/) {
     state2=LOOP2_STEP5;//next step
     state2_micros +=/*some delay 10*1000 (10ms) */;
     /* do action for STEP4, like  Serial.print(" AcZ = "); Serial.println(AcZ / 16384); */
    }
  }
 if (state2==LOOP2_STEP5 && current_micros-state2_micros>=state2_delay) {
   //state2 paused for at least state2_delay
   if (/*some condition for leave state2 step5  like (True)*/) {
     state2=LOOP2_STEP6;//next step
     state2_micros +=/*some delay 10*1000 (10ms) */;
     /* do action for STEP5, like  Serial.print(" AcZ = "); Serial.println(AcZ / 16384); */
    }
  }
 if (state2==LOOP2_STEP6 && current_micros-state2_micros>=state2_delay) {
   //state2 paused for at least state2_delay
   if (/*some condition for leave state2 step6  like (True)*/) {
     state2=LOOP2_STEP7;//next step
     state2_micros +=/*some delay 10*1000 (10ms) */;
     /* do action for STEP6, like  Serial.println(""); */
    }
  }

 if (state2==LOOP2_STEP7 && current_micros-state2_micros>=state2_delay) {
   //state2 paused for at least state2_delay
   if (/*some condition for leave state2 step7  like (True)*/) {
     state2=LOOP2_STEP1;//start over
     state2_micros +=/*some delay (333-100-4*10)*1000 (rest to 333ms) */;
     /* do action for STEP7, like  nothing*/
    }
  }
/////
/* if we have more automatons, like stat3, stat4 and so on, put it her */
} // end loop()

```

---
Tags: arduino-uno, accelerometer, code-review, stepper, mpu6050
---


title: Sending Large Amounts of Serial Data

text:
# Question
Title: Sending Large Amounts of Serial Data
So in the fields of robotics sometimes you need multiple boards and or computers linked together to share information or save statistical data. Currently I need to send a few different variables over a serial connection and was wondering what was the best way to go about doing such?

So far I've determined that sending structures would probably be the easier way to send data. Does anyone know of any other way that might be more efficient?

Please keep in mind that I will essentially be having to send the data for 4 motors, compressor, different temperatures, random things, and the 3 sections of the arm.

# Answer
With my personal thoughts on Structs being the most efficient way to send many different variables I've constructed a library to help make it easier to send structs and variables over serial. Source Code

In this library it makes sending through serial easily. I've used with with hardware and software serial. Usually this is used in conjunct with xbee's so I can wirelessly send the data to and from the robot.

When sending data it make it simple as it allows you to either send a variable or a struct (it doesn't care).

**Here is an example of sending a simple char over the serial:**

```
// Send the variable charVariable over the serial.
// To send the variable you need to pass an instance of the Serial to use,
// a reference to the variable to send, and the size of the variable being sent.
// If you would like you can specify 2 extra arguments at the end which change the
// default prefix and suffix character used when attempting to reconstruct the variable
// on the receiving end. If prefix and suffix character are specified they'll need to
// match on the receiving end otherwise data won't properly be sent across

char charVariable = 'c'; // Define the variable to be sent over the serial
StreamSend::sendObject(Serial, &charVariable, sizeof(charVariable));

// Specify a prefix and suffix character
StreamSend::sendObject(Serial, &charVariable, sizeof(charVariable), 'a', 'z');

```

**Example of sending a simple int over the serial:**

```
int intVariable = 13496; // Define the int to be sent over the serial
StreamSend::sendObject(xbeeSerial, &intVariable, sizeof(intVariable));

// Specify a prefix and suffix character
StreamSend::sendObject(xbeeSerial, &intVariable, sizeof(intVariable), 'j', 'p');

```

**Example of sending a struct over serial:**

```
// Define the struct to be sent over the serial
struct SIMPLE_STRUCT {
  char charVariable;
  int intVariable[7];
  boolean boolVariable;
};
SIMPLE_STRUCT simpleStruct;
simpleStruct.charVariable = 'z'; // Set the charVariable in the struct to z

// Fill the intVariable array in the struct with numbers 0 through 6
for(int i=0; i<7; i++) {
  simpleStruct.intVariable[i] = i;
}

// Send the struct to the object xbeeSerial which is a software serial that was
// defined. Instead of using xbeeSerial you can use Serial which will imply the
// hardware serial, and on a Mega you can specify Serial, Serial1, Serial2, Serial3.
StreamSend::sendObject(xbeeSerial, &simpleStruct, sizeof(simpleStruct));

// Send the same as above with a different prefix and suffix from the default values
// defined in StreamSend. When specifying when prefix and suffix character to send
// you need to make sure that on the receiving end they match otherwise the data
// won't be able to be read on the other end.
StreamSend::sendObject(xbeeSerial, &simpleStruct, sizeof(simpleStruct), '3', 'u');

```

**Receiving Examples:**

**Receiving a char that was send via Streamsend:**

```
char charVariable; // Define the variable on where the data will be put

// Read the data from the Serial object an save it into charVariable once
// the data has been received
byte packetResults = StreamSend::receiveObject(Serial, &charVariable, sizeof(charVariable));

// Reconstruct the char coming from the Serial into charVariable that has a custom
// suffix of a and a prefix of z
byte packetResults = StreamSend::receiveObject(Serial, &charVariable, sizeof(charVariable), 'a', 'z');

```

**Receiving an int that was sent via StreamSend:**

```
int intVariable; // Define the variable on where the data will be put

// Reconstruct the int from xbeeSerial into the variable intVariable
byte packetResults = StreamSend::receiveObject(xbeeSerial, &intVariable, sizeof(intVariable));

// Reconstruct the data into intVariable that was send with a custom prefix
// of j and a suffix of p
byte packetResults = StreamSend::receiveObject(xbeeSerial, &intVariable, sizeof(intVariable), 'j', 'p');

```

**Receiving a Struct that was sent via StreamSend:**

```
// Define the struct that the data will be put
struct SIMPLE_STRUCT {
  char charVariable;
  int intVariable[7];
  boolean boolVariable;
};
SIMPLE_STRUCT simpleStruct; // Create a struct to store the data in

// Reconstruct the data from xbeeSerial into the object simpleStruct
byte packetResults = StreamSend::receiveObject(xbeeSerial, &simpleStruct, sizeof(simpleStruct));

// Reconstruct the data from xbeeSerial into the object simplestruct that has
// a prefix of 3 and a suffix of p
byte packetResults = StreamSend::receiveObject(xbeeSerial, &simpleStruct, sizeof(simpleStruct), '3', 'p');

```

Once you read the data using `StreamSend::receiveObject()` you need to know if the data was GOOD, Not Found, or BAD.

**Good** = Successful

**Not Found** = No prefix character was found in the specified ostream

**Bad** = Somehow there was a prefix character found, but the data isn't intact. Usually it means there was no suffix character found or the data wasn't the correct size.

**Testing Validity of Data:**

```
// Once you call StreamSend::receiveObject() it returns a byte of the status of
// how things went. If you run that though some of the testing functions it'll
// let you know how the transaction went
if(StreamSend::isPacketGood(packetResults)) {
  //The Packet was Good
} else {
  //The Packet was Bad
}

if(StreamSend::isPacketCorrupt(packetResults)) {
  //The Packet was Corrupt
} else {
  //The Packet wasn't found or it was Good
}

if(StreamSend::isPacketNotFound(packetResults)) {
  //The Packet was not found after Max # of Tries
} else {
  //The Packet was Found, but can be corrupt
}

```

**SteamSend Class:**

```
#include "Arduino.h"

#ifndef STREAMSEND_H
#define STREAMSEND_H

#define PACKET_NOT_FOUND 0
#define BAD_PACKET 1
#define GOOD_PACKET 2

// Set the Max size of the Serial Buffer or the amount of data you want to send+2
// You need to add 2 to allow the prefix and suffix character space to send.
#define MAX_SIZE 64

class StreamSend {
  private:
    static int getWrapperSize() { return sizeof(char)*2; }
    static byte receiveObject(Stream &ostream, void* ptr, unsigned int objSize, unsigned int loopSize);
    static byte receiveObject(Stream &ostream, void* ptr, unsigned int objSize, unsigned int loopSize, char prefixChar, char suffixChar);
    static char _prefixChar; // Default value is s
    static char _suffixChar; // Default value is e
    static int _maxLoopsToWait;

  public:
    static void sendObject(Stream &ostream, void* ptr, unsigned int objSize);
    static void sendObject(Stream &ostream, void* ptr, unsigned int objSize, char prefixChar, char suffixChar);
    static byte receiveObject(Stream &ostream, void* ptr, unsigned int objSize);
    static byte receiveObject(Stream &ostream, void* ptr, unsigned int objSize, char prefixChar, char suffixChar);
    static boolean isPacketNotFound(const byte packetStatus);
    static boolean isPacketCorrupt(const byte packetStatus);
    static boolean isPacketGood(const byte packetStatus);

    static void setPrefixChar(const char value) { _prefixChar = value; }
    static void setSuffixChar(const char value) { _suffixChar = value; }
    static void setMaxLoopsToWait(const int value) { _maxLoopsToWait = value; }
    static const char getPrefixChar() { return _prefixChar; }
    static const char getSuffixChar() { return _suffixChar; }
    static const int getMaxLoopsToWait() { return _maxLoopsToWait; }

};

//Preset Some Default Variables
//Can be modified when seen fit
char StreamSend::_prefixChar = 's';   // Starting Character before sending any data across the Serial
char StreamSend::_suffixChar = 'e';   // Ending character after all the data is sent
int StreamSend::_maxLoopsToWait = -1; //Set to -1 for size of current Object and wrapper

/**
  * sendObject
  *
  * Converts the Object to bytes and sends it to the stream
  *
  * @param Stream to send data to
  * @param ptr to struct to fill
  * @param size of struct
  * @param character to send before the data stream (optional)
  * @param character to send after the data stream (optional)
  */
void StreamSend::sendObject(Stream &ostream, void* ptr, unsigned int objSize) {
  sendObject(ostream, ptr, objSize, _prefixChar, _suffixChar);
}

void StreamSend::sendObject(Stream &ostream, void* ptr, unsigned int objSize, char prefixChar, char suffixChar) {
  if(MAX_SIZE >= objSize+getWrapperSize()) { //make sure the object isn't too large
    byte * b = (byte *) ptr; // Create a ptr array of the bytes to send
    ostream.write((byte)prefixChar); // Write the suffix character to signify the start of a stream

    // Loop through all the bytes being send and write them to the stream
    for(unsigned int i = 0; i<objSize; i++) {
      ostream.write(b[i]); // Write each byte to the stream
    }
    ostream.write((byte)suffixChar); // Write the prefix character to signify the end of a stream
  }
}

/**
  * receiveObject
  *
  * Gets the data from the stream and stores to supplied object
  *
  * @param Stream to read data from
  * @param ptr to struct to fill
  * @param size of struct
  * @param character to send before the data stream (optional)
  * @param character to send after the data stream (optional)
  */
byte StreamSend::receiveObject(Stream &ostream, void* ptr, unsigned int objSize) {
    return receiveObject(ostream, ptr, objSize, _prefixChar, _suffixChar);
}
byte StreamSend::receiveObject(Stream &ostream, void* ptr, unsigned int objSize, char prefixChar, char suffixChar) {
  return receiveObject(ostream, ptr, objSize, 0, prefixChar, suffixChar);
}

byte StreamSend::receiveObject(Stream &ostream, void* ptr, unsigned int objSize, unsigned int loopSize, char prefixChar, char suffixChar) {
  int maxLoops = (_maxLoopsToWait == -1) ? (objSize+getWrapperSize()) : _maxLoopsToWait;
  if(loopSize >= maxLoops) {
      return PACKET_NOT_FOUND;
  }
  if(ostream.available() >= (objSize+getWrapperSize())) { // Packet meets minimum size requirement
    if(ostream.read() != (byte)prefixChar) {
      // Prefix character is not found
      // Loop through the code again reading the next char
      return receiveObject(ostream, ptr, objSize, loopSize+1, prefixChar, suffixChar);
    }

    char data[objSize]; //Create a tmp char array of the data from Stream
    ostream.readBytes(data, objSize); //Read the # of bytes
    memcpy(ptr, data, objSize); //Copy the bytes into the struct

    if(ostream.read() != (byte)suffixChar) {
      //Suffix character is not found
      return BAD_PACKET;
    }
      return GOOD_PACKET;
  }
  return PACKET_NOT_FOUND; //Prefix character wasn't found so no packet detected
}

boolean StreamSend::isPacketNotFound(const byte packetStatus) {
    return (packetStatus == PACKET_NOT_FOUND);
}

boolean StreamSend::isPacketCorrupt(const byte packetStatus) {
    return (packetStatus == BAD_PACKET);
}

boolean StreamSend::isPacketGood(const byte packetStatus) {
    return (packetStatus == GOOD_PACKET);
}

#endif

```
> 9 votes

# Answer
If you really wanted to send it *fast*, i recommend Full Duplex Serial (FDX). It's the same protocol that USB and ethernet use, and it's a lot faster than UART. The downside is that it usually requires external hardware to facilitate the high data rates. I've heard that the new softwareSreial supports FDX, but this may be slower even than hardware UART. For more on communication protocols, see How to connect two Arduino without shields?
> 1 votes

# Answer
Sending a structure is fairly simple.

You can declare the structure as you normally would, and then use memcpy(@myStruct,@myArray) to copy the data to a new location, and then use something similar to the below code to write the data as a datastream.

```
unsigned char myArraySender[##];   //make ## large enough to fit struct
memcpy(&myStruct,&myArraySender);  //copy raw data from struct to the temp array
digitalWrite(frameStartPin,High);  //indicate to receiver that data is coming
serial.write(sizeof myStruct);     //tell receiver how many bytes to rx
Serial.write(&myArraySender,sizeof myStruct);   //write bytes
digitalWrite)frameStartPin,Low);   //done indicating transmission

```

Then you can attach an interrupt routine to the pin on the other device that does the following:

```
volatile unsigned char len, tempBuff[##];
//volatile because the interrupt will not happen at predictable intervals.

attachInterrupt(0,readSerial,Rising);

```

//tell the mcu to call fxn when pinhigh. This will happen during virtually any moment. if that is not desired, remove the interrupt and simply watch for new characters in your main executive loop (aka, UART polling).

```
void readSerial(unsigned char *myArrayReceiver){
    unsigned char tempbuff[sizeof myArrayReceiver];
    while (i<(sizeof myArrayReceiver)) tempBuff[i]=Serial.read();
    memcpy(&tempbuff,&myArrayReceiver);
    Serial.flush();
}

```

Syntax and use of pointers will need some review. I pulled an all-nighter so I'm sure the above code won't even compile, but the idea is there. Fill your structure, copy it, use out-of-band signalling to avoid framing errors, write the data. On the other end, receive the data, copy it to a struct, and then the data becomes accessible via normal member access methods.

The use of bitfields will also work, just be aware that the nibbles will appear to be backwards. For instance, attempting to write 0011 1101, may result in 1101 0011 appearing at the other end if the machines differ in byte order.

If data integrity is important, you can also add a checksum to make sure you aren't copying misaligned garbage data. This is quick and effective check that I recommend.
> 1 votes

# Answer
If you can tolerate the data volume, debugging communicatons is **so** much easier when sending strings than when sending binary; sprintf()/sscanf() and their variants are your friends here. Enclose the communication in dedicated functions in their own module (.cpp file); if you need to optimize the channel later - **after** you have a working system - you can replace the string-based module with one coded for smaller messages.

You'll make your life lots easier if you hold tight to protocol specs on transmission and interpret them more loosely on reception, regard to field widths, delimiters, line endings, insignificant zeros, presence of `+` signs, etc.
> 1 votes

# Answer
I have no official credentials here, but in my experience things have gone pretty efficiently when I pick a certain character position(s) to contain the state of a variable, so that you might designate the first three characters as the temperature, and the next three as the angle of a servo, and so on. On the sending end I would save the variables individually and then combine them in a string to send serially. On the receiving end I would have the string picked apart, getting the first three characters and turning them into whatever variable type i need, then doing so again to get the next variable value. This system works best when you know for certain the amount of characters each variable will take up, and you always look for the same variables (which I hope is a given) each time the serial data loops through.

You can pick one variable to put last of indeterminate length and then get that variable from it's first character to the end of the string. Granted, the serial data string could get really long depending on the variable types and the sheer amount of them, but this is the system I use and so far the only setback I've hit is the serial length, so that's the only disadvantage I know of.
> 0 votes

# Answer
## Send struct data across serial

Nothing fancy. Sends a struct. It uses an escape character '^' to delimit the data.

## Arduino code

```
typedef struct {
 float ax1;
 float ay1;
 float az1;
 float gx1;
 float gy1;
 float gz1;
 float ax2;
 float ay2;
 float az2;
 float gx2;
 float gy2;
 float gz2;

} __attribute__((__packed__))data_packet_t;

data_packet_t dp;

template <typename T> void sendData(T data)
{
 unsigned long uBufSize = sizeof(data);
 char pBuffer[uBufSize];

 memcpy(pBuffer, &dp, uBufSize);
 Serial.write('^');
 for(int i = 0; i<uBufSize;i++) {
   if(pBuffer[i] == '^')
   {
    Serial.write('^');
    }
   Serial.write(pBuffer[i]);
 }
}
void setup() {
  Serial.begin(57600);
}
void loop(){
dp.ax1 = 0.03; // Note that I didn't fill in the others. Too much work. ;p
sendData<data_packet_t>(dp);
}

```

## Python Code:

```
import serial
from  copy import copy
from struct import *

ser = serial.Serial(
#   port='/dev/cu.usbmodem1412',
  port='/dev/ttyUSB0',
#     port='/dev/cu.usbserial-AL034MCJ',
    baudrate=57600
)

def get_next_data_block(next_f):
    if not hasattr(get_next_data_block, "data_block"):
        get_next_data_block.data_block = []
    while (1):
        try:
            current_item = next_f()
            if current_item == '^':
                next_item = next_f()
                if next_item == '^':
                    get_next_data_block.data_block.append(next_item)
                else:
                    out = copy(get_next_data_block.data_block)
                    get_next_data_block.data_block = []
                    get_next_data_block.data_block.append(next_item)
                    return out
            else:
                get_next_data_block.data_block.append(current_item)
        except :
            break

for i in range(1000): # just so that the program ends - could be in a while loop
    data_ =  get_next_data_block(ser.read)
    try:
        print unpack('=ffffffffffff', ''.join(data_))
    except:
        continue

```
> 0 votes

---
Tags: serial
---


# Question
Title: Three or more Arduino slaves sending bytes to 2 different I2C devices
I'm trying to connect 3 Arduinos with this scheme: Arduino1 Master, Arduino2 Slave, Arduino3 Slave. The slave devices need to communicate with each other and I'm trying to programming Arduino2 and transmit bytes to the other slave device Arduino3 and Master Arduino1 at the same time. Is that possible?

Master CODE:

```
#include <Wire.h>

void setup() {
  Wire.begin();
}

void loop() {
  Wire.requestFrom(0x04, 2);
  while (Wire.available()) {
    var1 = Wire.read();
    var2 = Wire.read();
  }
}

```

Arduino1 Slave:

```
#include <Wire.h>

void setup() {
  Wire.begin(0x05);
  Wire.onReceive(receiveEvent);
}

void loop() {
}

void receiveEvent(int howMany) {
  var1 = Wire.read();
  Serial.print("VAR1 is : ");
  Serial.println(var1);
}

```

Adrduino2 Slave code:(Where I think I'm wrong)

```
#include <Wire.h>
int var = 123;
int var2 = 123;
int var3 = 123;

void setup() {
  Wire.begin(0x04);
  Wire.onRequest(requestEvent);
}

void loop() {
  Wire.beginTransmission(0x05);
  Wire.write(var);
  Wire.endTransmission();
}

void requestEvent() {
  Wire.write(var1);
  Wire.write(var2);
}

```

Is this the correct way to make the Arduino2 send to 2 devices?

# Answer
> 2 votes
As soon as an Arduino starts writing data, it is a Master. Do you use Arduino Mega 2560 and Arduino Uno and Nano boards ? In theory those ATmega microcontrollers can handle collisions in a multi-Master bus, and in theory the Wire library handles collisions as well. However, everyone tries to avoid that, because it causes a lot of problems. You would even have to program a complete new layer in the code to re-transmit data until it was received without collision.

Select one Arduino board as Master, and use the Master to read and write data. If you want to transfer data from one Slave to the other Slave, then use Master to read the data from one Slave and write the data to the other Slave.

It is possible to use other busses between the two Slave Arduino boards.

---
Tags: i2c
---


title: Servotimer2, detach "stop"

text:
# Question
Title: Servotimer2, detach "stop"
I'm still struggling with the Servotimer2 library

I have an Arduino uno board with a servo motor with the servotimer2 library because I'm using a music shield beside the servomotor and the music shield library and the servo.h wasn't compatible. But finally I make the two of them working together with the servotimer2.h but now I want my servo to rotate 90 or 180 and then "stop" for a minute and come back again, rotate, stop, rotate,stop, rotate, stop... short of thing so I read this what is commonly done to stop a servo after reaching desired point and now I know that servo can't stop, but they can detach so I tried making something like this

```
#include <ServoTimer2.h>  // the servo library
#define rollPin  9

ServoTimer2 servoRoll;

void setup() {
  servoRoll.attach(rollPin);

}

// this function just increments a value until it reaches a maximum
int incPulse(int val, int inc){
   if( val + inc  > 2000 )
      return 1000 ;
   else
       return val + inc;

}

void loop()
{
   mover();
   parar();

}

void mover() {
 int val;

   servoRoll.attach(rollPin);
   val = incPulse( servoRoll.read(), 2);
   servoRoll.write(val);
   delay(10);

}
void parar() {

  servoRoll.detach();
     delay(100);
}

```

but the servo is only moving very slow and I think is not detaching in any moment. I'm quite lost, I'm very noobie and in the post(what is commonly done to stop a servo after reaching desired point) they said things like making while(true){} loop in the setup? or use millis() and other things that I don't understand quite well But someone tried to do something like control the time the servo is stopping with the delay, so I tried something like this

```
#include <ServoTimer2.h>  // the servo library

// define the pins for the servos
#define rollPin  9

int pos = 0;

ServoTimer2 servoRoll;    // declare variables for up to eight servos

void setup() {
  servoRoll.attach(rollPin);     // attach a pin to the servos and they will start pulsing

}

//from https://learn.adafruit.com/multi-tasking-the-arduino-part-1/a-clean-sweep

void loop()
{
 for(pos = 0; pos < 180; pos += 1)  // goes from 0 degrees to 180 degrees
  {                                  // in steps of 1 degree
    servoRoll.write(pos);              // tell servo to go to position in variable 'pos'
    delay(15);                       // waits 15ms for the servo to reach the position
  }
  for(pos = 180; pos>=1; pos-=1)     // goes from 180 degrees to 0 degrees
  {
    servoRoll.write(pos);              // tell servo to go to position in variable 'pos'
    delay(15);                       // waits 15ms for the servo to reach the position
  }

}

```

but with this code, my servo is only moving once, and then stops and don't move again

and I think that my servo with the servotimer2 library is only moving with this

```
   int incPulse(int val, int inc){
   if( val + inc  > 2000 )
      return 1000 ;
   else
       return val + inc;
}

void loop()
{
 int val;

   val = incPulse( servoRoll.read(), 1);
   servoRoll.write(val);
  delay(10);
}

```

so, any ideas of what I'm doing wrong?

# Answer
> 1 votes
*my servo is only moving once, and then stops* You mean it turns 180° then no more? Once it has reached 180° (or 2000 µs) you need to decrease `val` by one to go the other way (from 2000 to 1000). For example:

```
int direction = 1;  // 1 or -1
void loop()
{
   int val;

   val = incPulse( servoRoll.read(), direction);
   servoRoll.write(val);
   if (direction <= 1000 || direction >= 2000) {
      direction = -direction;
   }
   delay(10);
}

```

---
Tags: arduino-uno, servo
---


# Question
Title: SMS Receiving problem - Arduino Uno and SIM900A GSM Module
My intention is to control an LED according to the content of the SMS received. For example, if the SMS is "ON", turn on the LED and if it is "OFF", turn it off. I referred many sites and got the below code. The digital pins 9 and 10 are used instead of Rx and Tx to avoid the code uploading problem.

(I have kept the different versions of AT commands commented in the code because I'm not sure which one is correct. With the current one, I'm able to get some kind of output which I've mentioned after the code.)

```
#include <SoftwareSerial.h>
SoftwareSerial mySerial(9, 10);

char msg;
void setup()
{
  Serial.begin(9600);
  mySerial.begin(9600);   // Setting the baud rate of GSM Module
  delay(1000);
  //mySerial.print("AT+CMGF=1r"); // set SMS mode to text
  mySerial.print("AT+CMGF=1\r");  // set SMS mode to text

  delay(100);
  //mySerial.println("AT+CNMI=2,2,0,0,0"); // AT Command to receive a live SMS
  //mySerial.print("AT+CNMI=2,2,0,0,0r");

  mySerial.print("AT+CNMI=1,2,0,0,0\r"); // AT Command to receive a live SMS
  delay(100);
  Serial.println("Ready");
}

void loop()
{
  if (mySerial.available()>0)
  {
    msg=mySerial.read();
    Serial.print(msg);
  }
}

```

This is the output I'm getting..

```
Ready
AT+CMGF=1
AT+CNMI=1,2,0,0,0

OK

+CMTI: "SM",31

+CMTI: "SM",32

+CMTI: "SM",33

+CMTI: "SM",34

```

The issue is, I'm not able to retrieve the message content. What I'm getting is

"+CMTI: "SM",31"

"+CMTI: "SM",32"

and the number keeps on incrementing. (33, 34 and so on).

I do understand that I have to parse the message to get the exact content, but here I'm not getting the content at all. What exactly should I do to get the SMS content? Could anybody help me to solve this?

One more thing, the GSM module I'm using is a SIM900A type (from elementzonline.com). It's not a shield type, so I've made connections using wires; the Rx, Tx connections and the ground one.

(Sorry for the bad explanation, I'm a complete noob in Arduino, a hobbyist.)

Thanks in advance.

# Answer
> 0 votes
You should download the SIM900 command set (Google away) and read it. According to your CNMI settings, sms notifications are pushed to the Arduino not the sms content, thus the +CMTI data you're receiving. `SM` tells you the sms is stored on the SIM and the number that follows tells you the index of the sms in the SIM memory. With that index, you use the command `AT+CMGR=<index>` to get the sms content (as well as the sender number and timestamp) from the modem.

So basically, you must parse the CMTI notification, get the number at the end, and use that number to retrieve the SMS content from the modem with the CMGR command. You could also change your CNMI settings to (2,2,0,0,0) i think, if you want the content of the messages to be sent by the modem, and not the notifications alone.

In either case, the SoftwareSerial Receive buffer will most likely overflow when receiving the sms content from the modem; because you cant read() fast enough. This will make the message appear truncated. You have to increase the size of the SoftwareSerial RX buffer to prevent this. Here's a link to an answer where this is explained. Good luck.

# Answer
> 1 votes
Instead of using At commands use the GSM library of Arduino it easier to understand and implement. the code to recieve SMS

```
    #include <GSM.h>

    // PIN Number for the SIM
    #define PINNUMBER "" //sim pin incase the sim is kept locked

    // initialize the library instances
    GSM gsmAccess;
    GSM_SMS sms;

    // Array to hold the number a SMS is retreived from
    char senderNumber[20];

    void setup() {
      // initialize serial communications and wait for port to open:
      Serial.begin(9600);
      while (!Serial) {
        ; // wait for serial port to connect. Needed for native USB port only
      }

      Serial.println("SMS Messages Receiver");

      // connection state
      boolean notConnected = true;

      // Start GSM connection
      while (notConnected) {
        if (gsmAccess.begin(PINNUMBER) == GSM_READY) {
          notConnected = false;
        } else {
          Serial.println("Not connected");
          delay(1000);
        }
      }

      Serial.println("GSM initialized");
      Serial.println("Waiting for messages");
    }

    void loop() {
      char c;

      // If there are any SMSs available()
      if (sms.available()) {
        Serial.println("Message received from:");

        // Get remote number
        sms.remoteNumber(senderNumber, 20);
        Serial.println(senderNumber);

        // An example of message disposal
        // Any messages starting with # should be discarded
        if (sms.peek() == '#') {
          Serial.println("Discarded SMS");
          sms.flush();
        }

        // Read message bytes and print them
        while (c = sms.read()) {
          Serial.print(c);
        }

        Serial.println("\nEND OF MESSAGE");

        // Delete message from modem memory
        sms.flush();
        Serial.println("MESSAGE DELETED");
      }

      delay(1000);

    }

```

# Answer
> 0 votes
use cnmi 2,2,0,0,0 to get the SMS contents use cnmi 1,2,0,0,0, to get only the notification with CMTI+.... if you want to read the cont then u need to parse and check wht number u get in SM and then read that numbered msg using CMGR

---
Tags: arduino-uno, gsm
---


title: Image Breakdown

text:
# Question
Title: Image Breakdown
I've been trying to figure out a way to store an image on the Arduino, and I couldn't figure it out. What I've been trying to do with this image is the following:

* Test that the arduino has the image by displaying on a touchscreen (I have the adafruit 2.8 inch touch screen)
* Break down the image into an array, in which contains pixel by pixel color RGB color info of the image

`int pictureData = [[100,50,0],[176,255,5],...]; // RGB Values within the array`

How can I store an image and break it down as shown? Is there no way to do this? I would appreciate any help! Thank you very much!

I am using Arduino IDE for code and I have Arduino Uno/MEGA, which ever is necessary for this task. All info of screen is on adafruit: https://www.adafruit.com/product/376

The below image shows an example of displaying the image:

# Answer
I presume you are trying to create a system that has one image stored, and want the image to be available without needing an SD card reader on the system.

If the logic of your program is small enough to fit into about 18KB of flash memory, you can store one 230KB image in flash on a Mega. (230KB+18KB+8KB = 256KB = Mega flash size. 8KB is Mega bootloader size.) See the PROGMEM page at arduino.cc for examples of declaring and accessing arrays from flash.

If you end up needing lots more flash for the logic of your program, consider compressing the 18 bits of each pixel to 16 bits. The 230KB figure is 240·320·3. Each pixel on the display uses six bits per color, stored in three bytes per pixel. Instead of keeping all the bits, you could clip the blue to its high four bits; ie, save 6-6-4 for RGB in two bytes instead of 6-6-6 in three bytes. Or could clip two of the colors to their high five bits; eg, save 6-5-5 or 5-6-5. At two bytes per pixel, an image would take 240·320·2 = 153600 bytes of flash, leaving roughly 94KB for program logic.

In all of these approaches, image data would be brought into RAM row by row or column by column, unpacked, and copied to the RAM buffers in the display.

One could also apply some compression algorithms to the image instead of using BMP format.

If you need more images than one, you could further reduce image quality, for example could save 3-3-2 high bits of color per pixel, or could save only every other pixel in a row or column or both, reducing storage to a half or fourth as much. Or you could have one reasonably good image stored 6-6-4 at 16 bits per pixel, so about 154KB, plus several monochrome images stored one bit per pixel, or about 10KB each.

---

*Edit 1:* Re “how would I take an image and convert it into the RGB array?”, one straightforward approach is to write an image-converter program (that runs on your development system) to read an image file and output C code representing the image data in arrays; that is, to produce C-style arrays printed in ASCII. Again, this recommendation is predicated on the notion that you are trying to create a system that has one image stored, and want the image to be available without needing an SD card reader on the system.

I recommend writing the image-converter program in Python. See, for example, the accepted answer at *Convert an image to 2D array in python*, to which you would need to add a few lines of code to write out C code to a file, so that you could include that code into a sketch. Also see *How to get an array from RGB values of a bitmap image?* and *Working with .bmp files in python 3*.

Some C-language examples appear in answers to *How to convert a .bmp image into Byte array using C Program* and *How to convert an image to WORD (uint16) array?*, which are among the first links in a stackexchange search for “convert bmp image to array”.

Wikipedia's BMP file format article shows the layout of BMP files in general. Using various image-handling libraries (as recommended in SE questions listed above) sidesteps having to deal with low-level BMP details. However, you may be able to use a simple program or application to produce RGB565 color format files, eg as at *Bitmap to RGB565 format* on codeguru.com, and then write a simple program to convert that particular form to C-style arrays printed in ASCII.
> 5 votes

# Answer
240 by 320 pixels. That's 76800 pixels. In your example it looks like you want 3 bytes per pixel, so that's 230400 bytes. An Arduino Mega has 8K bytes of SRAM memory. There's enough room in the memory on the Arduino Mega to hold 0.003% of your image.

Maybe you could store the image on an SD card and put it on the screen little piece by little piece, but that is going to be painfully slow.
> 5 votes

---
Tags: display, array
---


# Question
Title: Can I connect my Arduino Uno to a power source and a battery at the same time?
My aim is to be able to power my Arduino while there is a power supply and if there isn't the Arduino automatically switches over to the battery. The components connected to the Arduino are pir sensor, smoke sensor, SIM 800L, temperature sensor, 6v relay.

# Answer
> 1 votes
Yes, to my knowledge this is done automatically, and there is no harm when connecting the Arduino to two power sources. When I power my Arduino I have it connected to my computer and the wall. So theoretically, if the electricity in the wall stopped coming, it would start taking power from the computer. Same works for battery.

# Answer
> 0 votes
Most mainstream and reputable Arduino variants (the UNO or Pro, for example) have protection circuitry that allows it to basically ignore where its power is coming from, as long as the voltage isn't above 20v. This is because almost every Arduino device funnels its power through an appropriate regulator, ensuring there is no problem with the voltages or available current suddenly changing (switching power feeds). However, you should account for what happens when you plug an external power source in the same loop as a battery that might be a different voltage. If you're going to try to have them manually switch then you'll need an external circuit (perhaps using a transistor that shuts off the battery when the power supply is active, with capacitors for a buffer), else you could have problems with popping batteries. But be warned, if you plug your battery into the PWR (5V/3V3) pin(s) of the Arduino, then you'll need to provide your own protection.

---
Tags: arduino-uno, power
---


# Question
Title: Understanding how methods and pointers inside a function work
After this question i starteted going deep with the theory, and started studyng step-by-step with the "Beginning C, for Arduino " Jack Purdum.

I finished to study the functions chapter, but i still have some doubts on the code, i hope this will be not a dumb question.

---

## Why there is a Method "Print" not a Data Type inside the Function Argument List?

---

```
static void printImuData(Print &printer, int16_t Time0,
        int16_t AcX, int16_t AcY, int16_t AcZ,
        int16_t GyX, int16_t GyY, int16_t GyZ)
{
    printer.print(Time0); printer.print(",");
    printer.print(AcX);   printer.print(",");
    [...]
}

[...]

printImuData(dataFile, Time0, AcX, AcY, AcZ, GyX, GyY, GyZ);
if (Serial_plus_SD)
    printImuData(Serial, Time0, AcX, AcY, AcZ, GyX, GyY, GyZ);

```

I though the answer was "because you can pass data to a function by-value or by-reference" in fact the first input in the argument list is the left value (memory address) of a Method, but i am very confused.

Function arguments are used to pass data to the function that it may need to perform its task.

I tried to answer to the following questions to understand the code.

**1. What task does this function perform?**

The function will print some data on a Serial Monitor or SD Card

**2. What data do i need to send to the function?**

I need to send one Method through the left value of a pointer and 7 intergers. I can't understand why a method.

**3. What data do I get back from it?**

Nothing because is a void, it will perform some task inside the function (print inside the object thas is pointed?) but nothing will return to the caller.

In the book basic example is a function that returns the value 0 or 1 if is a Leap Year.

The function argument is an int and returns an int.

```
void loop()
{
    if (Serial.available() > 0) {
        int bufferCount;
        int year;
        char myData[MAXCHARS + 1]; // Save room for null
        bufferCount = ReadLine(myData);
        year = atoi(myData); // Convert to int
        Serial.print("Year: ");
        Serial.print(year);
        Serial.print(" is ");
        if (IsLeapYear(year) == 0) {
            Serial.print("not ");
        }
        Serial.println("a leap year");
}
}
/*****
Purpose: Determine if a given year is a leap year
Parameters:
int yr The year to test
Return value:
int 1 if the year is a leap year, 0 otherwise
*****/
    int IsLeapYear(int yr)
    {
    if (yr % 4 == 0 && yr % 100 != 0 || yr % 400 == 0) {
        return 1; // It is a leap year
    } else {
        return 0; // not a leap year
    }
}
/*****
Purpose: Read data from serial port until a newline character is read ('\n')
Parameters:
char str[] character array that will be treated as a null-terminated string
Return value:
int the number of characters read for the string
CAUTION: This method will sit here forever if no input is read from the serial port
and no newline character is entered.
****/
int ReadLine(char str[])
    {
        char c;
        int index = 0;
        while (true) {
        if (Serial.available() > 0) {
        index = Serial.readBytesUntil('\n', str, MAXCHARS);
        str[index] = '\0'; // null termination character
        break;
        }
    }
    return index;
}

```

Like in my the last question, I have a civil engineer background and i am a self-taught, so is my first time with coding :)

**Thank you for your patience.**

# Answer
"There are no stupid questions, just stupid answers"

> Why there is a Method "Print" not a Data Type inside the Function Argument List?

There is no "Method" Print in the argument list. There is a reference (not a pointer which would be a * not a &) to an object called `printer` that is of type Print. The code you have provided doesn't define `Print` but its a could guess that it is probably something to do with printing. By supplying the `printer` argument you can print this data to anything that inherits from the Print base class, Serial is a good possibility, but you could write a class that derived from Print and wrote the data to an LED matrix, etc. I can tell its not a Method, because you are calling the print method of printer, so it has to be either a class or structure.

> The function will print some data on a Serial Monitor or SD Card

I can see why you thought that but you are being too specific, it prints to anything that derives from Print, `Serial` and `dataFile` derive from it, but they might not be the only things.

> I need to send one Method through the left value of a pointer and 7 integers. I can't understand why a method.

An example might help:

```
class CGPrinter : public Print
{
  // Some code....
  virtual void print (const char* input) {// do something}
}

void loop()
{
  CGPrinter cgp;
  printImuData (Serial, 1,2,3,4,5,6,7);
  printImuData (cgp, 1,2,3,4,5,6,7);
}

```

`Serial` is an object, a variable, a specific instance of type of class that can print data.

CGPrinter is my new super sexy printing class that will read the characters that you 'print'. To print the 7 integers to CG's printer class is exactly the same call as the one to write it to the Serial Monitor, because both classes derive from Print.

> 3. What data do I get back from it?

Yes, correct on both points.

Does it make more sense now? If not, just say and I'll try and clarify it.
> 2 votes

---
Tags: c++, c
---


# Question
Title: I have cooked 3 regulators applying 12 V to RAW pin. Am I doing something wrong or did I get a bad batch?
I'm trying to make a simple keypad lock that has a 12 V magnetic lock. I supplied 12 V to the RAW pin on the Pro Mini with plans to actuate the relay with the 5 V from VCC pin. The lock was grounded on the terminal strip that the 12 V came from, and then the positive 12 V was switched through the relay.

Everything was working well until I powered the board through the RAW pin with 12 V. When I did that all three failed the smoke test.

My question is, am I doing something incorrectly or did I happen to get a bad batch (all three of the boards came in the same shipment, I assume they came from the same lot)?

# Answer
The Pro Mini's 5V regulator (MIC5205) can supply a maximum of 150 mA, from which the Pro Mini uses about 20 mA, leaving around 130 mA for other applications.

Check the data sheet of the relay, to get the maximum current draw. For example, the RWH-SH-105D relay requires around 70 mA in the "on" position. While this is under the 130mA limit, you may be using other IOs or powering other modules.

To reduce the current draw, use a transistor to drive the relay like this:
> 1 votes

# Answer
A magnetic lock will be based on a solenoid, which will probably draw quite a high current from the 12 V rail. When that load is switched, **a voltage spike will appear into the 12V rail** due to the inductance of the supply wires. The longer the wires and the higher the current, the bigger the voltage spike.

simulate this circuit – Schematic created using CircuitLab

If the spike goes above 20V (and it can easily happen, believe me) then **it will exceed the maximum rating of the MIC5205 voltage regulator and fry it** unless you prevent that with some extra components. The voltage rating of the regulator input capacitor in the Pro Mini probably isn't up to the task of handling 20+ V spikes either and may be getting damaged too.

Note that **the Pro Mini is specified to work with input voltages only up to 12 V**, so you are operating it with no margin whatsoever! You should **consider reducing that voltage** in first place. You could use a DC/DC converter module to step down the 12V to a more suitable 7V and provide isolation from the spikes at the same time.

Apart from that, **consider using a transient voltage suppressor (TVS or transzorb diode) and/or a large decoupling capacitor (with an adequate voltage rating)** as close as possible to the input of the Pro Mini or the DC/DC converter (if you use one). You might want to try decoupling your magnetic lock with a properly selected capacitor as well.

---

## Bonus: thermal considerations

Thermal issues shouldn't be the main culprit here, but be aware that the tiny MIC5205 can get extremely hot and enter thermal shutdown mode when operated at 12 V input voltage.

The junction to ambient thermal resistance of the regulator is 220 C/W. Its maximum operating junction temperature is 125 C. At 25 C ambient temperature that means the maximum allowable temperature rise is 100 C and the maximum allowable power dissipation is 455 mW. Because the regulator is dropping 7V, the maximum allowable current will be only 65 mA (instead of the 150 mA max that the MIC5205 can source in more favorable conditions). The consumption of the Pro Mini is around 20 mA, so that leaves you with only 45 mA for your application. You should consider whether this is enough for your application or not (some 5V relays draw around 80 mA, which will greatly exceed this 45 mA calculated limit, when connected to the VCC pin of the Pro Mini).
> 0 votes

---
Tags: power, arduino-pro-mini, voltage
---


# Question
Title: Cannot obtain reading from meter (Modbus)
I have a system in which I am taking readings from a meter and processing it through an Arduino Nano. My code looks as follows:

```
#include <SoftwareSerial.h>

#define SerialControl 7
#define RS485Tx HIGH
#define RS485Rx LOW

SoftwareSerial RS485Serial(11, 12);
uint8_t window[8]; // Initialising window of 8 bytes

byte SendKWh[] = { 0x01, 0x03, 0x40, 0x34, 0x00, 0x02, 0x90, 0x05 };

// 0x01: Meter Address, 0x03: Read Function Code, 0x40: Register Address Variable (Start address high bit)
// 0x34: Register Address Variable (Start address low bit)
// 0x00: Register Quantity (High Bit), 0x02: Register Quantity (Low Bit)
// 0x90: CRC check code (CRC code Low bit)
// 0x05: CRC check code (CRC code High bit)

void dumpWin() {
  for (int i = 0; i < 8; i++) {
    Serial.print(window[i], HEX);
    Serial.print(" ");
  }
  Serial.println();
}

void ReadRx() {
  // Sliding Window Implementation for reading data
  if(RS485Serial.available()) {
    uint8_t b = RS485Serial.read();
    dumpWin();
    // Slide the contents of the array down
    for (uint8_t i = 0; i < 7; i++) {
      window[i] = window[i+1];
    }
    window[7] = b; // Next frame inserted at the top of previous
    if ((window[0] == 0x01) && (window[1] == 0x03) &&
      (window[2] == 0x40) && (window[3] == 0x34)) {
      // Doing something with window[4] and window[5] here
    }
  }
}

void setup() {
  Serial.begin(115200);
  pinMode(SerialControl, OUTPUT);
  RS485Serial.begin(9600);
}

void loop() {
  static uint32_t ts = millis();
  if (millis() - ts >= 2000) {
    ts = millis();
    digitalWrite(SerialControl, RS485Tx);
    RS485Serial.write(SendKWh, sizeof(SendKWh));
    RS485Serial.flush();
    digitalWrite(SerialControl, RS485Rx);
    RS485Serial.listen();
  }
  ReadRx();
}

```

The `ReadRx()` is behaving odd and `dumpWin()` is giving `0 0 0 0 0 0 0 0` output. I have been trying but I'm not able to figure out where am I going wrong. Your help is appreciated!

EDIT 2: I changed the code as suggested by @Majenko but still `window[]` O/P is `0` for all. I am not able to understand as to why it is not able to read the values from `RS485Serial`.

# Answer
You need to stop thinking quite so linearly. You are working with asynchronous systems, so your code has to be asynchronous too.

Something more like this:

```
#include <SoftwareSerial.h>

#define SerialControl 7

#define RS485Tx HIGH
#define RS485Rx LOW

SoftwareSerial RS485Serial(11, 12);

byte SendKWh[] = { 0x01, 0x03, 0x40, 0x34, 0x00, 0x02, 0x90, 0x05 };

// 0x01: Meter Address, 0x03: Read Function Code, 0x40: Register Address Variable (Start address high bit)
// 0x34: Register Address Variable (Start address low bit)
// 0x00: Register Quantity (High Bit), 0x02: Register Quantity (Low Bit)
// 0x90: CRC check code (CRC code Low bit)
// 0x05: CRC check code (CRC code High bit)

uint8_t window[8]; // Initialising window of 8 bytes

void dumpWin() {
  for (int i = 0; i < 8; i++) {
    Serial.print(window[i], HEX);
    Serial.print(" ");
  }
  Serial.println();
}

void ReadRx() {
  if(RS485Serial.available()) {
    uint8_t b = RS485Serial.read();
    dumpWin();
    // Slide the contents of the array down
    for (uint8_t i = 0; i < 7; i++) {
      window[i] = window[i+1];
    }

    window[7] = b; // Next frame inserted at the top of previous

    if ((window[0] == 0x01) && (window[1] == 0x03) &&
        (window[2] == 0x40) && (window[3] == 0x34)) {
          // Doing something with window[4] and window[5] here
    }
  }
}

void setup() {
  Serial.begin(115200);
  pinMode(SerialControl, OUTPUT);
  digitalWrite(SerialControl, RS485Rx);
  RS485Serial.begin(9600);

}

void loop() {
  static uint32_t ts = millis();

  if (millis() - ts >= 2000) {
      ts = millis();
      digitalWrite(SerialControl, RS485Tx);
      RS485Serial.write(SendKWh, sizeof(SendKWh));
      RS485Serial.flush();
      digitalWrite(SerialControl, RS485Rx);
      RS485Serial.listen();
  }

  ReadRx();
}

```

Notice how I use `millis()` to send the command every 2 seconds asynchronously (i.e., without `delay()`). The RS485 is kept in READ mode *except for the brief moment while you send*. Also note the use of `flush()` to wait until the last symbol has been transmitted by the UART (software in this case) interface. It's important, otherwise you may cut off the transmission part way through (I don't think it's such a problem with SoftwareSerial, but with a hardware UART missing it out would be fatal).

The reading just reads one character and returns to the loop. Each iteration through the loop will (if a character is available) read just one character. Only when all 8 have been received and the contents of the window match up can you process anything (which you would put in place of the comment).

This method also leaves you free to implement other things in `loop()`, as long as they don't use `delay()` as well.
> 1 votes

---
Tags: programming, arduino-nano, c, sketch, modbus
---


# Question
Title: It is possible to carry a pic c code for arduino
Code C for **PIC16F887**, I want to be able to try this code in **ATMEGA328**, but I do not know how, I do not know the outputs of the pic, that is, none of the pic I know.

*Thank you for helping me. Grateful.*

```
/*
Universidad del Azuay
Microcontroladores
Proyecto Piano
Autores: Juan Pablo León, Santiago Vazques
Tutor: Ing. Kenneth Samuel Palacios Baus
Fecha: 2 de enero de 2015
*/

//Declaración de Funciones
void ndo(); //Nota Do
void sdo(); //Nota Do Sostenido
void nre(); //Nota Re
void sre(); //Nota Re Sostenido
void nmi(); //Nota Mi
void nfa(); //Nota Fa
void sfa(); //Nota Fa Sostenido
void nsol(); //Nota Sol
void ssol(); //Nota Sol Sostenido
void nla();  //Nota La
void sla(); //Nota La Sostenido
void nsi(); //Nota Si
void ndo2(); //Nota Do

//Programa Principal
void main (){
osccon=0x77; //Ocilador de 8bits interno del PIC16f887

TRISC=0XFF; //Puerto C habilitamos como entrada  para las notas normales
PORTC=0;;

TRISB=0XFF; //Puerto B habilitamos como entrada para los sostenidos
PORTB=0;

TRISD=0X00; //Puerto D habilitamos como salida para el sonido del parlante
PORTD=0;

ANSELH = 0x00;
ANSEL=0x00;      // Bits AN6:AN0 como E/S digital.

    while(1){

        PORTB=0xFF;  // 255   11111111
        switch(PORTB)
        {
               case  0b00000001: sdo();  break;  //#Do
               case  0b00000010: sre();  break;  //#Re
               case  0b00000100: sfa();  break;  //#Fa
               case  0b00001000: ssol(); break;  //#Sol
               case  0b00010000: sla();  break;  //#La
        }

        PORTC=0xFF;  // 255   11111111
        switch(PORTC)
        {
               case  0b00000001: ndo();  break;  //Do
               case  0b00000010: nre();  break;  //Re
               case  0b00000100: nmi();  break;  //Mi
               case  0b00001000: nfa();  break;  //Fa
               case  0b00010000: nsol(); break;  //Sol
               case  0b00100000: nla();  break;  //La
               case  0b01000000: nsi();  break;  //Si
               case  0b10000000: ndo2(); break;  //Do
        }
    }

}

void ndo(){      //Do
        PORTD=1;
        delay_us (1911);
        PORTD=0;
        delay_us (1911);
}

void sdo(){      //#Do
        PORTD=1;
        delay_us (1804);
        PORTD=0;
        delay_us (1804);
}

void nre(){     //Re
        PORTD=1;
        delay_us (1702);
        PORTD=0;
        delay_us (1702);
}

void sre(){     //#Re
        PORTD=1;
        delay_us (1607);
        PORTD=0;
        delay_us (1607);
}

void nmi(){     //Mi
        PORTD=1;
        delay_us (1517);
        PORTD=0;
        delay_us (1517);
}

void nfa(){     //Fa
        PORTD=1;
        delay_us (1432);
        PORTD=0;
        delay_us (1432);
}

void sfa(){     //#Fa
        PORTD=1;
        delay_us (1351);
        PORTD=0;
        delay_us (1351);
}

void nsol(){    //Sol
        PORTD=1;
        delay_us (1276);
        PORTD=0;
        delay_us (1276);
}

void ssol(){    //#Sol
        PORTD=1;
        delay_us (1203);
        PORTD=0;
        delay_us (1203);
}
void nla(){     //La
        PORTD=1;
        delay_us (1136);
        PORTD=0;
        delay_us (1136);
}

void sla(){    //#La
        PORTD=1;
        delay_us (1121);
        PORTD=0;
        delay_us (1121);
}

void nsi(){    //Si
        PORTD=1;
        delay_us (1012);
        PORTD=0;
        delay_us (1012);
}

void ndo2(){   //Do
        PORTD=1;
        delay_us (955);
        PORTD=0;
        delay_us (955);
}

```

Code file taken from this video: https://www.youtube.com/watch?v=2jVZnKjCltw

# Answer
There are two things you need to learn:

1. What the instructions in the PIC program mean, and
2. What the equivalent instructions (or functions for abstracted concepts) are in the Arduino API.

For instance, it looks like you may be making sounds of specific pitches. For that you would replace much of your code with the `tone()` function.

Reading IO pins would be done with `digitalRead()`, and `pinMode()` to set them to INPUT mode.

Basic C constructs like `switch`, and `if() { } else { }` etc are the same, but given the abstractions the Arduino API gives you it's probable you'd be using them in different ways anyway.

So in a nutshell: learn what your program is doing, then write the equivalent program for the Arduino.
> 1 votes

# Answer
No, you can not run Microchip PIC16F887 on an Atmel ATMEGA328 directly. Any code that does useful work likely interfaces with the "outside world" through the processor's inputs and outputs (ADC, GPIO, ect). It is very unlikely any two processor designs approach interfacing to the outside world in the same way.

The process of recoding software / firmware to run on different processors is called porting. It is a time consuming and costly process which is repeated over and over again. Porting is most often done because people or companies want to use the same software / firmware despite changing hardware due to speed increases, size reductions or cost reductions.
> 2 votes

---
Tags: atmega328
---


# Question
Title: I want to declare an array with variable size and also I want to ask from the user to enter it?
I'm using C++ language. double coordinates \[length\]\[5\];

# Answer
You'll have to dynamically allocate it.

```
int length;
double **coordinates;
cin >> length;
coordinates = new double*[length];
for (int i = 0; i < length; i ++ {
    coordinates[i] = new double[5];
}

```
> 0 votes

---
Tags: c++
---


# Question
Title: Can't use two SPI devices at the same time
I can use the MFRC522 using the following code:

```
#include <SPI.h>
#include <MFRC522.h>

MFRC522 mfrc522(10, 9);

void setup() {
    SPI.begin();
    mfrc522.PCD_Init();
}

void loop() {
    if (  mfrc522.PICC_IsNewCardPresent() && mfrc522.PICC_ReadCardSerial() ) {
         // Do stuff
    }
}

```

And it works great. I can also use the dot-matrix (8x8) using the following code:

```
#include "LedControl.h"

LedControl lc = LedControl(12,11,8,1);

void setup() {
    lc.shutdown(0,false);
    lc.setIntensity(0,3);
    lc.clearDisplay(0);

    lc.setLed(0,2,5,true);
    lc.setLed(0,5,5,true);

    lc.setLed(0,2,2,true);
    lc.setLed(0,3,1,true);
    lc.setLed(0,4,1,true);
    lc.setLed(0,5,2,true);
}

void loop() {
}

```

And it works just fine as well. However, when I try to use both of them using the following code:

```
#include <SPI.h>
#include <MFRC522.h>
#include "LedControl.h"

LedControl lc = LedControl(12,11,8,1);
MFRC522 mfrc522(10, 9);

void setup() {
    SPI.begin();
    mfrc522.PCD_Init();

    lc.shutdown(0,false);
    lc.setIntensity(0,3);
    lc.clearDisplay(0);

    lc.setLed(0,2,5,true);
    lc.setLed(0,5,5,true);

    lc.setLed(0,2,2,true);
    lc.setLed(0,3,1,true);
    lc.setLed(0,4,1,true);
    lc.setLed(0,5,2,true);
}

void loop() {
    if (  mfrc522.PICC_IsNewCardPresent() && mfrc522.PICC_ReadCardSerial() ) {
         // Do stuff
    }
}

```

In that case only one of them works (the MFRC522). I know that since they are connected in SPI mode they need to have different SS pins, so I used pin 10 for MFRC522 and pin 8 for dot-matrix. So, what's wrong? Why dot-matrix doesn't work at the same code with MFRC522??

# Answer
> 0 votes
The `LedControl` doesn't use `SPI` library but it's using `shiftOut` internally. So you can't use them both at the same pins as the `SPI` interface takes over them.

Basically `SPI.begin()` takes over the control on its pins and that means when you use `digitalWrite` or `pinMode` on those pins, it'll be ignored (at least on some of them).

If you add `SPI.begin()` into the second example (`LedControl` one) it'll stop working. However you can change pins for `LedControl` to other (free) pins and it should be working again.

And also there are mixed signals between both devices:

```
HW SPI wiring:
13  CLK    output
12  MISO   input
11  MOSI   output
9   SS     output

and LedControl wiring is:
12  MOSI   output (not really)
11  CLK    output

```

Something from the datasheet about alternate pin functions:

> * **SCK/PCINT5 – Port B, Bit 5**
> SCK: Master Clock output, Slave Clock input pin for SPI channel. When the SPI is enabled as a Slave, this pin is configured as an input regardless of the setting of DDB5. When the SPI is enabled as a Master, the data direction of this pin is controlled by DDB5. When the pin is forced by the SPI to be an input, the pull-up can still be controlled by the PORTB5 bit.
> PCINT5: Pin Change Interrupt source 5. The PB5 pin can serve as an external interrupt source.
> * **MISO/PCINT4 – Port B, Bit 4**
> MISO: Master Data input, Slave Data output pin for SPI channel. When the SPI is enabled as a Master, this pin is configured as an input regardless of the setting of DDB4. When the SPI is enabled as a Slave, the data direction of this pin is controlled by DDB4. When the pin is forced by the SPI to be an input, the pull-up can still be controlled by the PORTB4 bit.
> PCINT4: Pin Change Interrupt source 4. The PB4 pin can serve as an external interrupt source.
> * **MOSI/OC2/PCINT3 – Port B, Bit 3**
> MOSI: SPI Master Data output, Slave Data input for SPI channel. When the SPI is enabled as a Slave, this pin is configured as an input regardless of the setting of DDB3. When the SPI is enabled as a Master, the data direction of this pin is controlled by DDB3. When the pin is forced by the SPI to be an input, the pull-up can still be controlled by the PORTB3 bit.
> OC2, Output Compare Match Output: The PB3 pin can serve as an external output for the Timer/Counter2 Compare Match. The PB3 pin has to be configured as an output (DDB3 set (one)) to serve this function. The OC2 pin is also the output pin for the PWM mode timer function.
> PCINT3: Pin Change Interrupt source 3. The PB3 pin can serve as an external interrupt source.
> * **SS/OC1B/PCINT2 – Port B, Bit 2**
> SS: Slave Select input. When the SPI is enabled as a Slave, this pin is configured as an input regardless of the setting of DDB2. As a Slave, the SPI is activated when this pin is driven low. When the SPI is enabled as a Master, the data direction of this pin is controlled by DDB2. When the pin is forced by the SPI to be an input, the pull-up can still be controlled by the PORTB2 bit.
> OC1B, Output Compare Match output: The PB2 pin can serve as an external output for the Timer/Counter1 Compare Match B. The PB2 pin has to be configured as an output (DDB2 set (one)) to serve this function. The OC1B pin is also the output pin for the PWM mode timer function.
> PCINT2: Pin Change Interrupt source 2. The PB2 pin can serve as an external interrupt source.

---
Tags: arduino-uno
---


# Question
Title: Reading and processing a PWM on AtTiny45
I have this question and I can't find answers!

I wanted to use an AtTiny45V (due to low voltage requirements, it will run at 1.8 volts) to read a PWM from an Arduino, and then process this information.

Explained better:

let's say, I hook up one pin of the AtTiny to an Arduino pin (named `connection`), and in the IDE I write:

```
AnalogWrite(connection,X)

```

I want the AtTiny to write high on a port based on the X value.

Example:

X = 20 writes high on AtTiny PB5

X = 25 writes high on AtTiny PB5 and PB3

etc...

So, basically I want to read the duty cycle from the Arduino PWM and let the AtTiny do something based on duty cycle value.

Is this possible?

Thanks

# Answer
> 1 votes
You don't need to read the duty cycle, just the time that the PWM signal is high. First wait for the input pin to go high, then start a timer, wait for the signal to go low again, and finally read the timer value. If other tasks need to be performed concurrently then use pin change interrupt to detect the high and low transitions.

If the ATtiny is running Arduino software then the solution is even easier - just use the pulseIn() function.

This technique works for all PWM values *except* 0 and 255. With these values the pin stays low or high permanently, so there are no transitions to time. The easiest way around this is to simply avoid transmitting 0 or 255.

Alternatively you could pass the PWM signal through an RC filter to produce a 'DC' voltage, then read it with the ADC. However this will slow the response time down, and the signal will produce intermediate values as it goes from one voltage to another. To get good resolution the RC filter would need to have a long time constant, and you might have to average several readings to get a stable value.

# Answer
> 0 votes
If I understood correctly you want to drive a digital output on the AtTiny45V based on the PWM value from your Arduino, right?

I would suggest to use a simple low-pass RC filter to extract the mean value from the PWM and read as an analog voltage in the AtTiny45V. As the frequency of your PWM is known, you can easily design your filter to extract the mean value of your signal. Then, based on your PWM mean value, you can define which pin will be set.

---
Tags: pwm, attiny
---