message:
Code test the duration press of the button

I wrote code that tracks the duration of a button click. It has bounce protection and frequent clicks. (Freeze)

My code:

    bool freeze_time, btn_read, debounce;
    unsigned int freeze_timer, btn_timer;

    #define BTN 6

    void setup() {
      Serial.begin(9600);
      pinMode(BTN, INPUT);
    }

    void loop() {
      /* Freeze Timer Protection */
      if(freeze_time) {
        if((millis() - freeze_timer) >= 2500) {
          freeze_time = false;
          btn_read = false;
        }
      }
      /* Read Button State */
      if(digitalRead(BTN) == HIGH) {
        if(!btn_read) {
          btn_timer = millis();
          debounce = true;
          btn_read = true;
        }
      }
      /* BTN Read Process */
      if(btn_read) {
        /* Debounce Protection */
        if(debounce) {
          if((millis() - btn_timer) >= 1000) {
            if(digitalRead(BTN) == HIGH) {
              Serial.println("Debounce ok.");
              btn_timer = millis();
              debounce = false;
            } else {
              Serial.println("Debounce fail.");
              freeze_time = true;
              debounce = false;
            }
          }
        }
        /* BTN Read Process */
        else if(!freeze_time) {
          if((millis() - btn_timer) >= 1500) {
            if(digitalRead(BTN) == HIGH) {
              Serial.println("Ok. Button Pressed > 1500ms");
              freeze_timer = millis();
              freeze_time = true;
            } else {
              Serial.println("Ok. Button Pressed < 1500ms");
              freeze_timer = millis();
              freeze_time = true;
            }
          }
        }
      }
    }

 I checked it on real Arduino UNO and Tinkercad simulator. Initially, everything works well, but if I press the button indefinitely, the system will fail (every time you press the serial port, messages appear as if all flags were lost and the timers did not work. I filmed the behavior:

1) Initially: http://recordit.co/lVlR1z1CUq
2) System is broken: http://recordit.co/lhvzM100DI

What could be the problem and how to make it fault tolerant?

body:
# Why did the timers stop working?

The main issue seems to be that `freeze_timer` and `btn_timer` are of type `unsigned int`, while `millis`, as stated in its [documentation](https://www.arduino.cc/reference/en/language/functions/time/millis/), returns an `unsigned long`.

As you may know, `unsigned int` is normally be able to hold a much smaller range of values than `unsigned long`. In the case of whatever compiler Tinkercad uses for the Arduino Uno, I checked and `unsigned int` can hold values from 0 to 65535, while `unsigned long` can hold values from 0 to 4294967295. Whenever you save an `unsigned long` into an `unsigned int`, it will be reduced modulo 65536.

This means that once you pass 65.536 seconds checks such as the `(millis() - freeze_timer) >= 2500` will always be true (at least until `millis` wraps back around after 4294967.296 seconds - around 50 days).

If you would like to learn a bit more about integer conversions, I think [this Stack Overflow question](https://stackoverflow.com/questions/27889213/c-integer-downcast) covers it.

The simplest solution is, of course, to declare `freeze_timer` and `btn_timer` to be of the appropriate type, `unsigned long`.

# Use simpler code

All of the above being said, like [Gerben](https://arduino.stackexchange.com/questions/63008/code-test-the-duration-press-of-the-button#comment135530_63008) said, the code seems overly complex.

There also seem to be other issues. For instance, I would expect the debounce behavior should not ignore presses that last less than 1 second. Like Gerben said, 10 ms should be enough to discard any bounces.

Furthermore, I think it would be more appropriate to not even discard presses that last less than 10 ms. I would say the debouncer should trigger "press" regardless of whether the press lasted less than 10 ms. It's role should just be to ignore *multiple* presses within that 10 ms window (although to be fair, ignoring short presses is not a terribly big issue).

Although one could make some guesses, to really help you with this, we would need a description of your intended behavior. What is the purpose of freezing? Is it intended to allow multiple presses to be triggered when you never release the button (or maybe you should wait until release before triggering one again)?


sender: user

message:
How to use Serial.setTimeout()

I am just playing with the UART interface of my board to learn about how it works. Since I have only one board, I send data out just to receive them by my own board, which is working so far.

Now I wanted to find out what Serial.setTimeout() is for. As per description on the Arduino homepage, it sets the maximum time for to wait for data. The description says, upon others Serial.find() will use it.

So I set Serial.setTimeout() to 100ms, and between sending and trying to receive data, I put a delay of 500ms. Therefore my expectation would be, Serial.find() will not detect a message, since there is more than 100ms no traffic on the bus. But I am still recieving data, it seems that the Serial.setTimeout() has no effect.

What is wrong in my understanding/usage of Serial.setTimeout()?

Here is my example sketch:

    #include <M5Stack.h> // needed for my board M5Stack

    HardwareSerial Serial2(2); // R2: Recieve Serial2, 17: Transmit Serial2  --> connnect pin R2 and 17

    unsigned char buf_recive[1];
    unsigned char buf_transmit[2] = {0x42, 0x00};

    void setup()
    {
      M5.begin();
      Serial.begin(9600);    // setting baud rate for COM3
      Serial2.begin(9600);   // setting baud rate for M5Stack2M5Stack communication
      Serial2.setTimeout(100);    //set the Timeout to 100ms
    }

    void loop()
    {
      delay(500);
      // send buf_transmit
      Serial2.write(buf_transmit, 2);
      delay(500);
      // detect first byte of recieve message
      if (Serial2.find(0x42))
      { //start to read when detect 0x42
        Serial2.readBytes(buf_recive, 1);
        Serial.println(buf_recive[0]);
      }
      buf_transmit[1] = buf_transmit[1] + 0x01; // just to see that something's going on
    }

And here some prove, that I am still receiving data:

[![enter image description here][1]][1]

  [1]: https://i.stack.imgur.com/sqGsK.png

sender: assistant

body:
The bytes are received to rx buffer with interrupt in the core. The find() function finds them there after the 500 millis delay. Timeout is to wait for the next byte if the rx buffer is empty.

The timeout is good if you know that the other side sends a collection of characters or bytes. Like for example a line sent from Serial Monitor or a Http request on networking client. The transmition has small gaps between bytes, but you want to receive it at once. So a function waiting a little for the next byte is useful.

Serial, networking Client classes and other Arduino stream classes inherit reading functions from the Stream class. This class has all the read and parse functions. There are 3 non blocking functions `available`, `read` and `peek`. All other read and parse functions use the timeout and wait for the next byte if the rx buffer is empty.

try this sketch with Serial Monitor

    void setup() {
      Serial.begin(115200);
      Serial.setTimeout(10000);
    }

    void loop() {
      if (Serial.available()) {
        String s = Serial.readString();
        s.trim();
        Serial.println(s);
      }
    }

send a line from Serial Monitor. a couple of characters. then send fast another line and then wait longer then 10 secs and send one more.


message:
How to communicate between a webcam and an Arduino UNO and get the live feed on mobile using ESP8266?

I am working on a project of making a Smart Robot Car using Arduino UNO, L298N Motor Driver Module, ESP8266 Esp-01 WiFi module and RemoteXY app for controlling via smartphone over WiFi.

My question is: ***If I want to get the live feed of the view that my robot is seeing, using a webcam (say Logitech HD Webcam C270) using a USB to serial converter module or whatsoever, how can I make it possible?***
*Please let me know if there is any special shield or any processing board needed.* ***Help with coding and the conversion of Video data into the transmittable Data for Arduino and help in making that kind of data which can be read by the Device (e.g. Smartphone) is also needed and will be appreciable.***

It may be mentioned here that I am a beginner and I am currently learning through YouTube and Blog Tutorials. I am totally dependent on StackExchange like forums for the help in my projects either whenever I am making a mistake or when I want to try and learn something new or both. Please Help me while keeping these things in your mind also.

Please *suggest me some good books* on this branch of the subject that could make me able to do these kinds of things on my own.

Thank You So Much in advance!

(P.S.: If you feel this question should be downvoted then, please firstly let me know in the comments section why do you feel like this before downvoting, I may delete my question earlier, cause I am concerned about my reputation here.)

body:
The Uno is a very limited platform, perhaps surprisingly, given its wide range of abilities and built-in hardware features. The two most glaring limitations for you application are its 16MHz clock speed (relative to modern desktop processors) and thus its bandwidth, and it's non-expandable 2KBytes of RAM.

Image processing would be right out the window, and even merely transmitting a raw image would be pushing its bandwidth limits, for any reasonable frame-size with even a very modest frame-rate.

Example: For a 100x100 8-bit frame at 15 frames/sec, a 16MHz processor (16M instructions per sec) would have (16000000 / (100x100x15)) = ~107 clocks (instructions) available to process each byte. You'd need some of those to either poll for next-byte-ready or to enter and exit an Interrupt Service Routine to process the byte. You're probably up to around 20 clocks (at a wild guess), to do nothing more than a bit of wire can do! Maybe you could do some trivial manipulation of each byte on the way through (say, brightness manipulation) with a few more clocks and you're already using a significant fraction of the processor just for that. And there isn't enough memory to be able to process a region of the image. And if you could, you run out of processor time before you could do much .... The problem just cascades as you approach the limits of speed and memory-space.


body:
As rightly pointed out by others and @JRobert, its very difficult or nearly impossible to live stream a video/audio through Arduino Uno which uses Atmega328 micro-controller which is mostly used for simple embedded processing such as sensor reading, serial tr/rx, i2c like operations.

But there are some workarounds which can make it possible by using some SPI camera and some Bluetooth shield or ESP8266 together.

Take a look at this project which can be helpful to you.

[https://github.com/ArduCAM/Arduino][1]

But remember, don't expect a very good quality or higher frame-rate video stream. Also it might only send video, i.e. picture frames and not audio.

Second solutions is:

If you just want your robot to get equipped with a camera which need to be live streamed back to your android/ios phone with good quality AV then the best way to do this is by a standard method used by most RC toys, UAV or robots.

What you need is:

1) 5.8Ghz AV transmitter

 - A Mini FPV Camera NTSC/PAL with inbuilt transmitter or
 - FPV camera and a 5.8G 600mW Wireless Audio/Video Transmitter for FPV

with above options you can get a possible range of 1 Km to 5Km or more.

2) second thing you need is receiver section

 - OTG 5.8G 150CH Full Channel FPV Receiver For Android and iOS is best for this.
This above module will help you to receive AV from FPV camera/module to your android.

I'll not give you direct link to the products as that wont be a good idea here on SE. instead you can search for them on google and choose as per your requirement. most of these modules will be less than 2000 INR or 30$

  [1]: https://github.com/ArduCAM/Arduino


message:
Operating AD5780 EVAL Board Via MicroController

OK, so thanks in advance because I am new here. I am reading the AD57XX drivers here  https://wiki.analog.com/resources/tools-software/uc-drivers/renesas/ad5780 and am struggling to understand how to get the device working and understanding it properly.

I am using code here https://github.com/maxgerhardt/arduino-ad57xx-driver/blob/master/src/main.cpp in order to test the DAC. I have several questions about the drivers and operation in general. I will itemize them if that is ok

 1. Where in the drivers am I performing Slave Select and where am I determining Clock Speed? I have looked through the C in the drivers library, and it seems that each command, whether reading or writing selects the Slave/Master each time? I see no reference to which pins on my microcontroller it is reference though so I do not know if any of this is right.
 2.
 Why do I need to be reading in the Control Register or anything from the DAC at all? Why does this matter? All I want is to output a voltage
 3.
How do I perform the right conversion to a voltage that I want? The command " AD57XX_SetDacValue() " takes a long, but I do not understand how that relates to a float value of voltage. Say I want 2.35 Volts, or a Sine Function from -2 to 2 Volts, how do I do this conversion?
 4. I don't know how to debug the system in general. When I run the example code, which is supposed to output a triangle wave function, I get a sin function, which seems to just be noise.

body:
> Where in the drivers am I performing Slave Select and where am I determining Clock Speed? I have looked through the C in the drivers library, and it seems that each command, whether reading or writing selects the Slave/Master each time? I see no reference to which pins on my microcontroller it is reference though so I do not know if any of this is right.

The slave select is controlled within the [`SPI_Write()`](https://github.com/maxgerhardt/arduino-ad57xx-driver/blob/master/lib/ad57xx_generic_driver/src/Communication.cpp#L194) function.  It uses the [`PinMgt_PinWrite()`](https://github.com/maxgerhardt/arduino-ad57xx-driver/blob/master/lib/ad57xx_generic_driver/src/PinMgtLayer.cpp#L29) function to do the slave select control, which in turn selects a pin from the [`pinMapping[]`](https://github.com/maxgerhardt/arduino-ad57xx-driver/blob/master/lib/ad57xx_generic_driver/src/PinMgtLayer.cpp#L8) lookup table.

The clock speed is set in [`AD5780_Init()`](https://github.com/maxgerhardt/arduino-ad57xx-driver/blob/master/lib/ad57xx_generic_driver/src/AD5780.c#L62).

> Why do I need to be reading in the Control Register or anything from the DAC at all? Why does this matter? All I want is to output a voltage

You don't. The code is just for demonstration purposes. It shows you how you could query those registers. If you don't need to, then don't.

> How do I perform the right conversion to a voltage that I want? The command " AD57XX_SetDacValue() " takes a long, but I do not understand how that relates to a float value of voltage. Say I want 2.35 Volts, or a Sine Function from -2 to 2 Volts, how do I do this conversion?

That value is the raw value to set the DAC to. You refer to the [DAC datasheet](https://www.analog.com/media/en/technical-documentation/data-sheets/ad5780.pdf) to know what that value equates to.  In this case the range is from \$V_{REFN}\$ to \$V_{REFP}\$.  Divide that range by 218 and you have the voltage per bit.

> I don't know how to debug the system in general. When I run the example code, which is supposed to output a triangle wave function, I get a sin function, which seems to just be noise.

You need some debugging tools. Things like a logic analyser to be able to acually see what the IO pins of your MCU are doing.  An oscilloscope can be used to see if a signal is present, but to see all the SPI signals together you really want a logic analyser.


message:
Issues with CO2 sensor SEN0159

I followed the sketch example for the SEN0159 CO2 sensor as precised in the data sheet  https://www.dfrobot.com/wiki/index.php/CO2_Sensor_SKU:SEN0159. It's powered by a 9V/2A DC power supply more than 48h and it still reads 2.81V on the analog ouput pin even if i exhaust on the sensor during long time, nothing happen, giving - 1ppm CO2 value.

Can you explain me why i cannot observe CO2 variations ? Is there troubles with the board ?

Thanks!

body: Yes, i made a mistake... The arduino board should be powered by a 7-12V power supply to support high current from 5V pinout in order to power the sensor card... I'm very lucky, my sensor is not broken. I have powered it with 5V and it works fine!!! Thanks


message:
LCD displaying weird text

I am doing a project that requires input from a keypad to be displayed on the LCD display.

`lcd.print()` displays in proper form, but when the I press characters on the keypad, they are overwritten as weird symbols.

Any help would be appreciated.

Here's the code:

    void setup()
    {
      Serial.begin(9600);
      Serial.println("LCD test with PWM contrast adjustment");
      pinMode(13,OUTPUT);
      analogWrite(6,Contrast);

      lcd.begin(16,2);

      pinMode(buzzer, OUTPUT);
      lcd.print(" Electronic ");
      Serial.print(" Electronic ");
      lcd.setCursor(0,1);
      lcd.print(" Keypad Lock ");
      Serial.print(" Keypad Lock ");
      delay(2000);
      lcd.clear();
      lcd.print("Enter Ur Passkey:");
      Serial.println("Enter Ur Passkey:");
      lcd.setCursor(1,0);
      for(int j=0;j<4;j++)
        EEPROM.write(j, j+49);
      for(int j=0;j<4;j++)
        pass[j]=EEPROM.read(j);
    }

body:
I think you should use 48 instead of 49.

48 is the ASCII symbol of 0. If you add a number from 0-9 to it, than you get the ASCII symbols of '0' to '9'.

(and a small sidenote: `Enter Ur Passkey:` is more than 16 characters; also it is more 'professional not to make slang texts to try to fit it, why not using `Enter Passkey:` instead?


body:
stick to one type of variable, to prevent mix-up

So if you stick to a byte (uint8_t) type for keypad:

```
uint8_t keys[4][3] = {
  {1,2,3},
  {4,5,6},
  {7,8,9},
  {0xF,0xA,0xB}     // F-* B-#
}

```
 then you can save it to your EEPROM as a byte and read it as a byte.it will prevent mix-up.
your code which you are not displaying (everybody here can write one of those faster then to download it from here)already translate numbers to numbers and then you are growing them to symbols with higher value


message:
I'm getting NaN for readings on my DHT22 sensor when using 3v3 pin, but not 5v pin

I have a DHT22 temperature sensor and DS1302 RTC module connected to the 3v3 pins on an Arduino Nano. Both the sensor and the RTC module are rated to work on either 3.3V or 5V, but the recommendation is 3.3V.  For some reason though, when I connect the sensor and RTC to 3.3V power on the Nano, the sensor just returns NaN even though the RTC module works.  When I change the sensor to use 5V and leave the RTC on 3.3V, I get a proper temp and humidity value on the DHT22.  What is wrong?

Turns out the solder joint for the 3v3 pin on the nano was not properly done. I figured this out after I swapped out the nano for another nano and it worked. Resoldering the 3v3 pin fixed the problem.

body: Sometimes the problem is simply that you didn't properly solder the headers onto the Arduino. You should check to make sure that your solder joints are all good.


message:
Not sure which Arduino to pick

Is the Arduino Uno the best one to purchase for a complete beginner?

I eventually want to get into building Nodebots since I already have experience writing Nodejs web-based applications.

Or should I go directly to purchasing an Arduino Starter Kit? SparkFun Inventors Kit? Adafruit ARDX Experimentation Kit for Arduino? Seeed Studio ARDX starter kit? or Freetronics Experimenter’s Kit for Arduino?

I don't know the difference between these and based off what I have shared about my situation so far, which one should I start with to A. Learn the Basics, B. Evolve into developing Nodebots.

body:
NodeBots does external control of Arduino with Java Script. The controlling computer is a PC or a SOC like Raspberry PI. (Eventually Raspberry can run NodeBots without Arduino.)

For NodeBots, Arduino board runs a firmware called Firmata which executes the commands sent by the Johnny-Five Java Script firmata master library.

I would recommend you to learn C++ and Arduino functions and libraries and code the Arduino directly without Firmata and a controlling computer.


message:
Why LCD 16x2 cannot display "water leaking" when rain sensor detects water?

#include <SoftwareSerial.h>
    #include <LiquidCrystal.h>
    LiquidCrystal lcd(12, 11, 5, 4, 3, 2);
    SoftwareSerial mySerial(0, 1);

    int gas_sensor = A5;
    int water_sensor = 8;
    int buzzer = 9;
    int fan = 13;
    int sms_count = 0;

    void setup() {
      pinMode(gas_sensor, INPUT);
      pinMode(water_sensor, INPUT);
      pinMode(buzzer, OUTPUT);
      pinMode(fan, OUTPUT);
      mySerial.begin(9600);
      Serial.begin(9600);
      lcd.begin(16, 2);
      delay(500);
    }

    void loop() {
      if (digitalRead(water_sensor) == LOW && analogRead(gas_sensor)) {
        CheckWater_and_Gas();
      }
      else if (digitalRead(water_sensor) == LOW) {
        CheckWater();
      }
      else if (analogRead(gas_sensor)) {
        CheckGas();
      }
      else {
      }
    }

    void CheckWater_and_Gas() {
      int sensorValue = analogRead(gas_sensor);
      Serial.println(sensorValue);
      delay(1000);
      if ( digitalRead(water_sensor) == LOW && sensorValue > 150 ) {
        digitalWrite(buzzer, HIGH);
        digitalWrite(fan, HIGH);
        lcd.clear();
        lcd.setCursor(0, 0);
        lcd.print(" Water and ");
        lcd.setCursor(0, 1);
        lcd.print(" Gas Leaking ! ");
        SetAlertWater_and_Gas();
      }
      else {
        digitalWrite(buzzer, LOW);
        digitalWrite(fan, LOW);
        lcd.clear();
      }
    }

    void CheckWater() {
      if ( digitalRead(water_sensor) == LOW ) {
        digitalWrite(buzzer, HIGH);
        lcd.clear();
        lcd.setCursor(0, 1);
        lcd.print(" Water Leaking ! ");
        SetAlertWater();
      }
      else {
        digitalWrite(buzzer, LOW);
        lcd.clear();
      }
    }

    void CheckGas() {
      int sensorValue = analogRead(gas_sensor);
      Serial.println(sensorValue);
      delay(1000);
      if (sensorValue > 150) {
        digitalWrite(buzzer, HIGH);
        digitalWrite(fan, HIGH);
        lcd.clear();
        lcd.setCursor(0, 1);
        lcd.print("Gas Leaking !");
        SetAlertGas();
      }
      else {
        digitalWrite(buzzer, LOW);
        digitalWrite(fan, LOW);
        lcd.clear();
      }
    }

body:
You schould start searching the root cause for your error: code, display, sensor, … step by step.

Check if your display is working by 1.) reducing your loop() to

    void loop() {
        CheckWater();
    }

and 2.) change

    void CheckWater() {
      if ( digitalRead(water_sensor) == LOW ) {
        digitalWrite(buzzer, HIGH);
        ...

to

    void CheckWater() {
      if ( true ) {
        digitalWrite(buzzer, HIGH);
       ...

This allows you to check if your LCD is working properly. If not, start looking for the fault in wiring or maybe you are using a different LCD which has to be setup in a different mode as the sketch from online.

If this works, search for the rootcause in the sensor. Go back to the orignial code and put the input of the rain sensor to low. If your display shows: Water Leaking! something with your water sensor or it's Connection to your board seems to be wrong.


message:
7 LED Number Display

I need to write a string of number such as 1234567 on a 7 LED display. For example 1 will be lit up on display for 0.5 seconds, it will turn off then 2 will light up and so on. In the end I need to display "-" for 2 seconds. I also added the image of the given task.[![Given Task][1]][1]

  [1]: https://i.stack.imgur.com/BwQyI.jpg

The following is the code I wrote.
I would like to ask if it is the correct, and are there any flaws.

      const int LEDa=13;
      const int LEDb=12;
      const int LEDc=11;
      const int LEDd=10;
      const int LEDe=9;
      const int LEDf=8;
      const int LEDg=7;

      int i;
      int a;

      void setup() {

        pinMode(LEDa, OUTPUT);
        pinMode(LEDb, OUTPUT);
        pinMode(LEDc, OUTPUT);
        pinMode(LEDd, OUTPUT);
        pinMode(LEDe, OUTPUT);
        pinMode(LEDf, OUTPUT);
        pinMode(LEDg, OUTPUT);

      }

      void loop() {
        int array[7]= {1,8,0,5,1,0,0};
        for(i=0;i<8;i++){
          a= array[i];
          }
            switch(a){
              case 1:
              digitalWrite(LEDb,HIGH);
              digitalWrite(LEDc,HIGH);
              delay(500);
              digitalWrite(LEDb,LOW);
              digitalWrite(LEDc,LOW);
              break;
              case 2:
              digitalWrite(LEDa,HIGH);
              digitalWrite(LEDb,HIGH);
              digitalWrite(LEDg,HIGH);
              digitalWrite(LEDe,HIGH);
              digitalWrite(LEDd,HIGH);
              delay(500);
              digitalWrite(LEDa,LOW);
              digitalWrite(LEDb,LOW);
              digitalWrite(LEDg,LOW);
              digitalWrite(LEDe,LOW);
              digitalWrite(LEDd,LOW);
              break;
              case 3:
              digitalWrite(LEDa,HIGH);
              digitalWrite(LEDb,HIGH);
              digitalWrite(LEDc,HIGH);
              digitalWrite(LEDg,HIGH);
              digitalWrite(LEDd,HIGH);
              delay(500);
              digitalWrite(LEDa,LOW);
              digitalWrite(LEDb,LOW);
              digitalWrite(LEDc,LOW);
              digitalWrite(LEDg,LOW);
              digitalWrite(LEDd,LOW);
              break;
              case 4:
              digitalWrite(LEDf,HIGH);
              digitalWrite(LEDg,HIGH);
              digitalWrite(LEDb,HIGH);
              digitalWrite(LEDc,HIGH);
              delay(500);
              digitalWrite(LEDf,LOW);
              digitalWrite(LEDg,LOW);
              digitalWrite(LEDb,LOW);
              digitalWrite(LEDc,LOW);
              break;
              case 5:
              digitalWrite(LEDf,HIGH);
              digitalWrite(LEDg,HIGH);
              digitalWrite(LEDd,HIGH);
              digitalWrite(LEDc,HIGH);
              digitalWrite(LEDa,HIGH);
              delay(500);
              digitalWrite(LEDf,LOW);
              digitalWrite(LEDg,LOW);
              digitalWrite(LEDd,LOW);
              digitalWrite(LEDc,LOW);
              digitalWrite(LEDa,LOW);
              break;
              case 6:
              digitalWrite(LEDf,HIGH);
              digitalWrite(LEDg,HIGH);
              digitalWrite(LEDa,HIGH);
              digitalWrite(LEDc,HIGH);
              digitalWrite(LEDe,HIGH);
              digitalWrite(LEDd,HIGH);
              delay(500);
              digitalWrite(LEDf,LOW);
              digitalWrite(LEDg,LOW);
              digitalWrite(LEDa,LOW);
              digitalWrite(LEDc,LOW);
              digitalWrite(LEDe,LOW);
              digitalWrite(LEDd,LOW);
              break;
              case 7:
              digitalWrite(LEDa,HIGH);
              digitalWrite(LEDb,HIGH);
              digitalWrite(LEDc,HIGH);
              delay(500);
              digitalWrite(LEDa,LOW);
              digitalWrite(LEDb,LOW);
              digitalWrite(LEDc,LOW);
              break;
              case 8:
              digitalWrite(LEDa,HIGH);
              digitalWrite(LEDb,HIGH);
              digitalWrite(LEDc,HIGH);
              digitalWrite(LEDd,HIGH);
              digitalWrite(LEDe,HIGH);
              digitalWrite(LEDf,HIGH);
              digitalWrite(LEDg,HIGH);
              delay(500);
              digitalWrite(LEDa,LOW);
              digitalWrite(LEDb,LOW);
              digitalWrite(LEDc,LOW);
              digitalWrite(LEDd,LOW);
              digitalWrite(LEDe,LOW);
              digitalWrite(LEDf,LOW);
              digitalWrite(LEDg,LOW);
              break;
              case 9:
              digitalWrite(LEDa,HIGH);
              digitalWrite(LEDb,HIGH);
              digitalWrite(LEDc,HIGH);
              digitalWrite(LEDd,HIGH);
              digitalWrite(LEDf,HIGH);
              digitalWrite(LEDg,HIGH);
              delay(500);
              digitalWrite(LEDa,LOW);
              digitalWrite(LEDb,LOW);
              digitalWrite(LEDc,LOW);
              digitalWrite(LEDd,LOW);
              digitalWrite(LEDf,LOW);
              digitalWrite(LEDg,LOW);
              break;
              case 0:
              digitalWrite(LEDa,HIGH);
              digitalWrite(LEDb,HIGH);
              digitalWrite(LEDc,HIGH);
              digitalWrite(LEDd,HIGH);
              digitalWrite(LEDe,HIGH);
              delay(500);
              digitalWrite(LEDa,LOW);
              digitalWrite(LEDb,LOW);
              digitalWrite(LEDc,LOW);
              digitalWrite(LEDd,LOW);
              digitalWrite(LEDe,LOW);
              digitalWrite(LEDf,LOW);
              break;
              }
              if(i=8){
                digitalWrite(LEDg,HIGH);
                delay(2000);
                digitalWrite(LEDg,LOW);
                }
              }

body:
I see 3 errors:

1. You define the array to have 7 elements, but in the `for` loop, you count 8 elements, by using `i<8` (Array indizes start at 0, so 0 will be the first and 6 will be the last element). Currently you try to access an array element, that does not exist.

2. The `if` statement is also not useful here. In your current code you check for `i` being equal to 8, but it will never be 8 inside of the `for` loop, because you used the condition `i<8`. To display the last `-` after the number, you should put the code after the `for` loop.

3. In the same `if` statement you write `i=8`, but a single equality sign means assignment. The value 8 will be assigned to the variable `i` and this assignment is true everytime. If you want to test equality use `==` (double equality signs)

---

Tip: You can make your code smaller by defining functions for codes parts, that get repeated often (for example the code to turn off all LEDs).

Tip2: If you want the code to be very efficient, you can change the pins to use one single port. Then you can change all the pins of the port at once, by assigning a single byte to it. You can save these bytes in an array. This will make your code way shorter, but you also need a deeper understanding about port manipulations. You can choose, what you want to do.


body:
It looks like it is mostly correct, although that is a very long-winded way to set 7 segments to multiple values. I would be more inclined to set up an array of bytes where 7 bits of each byte contain ones/zeros to control the LEDs. Then you could skip the massive switch statement and simply loop through the array of bytes.

One mistake: `if(i=8)` should be `if (i == 8)`. (`=` is an assignment. You want the `==` comparison operator.) Your code won't work correctly until you fix that.


message:
How to stop motor after a desired time?

I am trying to stop a dc motor after a desired amount of time !! And the motor starts upon settling on a condition !! From that very moment i want my motor to just run for 5 seconds and stop!! Below is the pseudocode:

     #define max 150
     #define min -150
     #define pin1 3
     void setup()
        {
            Serial.begin(9600);
             mpu.initialise();
         }
       void loop()
         {
            x= some_accelerometer_values;
             If (x>250)
                {
                    analogWrite(pin1,255);
                    delay(5000);
                    exit(0);
                 }
          }
I tried using millis() but it starts time with execution of program and i can't get to implement it just before the motor starts running!

body:
Assuming you turn your motor on with `analogWrite(pin1, 255);` just write `analogWrite(pin1, 0);` after the `delay(5000);`.

And using `exit(0);` isn't as bad as people will most likely say. Using exit(0) is the same as `cli();` + `while(1)`. So it disables interrupts and stucks your code in a while loop till your reset the arduino.


message:
Basic Arduino Airplane Control

I have a task where I need to control the airplanes thrust and altitude direction(Up-Down). For the thrust I thought of using a DC Motor and a Servo for the other. Control of servo will be from the buttons and the thrust value will be given from the serial port. (This is not a project of a real vehicle, only thing I need to do is the code, rest is imaginary.)
[![enter image description here][1]][1]

  [1]: https://i.stack.imgur.com/ozbRt.jpg

I have wrote the following code. I would like to ask is there any flaws and how can I further improve it? Thanks in advance.
With my regards...

    #include <Servo.h>
      Servo servo1;
      int pos = 0;
      const int buttonSUP = 2;
      const int buttonSDOWN = 3;

      int buttonStateUP = 0;
      int buttonStateDOWN = 0;

      int motorPin = 4;

      void setup() {

      servo1.attach(9);
      pinMode( buttonSUP, INPUT);
      pinMode( buttonSDOWN, INPUT);

      pinMode(motorPin, OUTPUT);
        Serial.begin(9600);
        while (! Serial);
        Serial.println("Speed 0 to 255");

      }

      void loop() {
       buttonStateUP =digitalRead(buttonSUP);
       if(buttonStateUP=HIGH){
          servo1.write(90);
          Serial.println("UP");
        }
        if(buttonStateDOWN=HIGH){
          servo1.write(0);
         Serial.println("DOWN");
          }
        else{
            servo1.write(45);
            Serial.println("STABLE");
            }

        if (Serial.available())
        {
          int speed = Serial.parseInt();
          if (speed >= 0 && speed <= 255)
          {
            analogWrite(motorPin, speed);
            Serial.println(speed);
          }
        }

        }

body:
`while (! Serial);`  Is not needed if you have a board with USB-> Serial bridge Chip (arduino uno for example)

    if(buttonStateDOWN=HIGH){
    }

In every condition you used `=` instead of `==`. Your "condition" actually assigns `HIGH` to `buttonStateDOWN`. If you want to compare integers, use `==`.

And according to the question, I think you have misunderstood the speed buttons (or maybe I have). I think, they want you to code it so while the button is pressed or every time the button is pressed, the speed changes by +1 or -1.

Assuming the rest works fine, there could be a problem with your serial output, since you just spam messages.

Read about the `millis();`, it can help you so you only send something every x amount of seconds, without using `delay();` [Here][1]

  [1]: https://forum.arduino.cc/index.php?topic=503368.0


message:
MPU-6050 with Arduino - postmortem

I'm working with MPU-6050 with Arduino Uno.

I copied the code below from [Arduino Playground - MPU6050][1].

Code :

      // MPU-6050 Short Example Sketch
      // By Arduino User JohnChi
      // August 17, 2014
      // Public Domain
      #include<Wire.h>
      const int MPU_addr = 0x68; // I2C address of the MPU-6050
      int16_t AcX, AcY, AcZ, Tmp, GyX, GyY, GyZ;
      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);
      }
      void loop() {
        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
        AcX = Wire.read() << 8 | Wire.read(); // 0x3B (ACCEL_XOUT_H) & 0x3C (ACCEL_XOUT_L)
        AcY = Wire.read() << 8 | Wire.read(); // 0x3D (ACCEL_YOUT_H) & 0x3E (ACCEL_YOUT_L)
        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.print(AcX);
        Serial.print(" | AcY = "); Serial.print(AcY);
        Serial.print(" | AcZ = "); Serial.print(AcZ);
        Serial.print(" | Tmp = "); Serial.print(Tmp / 340.00 + 36.53); //equation for temperature in degrees C from datasheet
        Serial.print(" | GyX = "); Serial.print(GyX);
        Serial.print(" | GyY = "); Serial.print(GyY);
        Serial.print(" | GyZ = "); Serial.println(GyZ);
        delay(333);
      }

Firstly, I want to know every details about this code, **AcX, AcY, AcZ, GyX, GyY, GyZ** what all these mean ?

*It will be nice with some visual representation.*

Secondly, If I change the delay to 500 from 333, will it cause a problem ?

*This type of stupid question because, I can't find any relatable figure with 333 except 1000/3*

  [1]: https://playground.arduino.cc/Main/MPU-6050/

body:
I think that  AcX, AcY, AcZ, GyX, GyY, GyZ are raw acceleration and gyroscopic values recieved from mpu6050 in the corresponding directions. in order to recieve them a procedure is followed.

     Wire.read();
means two registers are read and stored in the same variable

       accelerometer_x = Wire.read()<<8 | Wire.read();

reads registers: 0x3B (ACCEL_XOUT_H) and 0x3C (ACCEL_XOUT_L) that is ,
it deals with bitwise operation to shift the values 8 bits left (multiplying it by 256).
This enables addition ("|" or "ored") of two datas in order to continuously output the accelerometer data !! Without this you would not be able to see the increasing and decreasing sloping values .
Further, the print just displays the instantaneous values on screen.

 If you want to go in deapth of the code, you can visit this site for line to line description !!

https://www.mschoeffler.de/2017/12/09/example-application-gy-521-module-mpu-6050-breakout-board-and-arduino-uno/

     delay(500);

Totally depends on your project, i don't see any forecoming issues if you will make 333 go 500 !! It will just stablize the output on screen there for a bit longer (for .5 seconds)


body:
    AcX = Accelerometer data in X axis in floating point.
    AcY = Accelerometer data in Y axis in floating point.
    AcZ = Accelerometer data in Z axis in floating point.
    GyX = Gyroscope data in X axis in floating point.
    GyY = Gyroscope data in X axis in floating point.
    GyZ = Gyroscope data in X axis in floating point

.

Secondly study regarding I2C communication and MPU 6050 datasheet.

Third you have any value for delay as it is how fast you want to fetch data from all axis from IMU.


message:
How to Simulate and Tune a PID

I've been trying to simulate a PID using [Brett Beauregard's PID library](https://github.com/br3ttb/Arduino-PID-Library/) in order to understand it better. Here is my code.

<!-- language: lang-cpp -->

    #include <PID_v1.h>

    const unsigned int numReadings = 500;
    double analogVals[numReadings];
    unsigned int i = 0;
    int angle = 0;
    //Define Variables we'll be connecting to
    double Setpoint, Input, Output;
    //Specify the links and initial tuning parameters
    PID myPID(&Input, &Output, &Setpoint,2,5,1, DIRECT);
    void setup()

    {
      //turn the PID on
      myPID.SetMode(AUTOMATIC);
      Serial.begin(115200);
      Setpoint = 300;
      myPID.SetOutputLimits(-2,2);
      myPID.SetSampleTime(100);
      Input = random(292, 302) ;
    }

    void loop()
    {
      if (i % 2 == 0) {
      Input += random(-2,3);
      }
      angle += 1 % 360;
      Input += sin(angle*355/(113*180));
      myPID.Compute();
      Input += Output;
        analogVals[i] = Input;
        i++;
        if (i>= numReadings)
        {
          for (int j = 0; j < i; j++) {
          Serial.println(analogVals[j]);
          }

          i = 0; //reset to beginning of array, so you don't try to save readings outside of the bounds of the array
        }
    }
Even if I restrict the output of the PID to a very small value, I get huge nonsense results of this code. It oscillates like -1000 to 1000. I've read this https://robotics.stackexchange.com/questions/167/what-are-good-strategies-for-tuning-pid-loops
and tried to adjust my parameters, but they're just shots in the dark really, I can't even damp these massive oscillations. How would I tune a PID to cancel out a sin error ?

Thanks in advance

body:
I do not have your PID_v1.h, but I made a simple experiment trying to control your example with a simple P-Controller instead of the PID lib. I made the following changes to your code:

    ...
    double K_P = 1;
    ...
    //myPID.Compute();
      Output = K_P*(Setpoint - Input);
      Input += Output;

This is working for very small amounts of `K_P`, but as soon as `K_P` gets higher than 2.0 it gets instable very fast. I guess this is what you are observing. The reason for me is, that you have implemented a ideal control path. In real control tasks you will always have some transfer behavior

Therefore I added a simple PT1 element (first-order lag element) to your code, now your system is much more stable and you can experiment with the K, I and D factors. Here it works with K_P even higher than 400:

    // #include <PID_v1.h>

    const unsigned int numReadings = 500;
    double analogVals[numReadings];
    unsigned int i = 0;
    int angle = 0;
    //Define Variables we'll be connecting to
    double Setpoint, Input, Output;
    double Input_PT1;
    double K_P = 20;
    //Specify the links and initial tuning parameters
    //PID myPID(&Input, &Output, &Setpoint,2,5,1, DIRECT);
    void setup()

    {
      //turn the PID on
      // myPID.SetMode(AUTOMATIC);
      Serial.begin(115200);
      Setpoint = 300;
      // myPID.SetOutputLimits(-2,2);
      //myPID.SetSampleTime(100);
      Input = random(292, 302) ;
    }

    void loop()
    {
      if (i % 2 == 0) {
        Input += random(-2, 3);
      }
      angle += 1 % 360;
      Input += sin(angle * 355 / (113 * 180));
      //myPID.Compute();
      Output = K_P * (Setpoint - Input_PT1);
      Input += Output;
      // start PT1
      Input_PT1 -= Input_PT1 / 25;
      Input_PT1 += Input / 25;
      // end PT1
      analogVals[i] = Input_PT1;
      i++;
      if (i >= numReadings)
      {
        for (int j = 0; j < i; j++) {
          Serial.println(analogVals[j]);
        }

        i = 0; //reset to beginning of array, so you don't try to save readings outside of the bounds of the array
      }
    }

 Some hint:

 - The sketch above does not initialize `Input_PT1`, so it takes some secondes until you reach a steady value of 300, if you do not want to wait, just initialize `Input_PT1` with 300. But this is exactly where you can start increasing first I, then D factors to try to increase speed for reaching a steady value of 300 and experiencing what influence I and D part will have.
 - `Input_PT1` is not a good naming, since this is the output of the PT1 element, but since you are using it as the PID Input, I did not change.

Here a drawing of what I implemented in contrast to your sketch (at least I hope so ;-))

[![enter image description here][1]][1]

  [1]: https://i.stack.imgur.com/3Mbhv.png


message:
Reading inside critical sections from ISR

Is it necessary to protect reads of volatile variables in critical sections when using interrupts? Or are critical sections only required when concurrently writing variables?

Here is an example of a variable written within an ISR which is protected with a critical section:
```c++
void loop() {
    portENTER_CRITICAL(&mux);
    uint other = variable_written_from_isr + 1;
    portEXIT_CRITICAL(&mux);
}
```
What will happen if an interrupt changes `variable_written_from_isr` while it is being read? Would anything worse that inconsistencies happen?

Here is an opposite example where a variable is written from an interrupt and read from the loop (or a task):
```c++
void IRAM_ATTR handleInterrupt() {
    portENTER_CRITICAL_ISR(&mux);
    uint other = variable_written_from_loop + 1;
    portEXIT_CRITICAL_ISR(&mux);
}
```
Please note that I aware of *stdatomic*. I am mainly interested in understanding the behavior of concurrent access in the context of interrupts.

body:
You should use critical sections around any operations that could potentially be affected by the execution of an ISR (or which could affect an ISR) *that aren't atomic*.

Simply put, an atomic instruction is one which can be represented by a single assembly language instruction. You can't interrupt during the execution of an assembly instruction, so anything that only takes one instruction can't be interrupted until it's complete.

Examples would be moving a value from one 8-bit variable (assuming an 8-bit architecture) into a register, storing an 8-bit value into memory, etc.

What instructions are likely to be atomic very much depends on the architecture that you are working on.  The only real way to be sure is to compile the code into assembly language and examine what is produced. Of course, that means learning the assembly language of your chosen architecture.

However: if in doubt, use a critical section. Better to be safe than sorry. But keep those critical sections as short as possible to not disturb the interrupts more than is needed.

For example, instead of starting a critical section, reading some volatile value, doing some calculations with it, and writing it elsewhere, you should use the critical section just to read the volatile value into a temporary variable. After the critical section, you can then do your calculations and things with it, while the interrupt is then free to be called again.


body: A non-atomic read in your main code of a 2-or-more-byte variable that can be written in an interrupt routine *does* need to be protected. In this case, the variable itself can't be corrupted, but the value read from it by your main code might be - in the case where the main code is reading the shared variable one byte at a time, and gets interrupted between two of those byte-reads.


message:
connection of led with dht and code combination

[![enter image description here][1]][1]Hi again? I saw my last question did not come out well, so let me rephrase it.
Ideally, my project is composed of 3 sensors: 2 dht-22 sensors and an mq-7 sensor.
**For the dht22 sensors**, I am using data pin connections 9 and 10 PWM on the Arduino mega 2560 board with their respective 10 kilo-ohm resistors, with 5v supply and ground connections.
The **issue** is that I want to set limits for both temperature and humidity for both sensors to be:  (16 <temperature < 32) degrees Celsius and for humidity to be: (11 < humidity < 15) %. And also when this limits are reached, LEDs (one for each sensor) should be able to display. For the LEDs I do not know where to connect them, so any form of assistance will be highly appreciated. I have attached code for the DHT-22 sensors for any improvements to be made.

    #include "DHT.h"

    #define DHT1PIN 9     // what pin we're connected to
    #define DHT2PIN 10

    #define DHT1TYPE DHT22
    #define DHT2TYPE DHT22

    // Connect pin 1 (on the left) of the sensor to +5V
    // Connect pin 2 of the sensor to whatever your DHTPIN is
    // Connect pin 4 (on the right) of the sensor to GROUND
    // Connect a 10K resistor from pin 2 (data) to pin 1 (power) of the sensor

    DHT dht1(DHT1PIN, DHT1TYPE);
    DHT dht2(DHT2PIN, DHT2TYPE);

    void setup() {
      Serial.begin(115200);
      Serial.println("DHTxx test!");

      dht1.begin();
      dht2.begin();
    }

    void loop() {
      // Reading temperature or humidity takes about 250 milliseconds!
      // Sensor readings may also be up to 2 seconds 'old' (its a very slow sensor)
      float h1 = dht1.readHumidity();
      float t1 = dht1.readTemperature();
      float h2 = dht2.readHumidity();
      float t2 = dht2.readTemperature();

      // check if returns are valid, if they are NaN (not a number) then something went wrong!
      if (isnan(t1) || isnan(h1)) {
        Serial.println("Failed to read from DHT #1");
      } else {
        Serial.print("Humidity 1: ");
        Serial.print(h1);
        Serial.print(" %\t");
        Serial.print("Temperature 1: ");
        Serial.print(t1);
        Serial.println(" *C");
      }
      if (isnan(t2) || isnan(h2)) {
        Serial.println("Failed to read from DHT #2");
      } else {
        Serial.print("Humidity 2: ");
        Serial.print(h2);
        Serial.print(" %\t");
        Serial.print("Temperature 2: ");
        Serial.print(t2);
        Serial.println(" *C");
      }
      Serial.println();
    }

Ps: LEDs used are 10mm.
For the **MQ-7 sensor**, this is it's code.

    /* MQ-7 Carbon Monoxide Sensor Circuit with Arduino */

     const int AOUTpin=0;//the AOUT pin of the CO sensor goes into analog pin A0 of the arduino
     const int DOUTpin=8;//the DOUT pin of the CO sensor goes into digital pin D8 of the arduino
     const int ledPin=13;//the anode of the LED connects to digital pin D13 of the arduino

     int limit;
     int value;

     void setup() {
     Serial.begin(115200);//sets the baud rate
     pinMode(DOUTpin, INPUT);//sets the pin as an input to the arduino
     pinMode(ledPin, OUTPUT);//sets the pin as an output of the arduino
     }

     void loop()
     {
     value= analogRead(AOUTpin);//reads the analaog value from the CO sensor's AOUT pin
     limit= digitalRead(DOUTpin);//reads the digital value from the CO sensor's DOUT pin
     Serial.print("CO value: ");
     Serial.println(value);//prints the CO value
     Serial.print("Limit: ");
     Serial.print(limit);//prints the limit reached as either LOW or HIGH (above or underneath)
     delay(100);
     if (limit == HIGH){
     digitalWrite(ledPin, HIGH);//if limit has been reached, LED turns on as status indicator
     }
     else{
     digitalWrite(ledPin, LOW);//if threshold not reached, LED remains off
     }
     }

I am yet to buy a relay circuit to be able to connect it with the circuit using a , but for now I would appreciate it the scenarios highlighted for the sensors could be addressed and also, how the two codes could be combined to be one single code.
If there is any question, feel free to ask.
The project is for silo monitoring and control.

  [1]: https://i.stack.imgur.com/kVS2J.jpg

body:
Only thing that gives people problems when combining two simple sketches are "delay" commands. There is just one "delay" so it's perfect.

 1. Create new sketch
 2. Paste everything that's not in a method from the two sketches.
 3. Combine `setup` methods together by pasting first one and second one below.
 4. Remove duplicated commands like `Serial.begin(115200);` from the method
 5. Combine `loop` methods together by pasting first one and second one below.
 6. Move code in `loop` to make the code visually pleasing (it's called the "[smell][1]" of code)

This should not be a big problem with those two particular sketches.
Please ask more precise questions as soon as you will have problems.

  [1]: https://en.wikipedia.org/wiki/Code_smell


message:
Prevent function inlining

I'm trying to shrink the compiled code size, and I have noticed that the compiler inlines functions a lot, even the ones I have not marked "inline", but I can't manage to turn that off.

It looks like the compiler uses the -Os flag by default (optimize for low program size), because when I add it, the resulting program size is the same.

I tried adding "\__attribute__((noinline))" to the functions but it makes no difference. Any idea how to prevent function inlining?

I'm using Visualmicro on Visual Studio Community 2017. Arduino 1.8.8. Arduino Uno board.

body:
As I wrote in the comments, I can't recreate this problem again. So I apologize for wasting everyone's time. But I still find it weird how the -Os flag works. I assumed it meant smallest possible size. But I now think it means "fairly small, but also make it run fast". Look at the code below, and how using the noinline attribute makes the code smaller. I added the -Os compiler flag to be sure, but I think it is already on by default.

```
class InlineClass
{
public:
 void __attribute__((noinline)) testFunc(int arg1)  // 570 bytes
 //void testFunc(int arg1)    // 602 bytes
 //inline void testFunc(int arg1)  // 602 bytes
 {
  _var1 = arg1 + 1;
  _var2 = arg1 + 2;
  _var3 = arg1 + 3;
  _var4 = arg1 + 4;
  _var5 = arg1 + 5;
 }

private:
 volatile int _var1 = 0;
 volatile int _var2 = 0;
 volatile int _var3 = 0;
 volatile int _var4 = 0;
 volatile int _var5 = 0;
};

void setup()
{
 InlineClass ic;
 ic.testFunc(1);
 ic.testFunc(2);
 ic.testFunc(3);
 ic.testFunc(4);
 ic.testFunc(5);
}

```


message:
Changing Baud Rate not working

I have copied this code from [Github][1] :

     #include <Wire.h>
     #include <MPU6050.h>

    MPU6050 mpu;

    // Timers
    unsigned long timer = 0;
    float timeStep = 0.01;

    // Pitch, Roll and Yaw values
    float pitch = 0;
    float roll = 0;
    float yaw = 0;

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

        // Initialize MPU6050
        while(!mpu.begin(MPU6050_SCALE_2000DPS, MPU6050_RANGE_2G))
        {
             //Serial.println("Could not find a valid MPU6050 sensor, check
                   wiring!");
         }

         // Calibrate gyroscope. The calibration must be at rest.
         // If you don't want calibrate, comment this line.
        //mpu.calibrateGyro();

         // Set threshold sensivty. Default 3.
         // If you don't want use threshold, comment this line or set 0.
          mpu.setThreshold(1);
       }

       void loop()
          {
           timer = millis();

          // Read normalized values
         Vector norm = mpu.readNormalizeGyro();

         // Calculate Pitch, Roll and Yaw
          pitch = pitch + norm.YAxis * timeStep;
           roll = roll + norm.XAxis * timeStep;
           yaw = yaw + norm.ZAxis * timeStep;

             // Output raw
          //Serial.print(" Pitch = ");
             Serial.print(pitch);
               Serial.print(":");
            //Serial.print(" Roll = ");
         Serial.print(roll);
            Serial.print(":");
           //Serial.print(" Yaw = ");
            Serial.println(yaw);

               // Wait to full timeStep period
          delay((timeStep*1000) - (millis() - timer));
         }

**Now the question is, whenever I try to change the baud rate Serial Monitor becomes empty.**

*How can this be resolved?*

Some screen-shots :

[![At 03:38][2]][2]
[![At 03:39][3]][3]

Stuck!!!

  [1]: https://github.com/jarzebski/Arduino-MPU6050/blob/master/MPU6050_gyro_pitch_roll_yaw/MPU6050_gyro_pitch_roll_yaw.ino
  [2]: https://i.stack.imgur.com/UhtrN.png
  [3]: https://i.stack.imgur.com/n0T9F.png

body:
You are not very much clear but these are the possible reasons for your problem.

 1. You are using a while loop in your setup() function in your code. Your code might get stuck in there that's why you are not able to see pitch and roll. Try removing comment from the Serial.begin function over there.

 2. After Changing baudrate in your code please make sure you are changing it on your serial monitor as well.


message:
UART ESP and MEGA2560

Could someone help me with some suggestions please?
Using ESP8266 and MEGA2560 on UART interface i want to display the message received on the mega serial to the LCD connected to it on i2c. The problem is that the LCD shows some strange unknown character and the serial monitor corresponding to mega shows this :

    LED on LED OFF LED on LED OFF LED on LED OFF LED on LED OFF LED on LED OFF LED on LED OFF LED on LED OFF LED on LED OFF LED on LED OFF LED on

when it should display this:

    LED on
    LED OFF
    LED on
    LED OFF
    LED on
    LED OFF
    LED on
    LED OFF
    LED on
    LED OFF
    LED on
    LED OFF
    LED on
    LED OFF
    LED on
    LED OFF
    LED on
    LED OFF

the code for ESP is this:

    int pinLed = 16;
    void setup()
    {

     Serial.begin(115200);
     Serial.begin(115200);
     pinMode(16,OUTPUT);
     delay(500);
    }

    void loop()
    {

    digitalWrite(16,HIGH);
    Serial.print("LED on\n");
    delay(5000);

    digitalWrite(16,LOW);
    Serial.print("LED OFF\n");
    delay(5000);

    }

the code for mega is this:

    #include <Wire.h>
    #include <LiquidCrystal_I2C.h>
    #include<SoftwareSerial.h>
    LiquidCrystal_I2C lcd(0x3F,20,4);

    void setup()
    {

      Serial.begin(115200);
      lcd.init();
      lcd.backlight();
      while (!Serial)
      {

        Serial.print("Attempting to connect! ");
        Serial.print("Trying again...");
      }
    }

      void loop()
    {

      if (Serial.available()>0)

      {
        char c = Serial.write(Serial.read());
        Serial.print(c);
        lcd.print(c);
      }
    }

body:
Solution to your problems.

 1. Use println instead of print.
 2. Change `char c = Serial.write(Serial.read());` to `char c = Serial.read();`


message:
Strange behaviour with WS2812B RGB LED Strip

I tried to use a RGB LED strip, following a guide.
I connected the voltage pin to the Arduino UNO **5v pin**, the ground pin to the **GRN pin** and I used the pin 5 for **DIN**.

I used this image as reference:
[![enter image description here][1]][1]

I tried two different libraries, with the first one, the FAST LED, I used this code:

    #include <FastLED.h>

    #define LED_PIN     5
    #define NUM_LEDS    15
    #define BRIGHTNESS  64
    #define LED_TYPE    WS2811
    #define COLOR_ORDER GRB
    CRGB leds[NUM_LEDS];

    #define UPDATES_PER_SECOND 100

    CRGBPalette16 currentPalette;
    TBlendType    currentBlending;

    extern CRGBPalette16 myRedWhiteBluePalette;
    extern const TProgmemPalette16 myRedWhiteBluePalette_p PROGMEM;

    void setup() {
        delay( 3000 ); // power-up safety delay
        FastLED.addLeds<LED_TYPE, LED_PIN, COLOR_ORDER>(leds, NUM_LEDS).setCorrection( TypicalLEDStrip );
        FastLED.setBrightness(  BRIGHTNESS );

        currentPalette = RainbowColors_p;
        currentBlending = LINEARBLEND;
    }

    void loop()
    {
        ChangePalettePeriodically();

        static uint8_t startIndex = 0;
        startIndex = startIndex + 1; /* motion speed */

        FillLEDsFromPaletteColors( startIndex);

        FastLED.show();
        FastLED.delay(1000 / UPDATES_PER_SECOND);
    }

    void FillLEDsFromPaletteColors( uint8_t colorIndex)
    {
        uint8_t brightness = 255;

        for( int i = 0; i < NUM_LEDS; i++) {
            leds[i] = ColorFromPalette( currentPalette, colorIndex, brightness, currentBlending);
            colorIndex += 3;
        }
    }

    void ChangePalettePeriodically()
    {
        uint8_t secondHand = (millis() / 1000) % 60;
        static uint8_t lastSecond = 99;

        if( lastSecond != secondHand) {
            lastSecond = secondHand;
            if( secondHand ==  0)  { currentPalette = RainbowColors_p;         currentBlending = LINEARBLEND; }
            if( secondHand == 10)  { currentPalette = RainbowStripeColors_p;   currentBlending = NOBLEND;  }
            if( secondHand == 15)  { currentPalette = RainbowStripeColors_p;   currentBlending = LINEARBLEND; }
            if( secondHand == 20)  { SetupPurpleAndGreenPalette();             currentBlending = LINEARBLEND; }
            if( secondHand == 25)  { SetupTotallyRandomPalette();              currentBlending = LINEARBLEND; }
            if( secondHand == 30)  { SetupBlackAndWhiteStripedPalette();       currentBlending = NOBLEND; }
            if( secondHand == 35)  { SetupBlackAndWhiteStripedPalette();       currentBlending = LINEARBLEND; }
            if( secondHand == 40)  { currentPalette = CloudColors_p;           currentBlending = LINEARBLEND; }
            if( secondHand == 45)  { currentPalette = PartyColors_p;           currentBlending = LINEARBLEND; }
            if( secondHand == 50)  { currentPalette = myRedWhiteBluePalette_p; currentBlending = NOBLEND;  }
            if( secondHand == 55)  { currentPalette = myRedWhiteBluePalette_p; currentBlending = LINEARBLEND; }
        }
    }

    void SetupTotallyRandomPalette()
    {
        for( int i = 0; i < 16; i++) {
            currentPalette[i] = CHSV( random8(), 255, random8());
        }
    }

    void SetupBlackAndWhiteStripedPalette()
    {
        fill_solid( currentPalette, 16, CRGB::Black);
        currentPalette[0] = CRGB::White;
        currentPalette[4] = CRGB::White;
        currentPalette[8] = CRGB::White;
        currentPalette[12] = CRGB::White;

    }

    // This function sets up a palette of purple and green stripes.
    void SetupPurpleAndGreenPalette()
    {
        CRGB purple = CHSV( HUE_PURPLE, 255, 255);
        CRGB green  = CHSV( HUE_GREEN, 255, 255);
        CRGB black  = CRGB::Black;

        currentPalette = CRGBPalette16(
                                       green,  green,  black,  black,
                                       purple, purple, black,  black,
                                       green,  green,  black,  black,
                                       purple, purple, black,  black );
    }

    const TProgmemPalette16 myRedWhiteBluePalette_p PROGMEM =
    {
        CRGB::Red,
        CRGB::Gray,
        CRGB::Blue,
        CRGB::Black,

        CRGB::Red,
        CRGB::Gray,
        CRGB::Blue,
        CRGB::Black,

        CRGB::Red,
        CRGB::Red,
        CRGB::Gray,
        CRGB::Gray,
        CRGB::Blue,
        CRGB::Blue,
        CRGB::Black,
        CRGB::Black
    };

and with the second library, Adafruit_Neopixel

    #include <Adafruit_NeoPixel.h>
    #define PIN 5
    #define NUM_LEDS 15
    // Parameter 1 = number of pixels in strip
    // Parameter 2 = pin number (most are valid)
    // Parameter 3 = pixel type flags, add together as needed:
    //   NEO_KHZ800  800 KHz bitstream (most NeoPixel products w/WS2812 LEDs)
    //   NEO_KHZ400  400 KHz (classic 'v1' (not v2) FLORA pixels, WS2811 drivers)
    //   NEO_GRB     Pixels are wired for GRB bitstream (most NeoPixel products)
    //   NEO_RGB     Pixels are wired for RGB bitstream (v1 FLORA pixels, not v2)
    Adafruit_NeoPixel strip = Adafruit_NeoPixel(NUM_LEDS, PIN, NEO_GRB + NEO_KHZ800);

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

    // *** REPLACE FROM HERE ***
    void loop() {
      RGBLoop();
    }

    void RGBLoop(){
      for(int j = 0; j < 3; j++ ) {
        // Fade IN
        for(int k = 0; k < 256; k++) {
          switch(j) {
            case 0: setAll(k,0,0); break;
            case 1: setAll(0,k,0); break;
            case 2: setAll(0,0,k); break;
          }
          showStrip();
          delay(3);
        }
        // Fade OUT
        for(int k = 255; k >= 0; k--) {
          switch(j) {
            case 0: setAll(k,0,0); break;
            case 1: setAll(0,k,0); break;
            case 2: setAll(0,0,k); break;
          }
          showStrip();
          delay(3);
        }
      }
    }
    // *** REPLACE TO HERE ***

    void showStrip() {
     #ifdef ADAFRUIT_NEOPIXEL_H
       // NeoPixel
       strip.show();
     #endif
     #ifndef ADAFRUIT_NEOPIXEL_H
       // FastLED
       FastLED.show();
     #endif
    }

    void setPixel(int Pixel, byte red, byte green, byte blue) {
     #ifdef ADAFRUIT_NEOPIXEL_H
       // NeoPixel
       strip.setPixelColor(Pixel, strip.Color(red, green, blue));
     #endif
     #ifndef ADAFRUIT_NEOPIXEL_H
       // FastLED
       leds[Pixel].r = red;
       leds[Pixel].g = green;
       leds[Pixel].b = blue;
     #endif
    }

    void setAll(byte red, byte green, byte blue) {
      for(int i = 0; i < NUM_LEDS; i++ ) {
        setPixel(i, red, green, blue);
      }
      showStrip();
    }

I don't know why, but only some of the leds in the strips make lights and only blue lights. How can I fix this problem?
I also tried to change the **Din** pin using 4, 5 and 6, but nothing changed.

[1]: https://i.stack.imgur.com/W0VKN.png

**EDIT**

I found that all my led were broken... I bought a new strip and now I have a prototype perfectly working using any of the code above. Thanks for helping me

body:
In the first sketch you use

    #define LED_TYPE    WS2811

While you have WS2812

Each led strip type has different timings, so it can occur that some LEDs will flash, or are on or off while they should not be, if the wrong model is selected.

Probably the first LEDs work better than later ones.


body:
What makes you sure replacing the LED strip was the solution? I suggest running the LED strip from the Arduino +5V is a likely problem (too much current drawn) and using a different LED strip you've just been lucky that it works now.

Try with a separate power supply for the LEDs but connect grounds together. If you don't have another 5V power supply which can supply at least 1 Amp, try limiting the brightness and/or number of LEDs *in software* to see if it works and if so, then try with the original strip.


message:
Fading led with push button

I need to make for school a project. That when i hold a button it fades. But when you let go the button it needs to stop immediately. But when i you hold the button again it needs to start again with fading but the brightness needs to start from 0. I have a program but when i press again it just starts from the previous brightness. Pls help. This is my code:

    int led = 9;
    int brightness = 5;
    int fadeAmount = 5;

    void setup() {
       Serial.begin(9600);
        pinMode(led, OUTPUT);
    }
    void loop() {
      int val = digitalRead(2);
      Serial.println(val);
    if (val==HIGH){
      analogWrite(led, brightness);
      brightness = brightness + fadeAmount;
      if (brightness <= 0 || brightness >= 255) {
        fadeAmount = -fadeAmount; }
      delay(100);
    }
    else{

      digitalWrite(9, LOW);
    }
    }

body:
The main problem is you have to reset brightness to 0 when the switch is LOW. Btw, I did not test the sketch, only compiled it.

    int led = 9;
    int brightness = 5;
    int fadeAmount = 5;

    void setup() {
       Serial.begin(9600);
        pinMode(led, OUTPUT);
    }
    void loop() {
      int val = digitalRead(2);
      Serial.println(val);
    if (val==HIGH){
      analogWrite(led, brightness);
      brightness = brightness + fadeAmount;
      if (brightness <= 0 || brightness >= 255) {
        fadeAmount = -fadeAmount; }
      delay(100);
    }
    else{

      digitalWrite(9, LOW);
      brightness = 0;    // Restart with brightness 0
    }
    }

Some other improvements result in:

    #define LED_PIN      9
    #define DELAY_TIME 100
    int brightness = 5;
    int fadeAmount = 5;

    void setup() {
       Serial.begin(9600);
       pinMode(LED_PIN, OUTPUT);
    }

    void loop() {
      int switchButton = digitalRead(2);
      Serial.println(switchButton);

      if (switchButton == HIGH) {
        analogWrite(LED_PIN, brightness);
        brightness += fadeAmount;
        if ((brightness <= 0) || (brightness >= 255)) {
          fadeAmount = -fadeAmount;
        }
        delay(DELAY_TIME );
      }
      else {
        digitalWrite(LED_PIN, LOW);
        brightness = 0;    // Restart with brightness 0
      }
    }

Explanation

1. Always indent your code (so that { and } are clear, notice each new { increases the indentation by two spaces, each } decreases the indentation by two spaces.
2. For values that do not change use a #define. This prevents (in this case) a few bytes not be stored in valuable memory space. Especially if you would use arrays this is important.
3. You used 9 in `digitalWrite(9, LOW);` which was probably a mistake, always use defines wherever possible. I also would use `#define DELAY_TIME 100` instead of the hardcoded 100 value.
4. I addes some spaces before/after values (like `switchButton == HIGH`). It doesn't matter if you do or not, but be consequent.
5. Use good variable names (`switchButton` is more clear than `val`.
6. Use `brightness += fadeAmount;` instead of `brightness = brightness + fadeAmount;`; this is the normal way of increasing (or decreasing/multiplying/whatever) the value of a variable.
7. Use ( and ) in non trivial if statements like `if ((brightness <= 0) || (brightness >= 255))`, this could save you hours of searching in case you ever make a mistake (in this case there is no functional change).

Good luck with your project.


message:
MAX7219 and Arduino

I am getting started in running this 8x8 led on an Arduino. Regardless of which tutorial sketch I attempted, I never got a scrolling text that I expect. What happens seems to be only a single (out of four) led module being addressed at a time, resulting in, for example, the message being scrolled on one module at a time, but all four in succession. Could it be a module problem?

body:
Got it somewhat working by changing:

    #define HARDWARE_TYPE MD_MAX72XX::FC16_HW
    to:
    #define HARDWARE_TYPE MD_MAX72XX::ICSTATION_HW
    But still a little problem with the last character in a message not showing all leds lit until it starts to scroll after the initial program delay. Then all is fine.
    Anyone want to address that issue? My sketch follows:

    {    // Use the Parola library to scroll text on the display
    //
    // Demonstrates the use of the scrolling function to display text received
    // from the serial interface
    //
    // User can enter text on the serial monitor and this will display as a
    // scrolling message on the display.
    // Speed for the display is controlled by a pot on SPEED_IN analog in.
    // Scrolling direction is controlled by a switch on DIRECTION_SET digital in.
    // Invert ON/OFF is set by a switch on INVERT_SET digital in.
    //
    // UISwitch library can be found at https://github.com/MajicDesigns/MD_UISwitch
    // MD_MAX72XX library can be found at https://github.com/MajicDesigns/MD_MAX72XX
    //

    #include <MD_Parola.h>
    #include <MD_MAX72xx.h>
    #include <SPI.h>

    // set to 1 if we are implementing the user interface pot, switch, etc
    #define USE_UI_CONTROL 0

    #if USE_UI_CONTROL
    #include <MD_UISwitch.h>
    #endif

    // Turn on debug statements to the serial output
    #define DEBUG 0

    #if DEBUG
    #define PRINT(s, x) { Serial.print(F(s)); Serial.print(x); }
    #define PRINTS(x) Serial.print(F(x))
    #define PRINTX(x) Serial.println(x, HEX)
    #else
    #define PRINT(s, x)
    #define PRINTS(x)
    #define PRINTX(x)
    #endif

    // Define the number of devices we have in the chain and the hardware interface
    // NOTE: These pin numbers will probably not work with your hardware and may
    // need to be adapted
    //#define HARDWARE_TYPE MD_MAX72XX::FC16_HW
    //#define HARDWARE_TYPE MD_MAX72XX::GENERIC_HW
    #define HARDWARE_TYPE MD_MAX72XX::ICSTATION_HW
    #define MAX_DEVICES 4
    #define CLK_PIN   13
    #define DATA_PIN  11
    #define CS_PIN    10

    // HARDWARE SPI
    MD_Parola P = MD_Parola(HARDWARE_TYPE, CS_PIN, MAX_DEVICES);
    // SOFTWARE SPI
    //MD_Parola P = MD_Parola(HARDWARE_TYPE, DATA_PIN, CLK_PIN, CS_PIN, MAX_DEVICES);

    // Scrolling parameters
    #if USE_UI_CONTROL
    const uint8_t SPEED_IN = A5;
    const uint8_t DIRECTION_SET = 8;  // change the effect
    const uint8_t INVERT_SET = 9;     // change the invert

    const uint8_t SPEED_DEADBAND = 5;
    #endif // USE_UI_CONTROL

    uint8_t scrollSpeed = 25;    // default frame delay value
    textEffect_t scrollEffect = PA_SCROLL_LEFT;
    textPosition_t scrollAlign = PA_LEFT;
    uint16_t scrollPause = 2000; // in milliseconds

    // Global message buffers shared by Serial and Scrolling functions
    #define BUF_SIZE 75
    char curMessage[BUF_SIZE] = { "" };
    char newMessage[BUF_SIZE] = { "Got Signals?" };//{ "Hello! Enter new message?" };
    bool newMessageAvailable = true;

    #if USE_UI_CONTROL

    MD_UISwitch_Digital uiDirection(DIRECTION_SET);
    MD_UISwitch_Digital uiInvert(INVERT_SET);

    void doUI(void)
    {
      // set the speed if it has changed
      {
        int16_t speed = map(analogRead(SPEED_IN), 0, 1023, 10, 150);

        if ((speed >= ((int16_t)P.getSpeed() + SPEED_DEADBAND)) ||
          (speed <= ((int16_t)P.getSpeed() - SPEED_DEADBAND)))
        {
          P.setSpeed(speed);
          scrollSpeed = speed;
          PRINT("\nChanged speed to ", P.getSpeed());
        }
      }

      if (uiDirection.read() == MD_UISwitch::KEY_PRESS) // SCROLL DIRECTION
      {
        PRINTS("\nChanging scroll direction");
        scrollEffect = (scrollEffect == PA_SCROLL_LEFT ? PA_SCROLL_RIGHT : PA_SCROLL_LEFT);
        P.setTextEffect(scrollEffect, scrollEffect);
        P.displayClear();
        P.displayReset();
      }

      if (uiInvert.read() == MD_UISwitch::KEY_PRESS)  // INVERT MODE
      {
        PRINTS("\nChanging invert mode");
        P.setInvert(!P.getInvert());
      }
    }
    #endif // USE_UI_CONTROL

    void readSerial(void)
    {
      static char *cp = newMessage;

      while (Serial.available())
      {
        *cp = (char)Serial.read();
        if ((*cp == '\n') || (cp - newMessage >= BUF_SIZE-2)) // end of message character or full buffer
        {
          *cp = '\0'; // end the string
          // restart the index for next filling spree and flag we have a message waiting
          cp = newMessage;
          newMessageAvailable = true;
        }
        else  // move char pointer to next position
          cp++;
      }
    }

    void setup()
    {
      Serial.begin(57600);
      Serial.print("\n[Parola Scrolling Display]\nType a message for the scrolling display\nEnd message line with a newline");

    #if USE_UI_CONTROL
      uiDirection.begin();
      uiInvert.begin();
      pinMode(SPEED_IN, INPUT);

      doUI();
    #endif // USE_UI_CONTROL

      P.begin();
      P.displayText(curMessage, scrollAlign, scrollSpeed, scrollPause, scrollEffect, scrollEffect);
    }

    void loop()
    {
    #if USE_UI_CONTROL
      doUI();
    #endif // USE_UI_CONTROL

      if (P.displayAnimate())
      {
        if (newMessageAvailable)
        {
          strcpy(curMessage, newMessage);
          newMessageAvailable = false;
        }
        P.displayReset();
      }
      readSerial();
    }
}


message:
Is there a way to get my MacBook's date and time into Arduino IDE?

I am using a DS3231 RTC module. It requires to set the time every time it is reset. I was wondering if I could read my MacBook's time and date and feed into the module at the setup stage. Is this possible?

P.S. I do not have to use a battery.

body:
You can use `__DATE__` and `__TIME__` compiler time constants in IDE and do check inside of your `setup()` function if the RTC clock is zeroed then parse and set compile time values.

    char cr[] = __DATE__;
    char ct[] = __TIME__;

At the compile time these macros will be replaced with text constants `"Apr  4 2019"` and `"10:35:22"` respectively.


message:
How to stabilize magnetic levitation system?

I followed everything from this project but still, the magnet is not levitating - https://www.hackster.io/jsirgado/magnet-levitation-with-arduino-eeeee4

The best I can do is to make the magnet jump up and down fast but it never levitates. Have tried changing PID setting from the project as aggressive and mild but still didn't achieve the final result.

I need advice from an expert to tell me what I am doing wrong here. All components are in good condition and 5v electromagnet is strong enough.

So what am I missing here? will implementing fast PWM mode be helpful?

  [1]: https://electronics.stackexchange.com/questions/429840/not-able-to-levitate-magnet-for-magnetic-levitation-project

body: The answer to the solution was quite simple. I just had to comment out all serial port reading and Arduino processing became 60 times faster which helped to levitate the magnet. Thanks to everyone who helped me here :)


message:
How to generate .a and .so files to add in arduino project

I know to make a library on arduino ide with source codes, but I cant send my source code to another users who want to use my lib.

So I need to make a library with precompiled=true info at library.properties. And I need to put my .a and .so files at src/{build.mcu} (in my case, src/avr/mylib.a and mylib.so).

But, where is that files (.a and .so)?!

Does the arduino compiler generate this files? If so, where? If dont, how compiler I need to use?

I found the .o file at appData\local\Temp\arduino_build_XXXX\libraries\mylib\

Thank you very much and sory about my english.

body:
* **Note: I have never done this with the Arduino IDE, so I don't know if the resultant file will be of any use to you.**

A `.a` file (you don't want a `.so` file - that's a shared library that makes no sense on a platform without an OS) is merely an archive (`ar` archive, specifically) that contains one or more .o files.

You create one simply enough using:

    avr-ar rcs myLib.a myLib.o

You will find the `avr-ar` program in the tools installation within your Arduino IDE somewhere.

----

As an aside, [UECIDE](https://uecide.org) (which I wrote) uses library files like these to cache its libraries and other compiled code. You can use UECIDE to directly grab a .a file for your library, which you would find in the `cache` folder of the UECIDE data folder (find it through the Help -> Debug menu).


body:
Thank you Majenko!

But, the program is not avr-ar for me, I use the avr-gcc-ar.

After that, I must to dot_a_linkage=true in my library.properties and manually add mylib.a at AppData\Local\Temp\arduino_build_115676\libraries\mylib\

I dont know why, but this help for me.

I hope help other.

Best regards.


body:
[library] = library name

1) edit the [library] library.properties file and add dot_a_linkage=true to the end ... (/home/name/Arduino/libraries/[library]/library.properties)

2) build the example ...

3) After the build is complete navigate to the build folder (In Linux it's located in the /tmp/arduino_build_xxxxxx folder) then copy the dot_a file from under library folder (libraries/[library].a) to the arduino library folder for the [library] library (/home/name/Arduino/libraries/[library]/src/esp8266/lib[library].a)

4) edit the [library] library library.properties file again and remove dot_a_linkage=true and add precompiled=true and ldflags=-l[library] to the end of the file ...

5)  build the example ... this time it links to the dot_a file ...


message:
how to use AckPayload correctly

i'm trying to send String from an Arduino(Uno) using the Serial. to an another Arduino(Uno). using nRF24l01+. and I'm using the library RF24.h
the String is sended correctly but I have some problems with the acknowledgement.

This is my Rx code.

    #include<SPI.h>
    #include<nRF24L01.h>
    #include<RF24.h>
    const uint64_t pipe[1]= {0xF0F0F0F0E1LL};
    RF24 radio(9,10);
    char buf[32]= "";
    char false_buf[32]= "MKJK212U1H7";
    void setup()
    {
      Serial.begin(115200);
      radio.begin();
      radio.setChannel(0x35);
      radio.setAutoAck(true);
      radio.enableAckPayload();
      radio.enableDynamicPayloads();
      radio.openReadingPipe(1,pipe[0]);
      radio.startListening();
      radio.setRetries(1,15);
      radio.writeAckPayload( 1, false_buf, sizeof(false_buf) );
    }
    void loop()
    {
    int OkMsg;
      while(!radio.available()){};
      if ( radio.available() > 0) {
        radio.read(&buf,sizeof(buf) );
        Serial.println(buf);
        radio.writeAckPayload( 1, buf, sizeof(false_buf) );
          while(!radio.available()){};
      if ( radio.available() > 0) {
        radio.read(&OkMsg,sizeof(OkMsg) );
        Serial.println(OkMsg);
        if(OkMsg == 1){Serial.println("OkMsg's true!");}
        else {Serial.println("OkMsg's false!");}
        }}
      }

and this is my Tx code

    #include <SPI.h>
    #include <RF24.h>
    #include <nRF24L01.h>
    RF24 radio(9, 10); // CE, CSN

    const uint64_t pipe[1]= {0xF0F0F0F0E1LL};

    char CharToSend[32]= "" ;
    char Ack[32]= "" ;
    String inputString = "";
    String Allconfiguration = "";
    boolean stringComplete = false;
    char  inChar;
    boolean isConnected = false;
    int OkMsg = 0;

    void setup()
    {
      SPI.begin();
      Serial.begin(115200);
      RadioSetupTransmiter();
    }

    void loop()
    {
      if(stringComplete)
      {
             if(Allconfiguration.startsWith("\n")){Allconfiguration.remove(0,1);}
         Allconfiguration.remove(Allconfiguration.length());
        inputString = "";
        Serial.print("Allconfiguration : ");
         Serial.println(Allconfiguration);
        int counter = 0;
        for(int i=0; i<Allconfiguration.length(); i++)
        {
          if((Allconfiguration[i] == '\n')&&(i!=Allconfiguration.length()))
          {
            int pre_counter = counter;
            counter = i+1;
            inputString = Allconfiguration.substring(pre_counter, counter);
            if(inputString[0]!='$'){inputString.toCharArray(CharToSend,32);}

            if(radio.write(&CharToSend, sizeof(CharToSend)))
            {CheckData();
           Serial.print("inputString : ");
             Serial.print(CharToSend);}
          }
           if(i == Allconfiguration.length()){
            const char EndChar[2] = "$";

           }
            inputString = "";
        }
        Allconfiguration = "";
        stringComplete = false;
      }
    }

    void serialEvent() {
      while (Serial.available()) {
      char inChar = (char)Serial.read();
        Allconfiguration +=inChar;
         if (inChar == '$'){stringComplete = true;
        }
        }
    }

    void RadioSetupTransmiter(){  radio.begin();

      radio.setChannel(0x35);
      delay(100);
      radio.setAutoAck( true ) ;
      radio.enableAckPayload();
      radio.enableDynamicPayloads();
      // radio.printDetails();

      radio.stopListening();
      radio.openWritingPipe(pipe[0]);

      radio.setRetries(1, 15);
     }

    void CheckData(){
      int OkMsg = 0;
        while (!radio.isAckPayloadAvailable()){};
          if(radio.isAckPayloadAvailable())
          {
           radio.read(&Ack,sizeof(Ack));
           //Serial.println(Ack);
           if(strcmp(CharToSend,Ack) == 0){
            OkMsg = 1  ;
            Serial.println("AckRecived");
            radio.write(&OkMsg,sizeof(OkMsg));}
        }
    }

body:
I have not used the RF24 libary, but below are the register settings that should be written during `void setup()` to use the ACK_PAYLOAD functionality (N.B. nRF24L01+ only, does not exist on nRF24L01.  Check you are using the right version of the radio!)

**TX:**

  - 0x00 CONFIG = PTX mode
  - 0x0B RX_PW_P0 = Number of data bytes in pipe 0
  - 0x1C DYNPD = 0x01. Enable dynamic payload on pipe 0 (set DPL_P0 bit)
  - 0x1D FEATURE = 0x06 (set bits EN_DPL and EN_ACK_PAY).

**RX**

  - 0x00 CONFIG = PRX mode
  - 0x0B RX_PW_P0 = Number of data bytes in pipe 0
  - 0x1C DYNPD = 0x01. Enable dynamic payload on pipe 0 (set DPL_P0 bit)
  - 0x1D FEATURE = 0x06 (set bits EN_DPL and EN_ACK_PAY).
  - Finally, load an initial payload using the W_ACK_PAYLOAD instruction 0xA8, i.e. `SPI.transfer(0xA8); SPI.transfer(payload);`.


message:
How to compare a string

coming from serial monitor with some predefined text stored  as a local variable?
If I say:
```
int led = 2;
String a = " abcds";

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

void loop() {
  String b = Serial.read();
  Serial.println(b);

  if (b != a) {
    digitalWrite(2,LOW);
  }
  else
  {
    digitalWrite(2,HIGH);
  }
}
```
just as an example, this code will not compile because on the serial I receive bytes and I want to compare with a string.
So my question is...
how should be done?

body:
If you do a Google search on "Arduino String" you should find a class reference on the String class. https://www.arduino.cc/reference/en/language/variables/data-types/stringobject/

It has a function `compareTo()` that should do what you need.


body: C has strcmp() function that is used to compare two strings. It will return zero if two strings are equal non zero when not.


body:
version using String (not recommended, but it makes simpler to understand the following C-string version)

    #define LED 2
    const char* a = "abcd";

    void setup() {
      Serial.begin(115200);
      pinMode(LED, OUTPUT);
    }

    void loop() {
      if (Serial.available()) {
        String s = Serial.readStringUntil('\n');
        s.trim();
        if (s == a) {
          digitalWrite(LED, HIGH);
        } else {
          digitalWrite(LED, LOW);
        }
      }
    }

the version with C-string:

    #define LED 2
    const char* a = "abcd";
    char buffer[32];

    void setup() {
      Serial.begin(115200);
      pinMode(LED, OUTPUT);
    }

    void loop() {
      if (Serial.available()) {
        size_t l = Serial.readBytesUntil('\n', buffer, sizeof(buffer - 1));
        if (buffer[l - 1] == '\r') {
          l--;
        }
        buffer[l] = 0; // the terminating zero
        Serial.println(buffer);
        if (strcmp(buffer, a) == 0) {
          digitalWrite(LED, HIGH);
        } else {
          digitalWrite(LED, LOW);
        }
      }
    }


body:
Here is the loop() code from the SafeString_ReadCmdsTimed.ino example in the SafeString library available from the Arduino library manager.  It is non-blocking, i.e. no delays.

There is an extensive [tutorial and examples available for SafeStrings][1].
SafeStrings has built-in error checking and debugging.  SafeStrings provides the functionality of Strings without the memory fragmentation problems of dynamic memory allocation.

If you are reading from telnet there is also a processbackspaces() method in SafeStrings to handle terminal typing corrections.
The delimiters are whatever you would like.  The example handles Windows, Unix and Mac end-of-lines.

    char delimiters[] = " .,\r\n"; // space dot comma CR NL are cmd delimiters

    void loop() {
      if (input.read(Serial)) {  // read from Serial, returns true if at least one character was added to SafeString input
        input.debug("after read => ");
        timeout.start(TIMEOUT_MS); // restart a 0.1sec timer every time something is read
      }

      if (input.nextToken(token, delimiters)) { // process at most one token per loop does not return tokens longer than input.capacity()
        token.debug("after nextToken => ");

        if (token == startCmdStr) {
          running = true;  Serial.print(F("start at ")); Serial.println(loopCounter);

        } else if (token == stopCmdStr) {
          running = false; Serial.print(F("stop at ")); Serial.println(loopCounter);

        } else if (token == resetCmdStr) {
          loopCounter = 0; Serial.print(F("reset Counter:")); Serial.println(loopCounter);

        }// else  // not a valid cmd ignore
      }
      if (timeout.justFinished()) { // nothing received for 0.1secs, terminated last chars so token will be processed.
        input += delimiters[0]; // any delimiter will do
        SafeString::Output.print(F("Input timed out"));
      }
      // rest of code here is executed while the user typing in commands
      if (running) {
        loopCounter++;
        if ((loopCounter % 100000) == 0) {
          Serial.print(F("Counter:")); Serial.println(loopCounter);
        }
      }
    }

  [1]: https://www.forward.com.au/pfod/ArduinoProgramming/SafeString/index.html


message:
Ardunio Mega/ATmega2560: Using Port F or K for both analog inputs and digital outputs

On an ATmega2560, can ports have some pins used for analog inputs but others as digtial i/o? Specifically, I only need to use 3-5 analog inputs but have many digital inputs. I would like to use the remaining 3-5 pins as digital outputs if possible.

Additionally, does it make a difference if the port in question is Port F vs. Port K? For Port F, the datasheet seems to imply that all 8 of the pins are analog only if the ADC is enabled:

> Port F serves as analog inputs to the A/D Converter.
>
>Port F also serves as an 8-bit bi-directional I/O port, if the A/D Converter is not used.

For Port K, however, the datasheets port description does not have the distinction:
> Port K serves as analog inputs to the A/D Converter.
>
>Port K is a 8-bit bi-directional I/O port with internal pull-up resistors (selected for each bit).

It seems that this is definitely possible for the Arduino Uno/ATmega328P ADC port (except for the ADC6/7 pins for 32-pin form factors), but I can't seem to find anything confirming for the Arduino Mega/ATmega2560 or distinguishing between whether this is done on Port F or Port K

body:
> On an ATmega2560, can ports have some pins used for analog inputs but others as digtial i/o?

Yes, the ADC MUX controls the selection of the pin that is connected to the converter. This is independent of the digital pin control.

Cheers!

PS: See the Arduino core source code for further details on the ADC MUX control registers.


message:
Notoriously unstable ESP8266 MQTT-client

I am doing a project where an ESP8266 receives data from an Arduino Uno and publishes it via MQTT. After a random amount of time, it will stop sending data to my MQTT broker. It might be an hour, it might be a day or two.

It's set up to send data every second, and I made a debug output telling me the WiFi signal quality as well. Seems like that's not it.

I have tried making checks that will reconnect to MQTT if it looses connection, and that it resets itself if it looses WiFi connection. I'm out of ideas right now, any help appreciated!

Here's my MQTT reconnnect function
<!-- language-all: lang-cpp -->

    void reconnect() {
      // Loop until we're reconnected
      while (!client.connected()) {
        Serial.print("Attempting MQTT connection...");
        // Create a random client ID
        String clientId = "ESP8266Client-";
        clientId += String(random(0xffff), HEX);
        // Attempt to connect
        if (client.connect(clientId.c_str())) {
          Serial.println("connected");
          // Once connected, publish an announcement...
          client.publish("pressure/debug", "ESP8266: reconnected!");
        } else {
          Serial.print("failed, rc=");
          Serial.print(client.state());
          Serial.println(" try again in 5 seconds");
          // Wait 5 seconds before retrying
          delay(5000);
        }
      }
    }

and here's where it checks for WiFi

    void checkWifiConnection() {
      if (WiFi.status() != WL_CONNECTED)
      {
        int countdown = millis() + 15000;
        WiFi.mode(WIFI_STA);
        WiFi.begin(ssid, password);
        while (WiFi.status() != WL_CONNECTED) {
          if (countdown > millis()) {
          delay(500);
          Serial.println("Connecting to WiFi..");
          } else {
            Serial.println("Timed out! Restarting...");
            ESP.reset();
          }
      }
      }
    }

Both are run every loop.

The arduino sends the data like it's supposed to, and I've lowered the connection speed to 19200bps in order to ensure a more stable connection, using SoftwareSerial. Any more things i could monitor? I tried it with two different ESP8266MOD/"ESP07" boards with the same result.

Here's a debug output:

    09:13:05.039 -> unpub data 0/ AP:Akvasafe/ RSSI:-69 dB / Vcc:3519mV / free heap:49440 / fragmentation:1%

body:
I use adafruit mqtt library. After a few fixes, it is running very stable.

**Tips:**

1) Make sure you put subscribe line BEFORE connecting to mqtt (you can put it in setup and connect to mqtt in loop)

**Like:**

Setup: `mqtt.subscribe(&motor);`

Loop: `MQTT_connect();`

Yes, you can both publish and subscribe at the same time.

2) **IN THE LINE:** `Adafruit_MQTT_Client(server,port,user,pass)`

**CHANGE TO THIS:** `Adafruit_MQTT(server,port,clientid,user,pass)`

Use this with client id (MUST BE UNIQUE (EG: Different for all clients))
or your client will be kicked off when other client with same id connects.

3) **Convert value.lastread from char* to int :** `int val = atoi((char *)sensor.lastread);`

More about ESP8266 & ESP32 : http://github.com/ajaybnl


message:
Hand-held programmable device needed

Hopefully this question is not too off-topic for this board. I need a ready-made programmable hand-held device with an ethernet-connection. Something like an Arduino with batteries and display and some buttons in a box.
This is for my company so a complete ground-up assembly is too expensive and time-consuming in this case. Any hints to companies that produce something like this are welcome. And yes, I tried searching with different search-engines already. :-)
Thanks for your time!

body:
I have no opinion about this hardware (I don't own it) so please treat my answer as information only. When I was searching through web I found [M5Stack][1]

It looks like hardware made for IoT development.
It has a LCD and 3 buttons and think it can be programmed using ArduinoIDE.
It's designed that you can design any hardware you want and "stack" the device on top of it. Found if available to buy from China for below 30USD.

[![M5Stack parts][2]][2]

https://www.youtube.com/watch?v=U2es-l4z2Zg

  [1]: https://m5stack.com/
  [2]: https://i.stack.imgur.com/lwwsn.png


message:
Send ECG signal with NRF24L01 from Arduino to Raspberry Pi 3

I'm using nRF24L01 to send ECG samples from an Arduino to Raspberry Pi, the type of sample is double after denoising, and I stock them in a byte[8] to send 8 by 8 sample. When I print the sample before stockage that show the good results, but if I print data stored in the byte the signal show a lot of fluctuations. In Raspberry Pi, I can read correctly byte data like transmitted, but if I send them in a vector of double or int in reception (python) don't give the same frame transmitted.

    #include <IIRFilter.h>
    #include <FIRFilter.h>

    #include <SPI.h> // Call SPI Library
    #include <nRF24L01.h> // Call NRE Version Library
    #include <RF24.h> // RF24 Header File

    #define CE_PIN  9
    #define CSN_PIN 10
    const uint64_t pipe = 0xF0F0F0F0E1LL;
    RF24 radio(CE_PIN, CSN_PIN);

    const int ECG_samplefreq  = 200;//sampling frequcy
    const int DC_offset = 511;

    const double b_lp[] = {0.0026, 0.0155, 0.0388, 0.0517, 0.0388, 0.0155, 0.0026};
    const double a_lp[] = {1.0000, -2.3797, 2.9104, -2.0551, 0.8779, -0.2099, 0.0218};

    IIRFilter lp(b_lp, a_lp);
    unsigned int i = 0;

    void setup() {
      Serial.begin(9600);
      radio.begin();//Intializing NRF24L01 Module
      radio.setPALevel(RF24_PA_MAX);
      radio.setChannel(0x76);
      radio.openWritingPipe(pipe);// For Transmitting Operation, Must OpenWritingPipe
      radio.enableDynamicPayloads();
      radio.powerUp();
      pinMode(7, INPUT); // Setup for leads off detection LO +
      pinMode(8, INPUT); // Setup for leads off detection LO -

    }
    void loop() {
      const static unsigned long ECG_interval  = round(1e6 / ECG_samplefreq);  //sampling period = 5000 ms => 200 sample by 1 seconde
      static unsigned long ECG_prevmicros = micros();
      byte  s[8] = {0};

      if ((digitalRead(7) == 1) || (digitalRead(8) == 1)) {
        Serial.println('!');
      }

      else {
        for (int i = 0; i < 8; i++)
        {

          if (!Serial) {
            ECG_prevmicros = micros();
          }
          else if (micros() - ECG_prevmicros >= ECG_interval)
          {
            int value = analogRead(A5);
            double filtered = lp.filter( value - DC_offset);

            filtered = round( filtered + DC_offset);
            s[i] =  filtered
            Serial.println( s[i]);
            ECG_prevmicros += ECG_interval;

          }
        }
        radio.write(&s, sizeof(s) ); // sending in real time ECG sample. 8 sample by transmission . 8 => 4 oct of one sampe = 32 oct by transmission.

      }
    }

the problem thant i put in s[i] a double of four octs. im searching how can i send them whithout byte array, and receive the correctly. So thankful for your help

body:
I see multiple flaws in your code:

* `radio.write(&s, sizeof(s));` does not what you think it would. The correct statement would be `radio.write(s, sizeof(s));` without the ampersand.
* You are using `double`. Not using floating point numbers at all would be preferable.
* Your `s` is of type byte. Thus it only holds 8 bytes. So your floating point calculations are being truncated to the range [0, 255]. From your problem description this is not what you are trying to achieve, I think.


message:
How to Connect TFT LCD display with NodeMCU?

I am doing this project wherein I want to display some image on the LCD screen. I am having a problem with the connecting nodemcu with my TFT LCD screen. I cannot find any references. Does a TFT screen go well with a NodeMCU? if yes, please help

I tried taking refrence from this website but i ended up damaging my nodeMCU

http://nobrok.com/connecting-tft-lcd-touch-screen-with-nodemcu-esp8266/

Also attaching images of TFT display and my NodeMCU.
[![Here's my TFT screen (ILI9341 non touch screen)][1]][1]

[![NodeMCU][2]][2]

It would be great if you can help. Thanks :)

  [1]: https://i.stack.imgur.com/gmIOZ.jpg
  [2]: https://i.stack.imgur.com/OQ6mN.jpg

body:
That kind of TFT doesn't work well with the NodeMCU (or the ESP8266 in general).

Simply put: that TFT requires a lot of GPIO pins - 10 at an absolute bare minimum, but better if you have more available.  The ESP8266 doesn't have many IO pins - and some of them are very sensitive about what they can be connected to without affecting the boot process.

It is better to choose a TFT screen with an SPI interface, which uses far fewer pins - although is slower to refresh the screen data.

If you are careful with your GPIO selection it *may* be possible to work with that screen. There are no specific requirements for what pins need to be connected to where (as far as hardware functionality goes), so it's up to you to find the right combination that doesn't cripple the boot process (stay away from GPIOs 0, 2 and 15 if you can).


body:
According to its web site, the TFT module does have SPI interface. https://www.jixin.pro/product/717.html
The site is in Chinese though.