# Question
Title: Transmitting multiple values to an Arduino, and interpreting them with minimum delay
I am building an underwater robot, which can move up/down and forward/reverse, controlled by a Joystick.

The situation is like this :

A USB joystick is connected to a PC, the PC is connected to an Arduino via a tether cable (Ethernet), and the motors of the robot are connected to the Arduino.

The joystick I am using has two sticks, and I have decided to use one stick to control the up/down movement (actually, I'm using only one axis of that stick for this) and the second stick to control the left/right movement.

Whenever the user manipulates both sticks simultaneously (to achieve diagonal motion, for example), the joystick will send two signals, one after the other, one for each stick.

Keeping in mind the limited receiver buffer size of the Arduino, how do I program the Arduino so that it can understand the difference between the linear motion signal and the diagonal motion signal?

I am highly motivated to program this on my own. I just need an intuition for this.

A thought came to my mind is, to use the following strategy:

For my up/down stick value, I add a character such as `U`, followed by the integer joystick value, e.g. I send `U4` to go up at speed `4`. With some twitching, I can even send a down signal with the same preceding character `U`.

Similarly, for forward/backward, I send `F` to go forward/backward at speed `3`. And for diagonal, I send something like `T5` to go diagonally at speed `5`.

My concern with this is that I will transmit two characters from the PC to the Arduino. Will the Arduino be able to read these two characters, interpret them and act accordingly, without a noticeable lag? Or is there an other better way?

This also makes me wonder, how commercial robots (such as commercial drones) handle such situations?

The movements the robot will make need to be quick. There should not be "visible" lag, that is, the user should not feel that the robot is responding after a couple of seconds.

# Answer
> 1 votes
I don't know about commercial drones, however your 'protocol' seems to be quite efficient, as it uses 4 bytes to send 2 values (e.g. U3F5) for Up with speed 3 and Forward with speed 5.

Let's assume values from 0-7. Then you can send them both in 8 bits/one byte:

H H H H V V V V

Where H is the horizontal speed (from -8 (000) to +7 (111), in total 16 possible values. For the vertical speed you can do the same.

So within one byte you send both speeds (meaning also there is no lag). In case you need more accuracy, than send two bytes: one byte with horizontal and one byte with vertical speed. Depending on the sending/receiving speed I doubt there is any lag.

Even with your protocol I doubt there is a lag, but the above is more efficient.

I'm sure even more efficient algorithms can be created, probably by using the difference with the previous value (like sending delta values).

Another algorithm that can be created, assuming there is a big chance that only one of the two directions is changed (either horizontal or vertical is) and having a high accuracy

```
D V V V V V V V

```

Where D is the direction (0 = horizontal, 1 = vertical) and V is the value/speed (-64 to +63, 7 remaining bits).

---
Tags: arduino-uno, communication, ethernet-shield, joystick
---


# Question
Title: Failed HC-05 Bluetooth sketch upload - (port and board correct)
I'm running this project with HC-05 https://create.arduino.cc/projecthub/millerman4487/view-serial-monitor-over-bluetooth-fbb0e5 and I am getting connection error. I have ensured my port selected and board is accurate but no such luck. The Arduino uno is powered by 3.7v batt (output ~8v with reg) so it is simply just a battery connection and BT module, but when uploading the sketch, it fails. I am relatively new to arduino, and am not sure where to begin this debug.

I am using PC windows, and using a BT dongle receiver for connection (maybe this affects port comm?)

Thanks in advance

Here us the error message

```
Arduino: 1.8.13 (Windows Store 1.8.42.0) (Windows 10), Board: "Arduino Uno"

Sketch uses 1954 bytes (6%) of program storage space. Maximum is 32256 bytes.

Global variables use 250 bytes (12%) of dynamic memory, leaving 1798 bytes for local variables.
Maximum is 2048 bytes.

avrdude: stk500_recv(): programmer is not responding

avrdude: stk500_getsync() attempt 1 of 10: not in sync: resp=0x04

avrdude: stk500_recv(): programmer is not responding

avrdude: stk500_getsync() attempt 2 of 10: not in sync: resp=0x04

avrdude: stk500_recv(): programmer is not responding

avrdude: stk500_getsync() attempt 3 of 10: not in sync: resp=0x04

avrdude: stk500_recv(): programmer is not responding

avrdude: stk500_getsync() attempt 4 of 10: not in sync: resp=0x04

avrdude: stk500_recv(): programmer is not responding

avrdude: stk500_getsync() attempt 5 of 10: not in sync: resp=0x04

avrdude: stk500_recv(): programmer is not responding

avrdude: stk500_getsync() attempt 6 of 10: not in sync: resp=0x04

avrdude: stk500_recv(): programmer is not responding

Problem uploading to board.  See http://www.arduino.cc/en/Guide/Troubleshooting#upload for
suggestions.

avrdude: stk500_getsync() attempt 7 of 10: not in sync: resp=0x04

avrdude: stk500_recv(): programmer is not responding

avrdude: stk500_getsync() attempt 8 of 10: not in sync: resp=0x04

avrdude: stk500_recv(): programmer is not responding

avrdude: stk500_getsync() attempt 9 of 10: not in sync: resp=0x04

avrdude: stk500_recv(): programmer is not responding

avrdude: stk500_getsync() attempt 10 of 10: not in sync: resp=0x04

```

# Answer
> 1 votes
when uploading the code, did you ensure disconnecting the Rx, Tx pins from the Arduino? Coz this is a similar error you get when you upload code with your comm pins connected. Try uploading the code with no wires connected.

---
Tags: arduino-uno, bluetooth, hc-05
---


# Question
Title: Nano Every clone with ATMega4808 not recognized
I've bought an Arduino Nano Every clone/compatible (not a standard Nano V3) that uses an ATMega4808 instead of the ATMega4809 the official Nano Every uses. This rather insignificant change of chip is detected by the Arduino IDE (v. 1.8.13) which tells me that the chip is wrong when I select "Nano Every" from the boards list and try to upload a sketch. The seller (link to the product) does not answer to my help requests. Does anybody own one of these and knows how to make it run?

Below a photo of the board. Note the small difference in pinout (4 extra pin, D22, D23, D24 and UPDI)

# Answer
Probled solved, it turns out to be a Thinary Nano Every.

Instructions for installing on the Arduino IDE are on Github here: https://github.com/Thinary/ThinaryArduino
> 1 votes

---
Tags: avrdude, atmega
---


# Question
Title: "No I2C devices found" Arduino Nano Every
I was able to set up a Arduino Nano with an I2C board very easily, but the Arduino Nano Every is giving me a much harder time (my project required low profile).

Just to test, I stripped some wires, and looped them into the board, I'm not sure I want to solder on the pins as they may be too tall. Anyways, just trying to get a proof of concept going right now.

Here's how it's connected:

based on this pin diagram: https://i2.wp.com/rosmianto.com/wp-content/uploads/2019/05/Untitled-Diagram-4.png?fit=1506%2C1974&ssl=1

The screen lights up so I know the 5v and Ground connections work, but when I scan for I2C devices with i2c\_scanner, it sees no devices.

```
18:20:56.254 -> Scanning...
18:20:56.289 -> No I2C devices found
18:20:56.289 ->
18:21:01.265 -> Scanning...
18:21:01.265 -> No I2C devices found
18:21:01.300 ->

```

# Answer
Looping the wires through the board and not soldering them is probably your problem. That's not going to make a very good connection. You may get power and ground that way, but digital signals like I2C comms are going to see a LOT of noise.
> 2 votes

---
Tags: arduino-nano, i2c
---


# Question
Title: Error occurs when compiling ESP32 self-update firmware code
```
when i write this code in esp8266, it's work fine. but when i tried that code in esp32 with some changes,it shows error on compile time:

board which i use : DOIT ESP32 DevKit v1

```

error is:

```
In file included from C:\Users\Gabbar Singh\Documents\Arduino\ESP32_OTA\ESP32_OTA.ino:5:0:
C:\Users\Gabbar Singh\AppData\Local\Arduino15\packages\esp32\hardware\esp32\1.0.4\libraries\HTTPUpdate\src/HTTPUpdate.h:47:6: error: multiple definition of 'enum HTTPUpdateResult'
 enum HTTPUpdateResult {
      ^
In file included from C:\Users\Gabbar Singh\Documents\Arduino\ESP32_OTA\ESP32_OTA.ino:3:0:
C:\Users\Gabbar Singh\Documents\Arduino\libraries\ESP32httpUpdate\src/ESP32httpUpdate.h:59:6: note: previous definition here
 enum HTTPUpdateResult {
      ^
Multiple libraries were found for "WiFi.h"
 Used:C:\Users\GabbarSingh\AppData\Local\Arduino15\packages\esp32\hardware\esp32\1.0.4\libraries\WiFi
 Not used: C:\Program Files (x86)\Arduino\libraries\WiFi

```

and the last error is : exit status 1 Error compiling for board DOIT ESP32 DEVKIT V1.

```
Code:

#include <Update.h>
#include <WiFi.h>
#include <ESP32httpUpdate.h>
#include <WiFiClient.h>
#include <HTTPUpdate.h>
#include <HTTPClient.h>

#define LED_BUILTIN 2

const String FirmwareVer = {"1.4"};

#define URL_fw_Version "http://vadaliya2007.000webhostapp.com/atte/ota/version.txt"
#define URL_fw_Bin "http://vadaliya2007.000webhostapp.com/atte/ota/firmware.bin"
HTTPClient http;

const char* ssid = "Honor8X";
const char* password = "1414141414";

void FirmwareUpdate()
{
  http.begin(URL_fw_Version, "5b fb d1 d4 49 d3 0f a9 c6 40 03 34 ba e0 24 05 aa d2 e2 01"); // check version URL
  delay(100);
  int httpCode = http.GET();            // get data from version file
  delay(100);
  String payload;
  if (httpCode == HTTP_CODE_OK)         // if version received
  {
    payload = http.getString();  // save received version
    Serial.println(payload );
  }
  else
  {
    Serial.print("error in downloading version file:");
    Serial.println(httpCode);

  }

  http.end();
  if (httpCode == HTTP_CODE_OK)         // if version received
  {
    if (payload.equals(FirmwareVer) )
    {
      Serial.println("Device already on latest firmware version");
    }
    else
    {
      Serial.println("New firmware detected");
      WiFiClient client;

      // The line below is optional. It can be used to blink the LED on the board during flashing
      // The LED will be on during download of one buffer of data from the network. The LED will
      // be off during writing that buffer to flash
      // On a good connection the LED should flash regularly. On a bad connection the LED will be
      // on much longer than it will be off. Other pins than LED_BUILTIN may be used. The second
      // value is used to put the LED on. If the LED is on with HIGH, that value should be passed
      //ESPhttpUpdate.setLedPin(LED_BUILTIN, LOW);

      t_httpUpdate_return ret = ESPhttpUpdate.update(URL_fw_Bin, "", "5b fb d1 d4 49 d3 0f a9 c6 40 03 34 ba e0 24 05 aa d2 e2 01");

      switch (ret) {
        case HTTP_UPDATE_FAILED:
          Serial.printf("HTTP_UPDATE_FAILD Error (%d): %s\n", ESPhttpUpdate.getLastError(), ESPhttpUpdate.getLastErrorString().c_str());
          break;

        case HTTP_UPDATE_NO_UPDATES:
          Serial.println("HTTP_UPDATE_NO_UPDATES");
          break;

        case HTTP_UPDATE_OK:
          Serial.println("HTTP_UPDATE_OK");
          break;
      }
    }
  }
}

unsigned long previousMillis = 0;        // will store last time LED was updated
const long interval = 30000;

void repeatedCall() {
  unsigned long currentMillis = millis();
  if ((currentMillis - previousMillis) >= interval)
  {
    // save the last time you blinked the LED
    previousMillis = currentMillis;
    FirmwareUpdate();
  }
}

void setup()
{
  Serial.begin(115200);
  Serial.println("");
  Serial.println("Start");
  WiFi.mode(WIFI_STA);
  WiFi.begin(ssid, password);
  while (WiFi.status() != WL_CONNECTED)
  {
    Serial.print("O");
    delay(500);
  }
  Serial.println("Connected to WiFi");
  pinMode(LED_BUILTIN, OUTPUT);
}
void loop()
{
  digitalWrite(LED_BUILTIN, HIGH);   // turn the LED on (HIGH is the voltage level)
  delay(100);                       // wait for a second
  digitalWrite(LED_BUILTIN, LOW);    // turn the LED off by making the voltage LOW
  delay(100);                       // wait for a second
  repeatedCall();
}

```

# Answer
the error is i used two libraries esp32httpupdate and httpupdate, which both have same function so i remove the other one(httpupdate)... and now problem is solved.
> 1 votes

---
Tags: esp32
---


# Question
Title: Arduino Keyboard starts lower case (but it shouldn't)
So I flashed the KeyboardMessage example to my Arduino SS Micro ATmega32U4.

When I open an editor and push the button, I would assume the output to be

> Zou pressed the button XX times.

(The "Z" is because I use a German keyboard)

In some editors (Arduino IDE, LibreOffice) this assumption is fulfilled.

However, in several other editors (Linux Shell, gedit), **most of the times** the output is

> zou pressed the button 1 times.

starting with a lower case "z".

I use a Debian Testing computer. The only thing I changed in the sketch was the `buttonPin` as my button is soldered to pin 11.

I noticed, that this problem doesn't occur when the button is pressed a second time shortly after the first message. To investigate this, I coded a little sketch to find the threshold.

This is what I got (in gedit)

As line 8 shows, even after 70 millis, the upper case start is not reliable, however, somewhere after 250 millis, the error occurs every time.

My questions are:

1. What could be the cause for this issue?
2. How can it be fixed (if necessary, I also welcome a workaround)?

Please tell me if you need any additional information.

\[edit\] After slightly altering the script, I noticed, that the problem doesn't only occur on the start of a line, but also (although less often) later in the output. See lines 24, 31 and 52 for example

# Answer
I am not sure I have the answer to your problem, just a collection of observations that hopefully steer you in the right direction.

According to your nopaste link, when you send "ON", the first four keyboard events received by `xev` are: press(Shift\_L), press(O), release(Shift\_L), release(o). One may notice that there is no point in releasing the Shift key if it's going to be pressed again right away, but let's assume that simply holding Shift is not such a useful optimization. The detail that strikes me is that the last two events look backwards: you usually release the letter *before* releasing Shift. As a result of releasing Shift first, the release event for the O key reports lowercase "o" as a keysym. I tried this backward way of releasing the keys on a real keyboard, but both gnome-terminal and gedit correctly registered the uppercase letters.

Another detail apparent in the xev dump is that the two key presses (Shit and O) happen at the exact same time. Ditto for the corresponding key releases. Looking at the source of the Keyboard library, it appears that both key presses are sent to the PC as a single "key report". Same for the key releases. This is contrary to what a real keyboard does: actuations on the Shift keys are reported immediately, irrespective of whether other keys are actuated.

You may try to modify the Keyboard library so that the actuations on Shift are sent in their own reports. Maybe something like this (**warning**: completely untested):

```
diff --git a/src/Keyboard.cpp b/src/Keyboard.cpp
index 4a948f6..9fbf7b6 100644
--- a/src/Keyboard.cpp
+++ b/src/Keyboard.cpp
@@ -239,6 +239,7 @@ size_t Keyboard_::press(uint8_t k)
        }
        if (k & 0x80) {                     // it's a capital letter or other character reached with shift
            _keyReport.modifiers |= 0x02;   // the left shift modifier
+           sendReport(&_keyReport);        // send the shift key by itself
            k &= 0x7F;
        }
    }
@@ -270,6 +271,7 @@ size_t Keyboard_::press(uint8_t k)
 size_t Keyboard_::release(uint8_t k)
 {
    uint8_t i;
+   bool has_shift = false;
    if (k >= 136) {         // it's a non-printing key (not a modifier)
        k = k - 136;
    } else if (k >= 128) {  // it's a modifier key
@@ -281,7 +283,7 @@ size_t Keyboard_::release(uint8_t k)
            return 0;
        }
        if (k & 0x80) {                         // it's a capital letter or other character reached with shift
-           _keyReport.modifiers &= ~(0x02);    // the left shift modifier
+           has_shift = true;
            k &= 0x7F;
        }
    }
@@ -295,6 +297,10 @@ size_t Keyboard_::release(uint8_t k)
    }

    sendReport(&_keyReport);
+   if (has_shift) {
+       _keyReport.modifiers &= ~(0x02);    // the left shift modifier
+       sendReport(&_keyReport);            // release shift after releasing the letter
+   }
    return 1;
 }

```

Alternatively, as suggested by @jstola in a comment, you may try to press the Shift key by itself. Maybe you don't need to care about the key release, or about any character but the first one (as it is the only one that seems to cause problems). A minimal workaround to try would be:

```
Keyboard.press(KEY_LEFT_SHIFT);
Keyboard.println("ON");

```
> 1 votes

---
Tags: arduino-leonardo, keyboard, atmega32u4, hid
---


title: Branchless programing on arduino?

text:
# Question
Title: Branchless programing on arduino?
So I've been looking into branchless programming to speed up code and I'm curious as to how exactly Arduino (or rather atmega328) actually reads machine instructions. Does it have a memory cache or does it read every instruction from the flash memory?

From my understanding of branchless programming it speeds up the computation because the CPU does not have to jump inside the instructions and can read it sequentially, hence does not need to load in new instructions in case it has to jump to a location that's not loaded.

My question is, does this apply to the atmega328? If it reads every instruction straight from flash without using a cache then it shouldn't matter much if it has to jump in the instructions, right?

# Answer
> 4 votes
There is no cache, so you don't need to worry about that. All instructions are fetched direct from flash and executed straight away.

There is, though, a 2-stage pipeline. That means that in one clock cycle an instruction is fetched from flash, and in the next clock cycle it's executed - and while that is being executed the next instruction is being fetched ready.

That means that when a branch occurs, since the AVR uses a very very simplistic approach to branch prediction (i.e., it assumes the branch will not be taken and just loads the next instruction regardless), it has to discard the contents of the pipeline and start from scratch.

That's only a one clock penalty while it loads the newly-branched-to instruction, but it's still a penalty.

Cache is only needed when the CPU core runs faster than the memory can be accessed. Since the AVR only runs at up to 20MHz that is considerably slower than the flash can be accessed, so adding cache would be completely pointless. Other faster MCUs do use caching, such as the 200MHz PIC32MZ, since otherwise "wait states" would have to be introduced to slow the reading from flash down.

---
Tags: programming, sketch, memory
---


# Question
Title: How to save a state - make an arduino run a code only once/make aruduino bahave differently the next time he is on
Im building a arduino based bicycle speedometer. When the code starts the user picks his bike size (which I need to calculate the radius). Then I have a state finite machine where the user taps the button between speed, time and temperature. I need to put this circuit on a battery and it needs to be mounted on a bike. But every time you plug and unplug the battery, the code runs from the beginning again, which I don't want. So every time the user turns the speedometer off then on, he needs to pick his bike size again. Is it possible to save the size he has picked so that the next time he turns it on, it doesn't come across.

So - user has his speedometer, turns it on, picks the bike size, turns it off, then sometime later turns it back on and the part for picking the bike size doesn't show up, it simply "knows" remembers what the user picked last time.

I don't know how could that work, would the Arduino run the certain code only once or is there a function for "the next time Arduino has electricity behave like this".

# Answer
> 6 votes
As one of the comments said, you will need to use the EEPROM library. When you save a variable in your code (e.g. `int test = 10;`) the variable along with its value gets stored in the RAM. The EEPROM is a piece of harddisk on your arduino that will remember its value when you power off your arduino.

If you implement a power-off button, simply save the state (or in your case, the wheel size) in EEPROM whenever the user inputs it. The next time you power up, you can check if there is a previous value in EEPROM and continue with that value if it exists. Otherwise ask the user for their wheel size.

You might want to implement a reset-button as well, to reset whenever you change bike or wheels. Look up a code example of EEPROM, as there are a lot online.

---
Tags: arduino-uno
---


# Question
Title: I want to stream audio from an Arduino to a device on the wifi
I only started learning Arduino recently. This is my first project.

So the idea for the project is that there will be an Arduino board(Ideally an Uno but I don't know if another board would be better) and when you hold a button down it will transmit what you are saying to a device on the wifi. I know I will have to get a WiFi module and like a microphone and button, so can you help me figure out just the gist of how the project will go and what parts I should get.

Thanks!

# Answer
> 4 votes
An Arduino can do this, but this is a very advanced problem on an Arduino. It sounds like perhaps you need something more plug-and-play. In that case, buy a Raspberry Pi 4 starter kit and a USB microphone, and start working on the problem from there. The Raspberry Pi 4 is a Linux computer, so everything you do will be writing scripts or programs (in any language: it's just a regular computer, so use Python, C, C++, Java, bash, whatever you want) to run on its Raspberry Pi OS (formerly called Raspbian) Linux operating system.

If you go this route, you'll want to ask your questions on the Raspberry Pi Stack Exchange as well.

Keep in mind the question you asked is too broad. You are generally expected to do your own background research and then ask more specific questions, demonstrating what you've already tried.

Getting an Arduino to send out microphone data is, like I said, a very advanced subject and project (think: professional level / expert hobby level) unless you can Google and find pre-made libraries and how-tos on the subject.

Essentially, for the Arduino Uno route you'd need to do some fancy high-rate ADC sampling with a modified ADC clock rate in a special ADC mode which takes repeated samples and then interrupts your code when a sample is ready, rather than just doing normal `analogRead()` since that is both blocking/polling-based which wastes clock cycles and creates sample jitter which causes audio distortion, and then you'd need to send this data via some Wifi shield (add-on board) or an ESP8266 or something, or via some other technology (wired or wireless) to a computer to pass it on to the internet. This may involve binary packetization/bit-packing, error checking, buffering, etc., all of which is its own special skill to acquire.

Some of my projects have taken me 3+ years to complete them, since I began complicated projects as a beginner. This is one of those multi-year type projects for a beginner for sure.

(Heck, if you give me two LEDs and two resistors and an Arduino Nano, with those items *alone*, I can send you on your way to work 8 hrs a day for 3 months straight on projects. It's easy to under-estimate the complexity of something until you're neck-deep in it.)

Update: if you want to go the Arduino route, here's some tips to get you on a search route more likely to get you to a solution faster. Again, no doubt an Arduino Uno *can* do this. It for sure can. But, a faster Arduino can do it easier and better. So:

1. **Google** search for projects on Adafruit which may do this. Ex: Google search for "adafruit stream audio". Their tutorials are 2nd to none--the best in the world--and their products top-notch.
2. Search for projects on Sparkfun which may do this. Ex: Google search for "sparkfun stream audio". They also are excellent and have world-class tutorials.
3. Search for projects which do this with a Teensy, Zero, Due, or other high-speed 32-bit microcontroller, instead of an Uno. Audio processing is more difficult for a slower 8-bit Uno than for any of those 3 Arduino/Arduino-compatible devices.
4. Also look on Instructables.com for tutorials and help.
5. One more thought: Google search for "atmega328 stream audio to wifi" (an Uno uses the ATmega328 microcontroller, so that's a good search term to use)

---

Update: also take a look at this tutorial by GreatScott (who is also super awesome) (https://www.instructables.com/id/Make-Your-Own-Spy-Bug-Arduino-Voice-Recorder/), which uses this AVR-based (for ATmega328: Arduino Uno, Nano, Pro Mini, etc., or ATmega2560: Mega) advanced audio library for both recording and playing back audio. See:

1. https://github.com/TMRh20/TMRpcm
    1. Recording Audio
    2. Audio streaming over NRF24L01+ radio link

# Answer
> 3 votes
You can use a ESP32 with built-in WiFi and Bluetooth. Record a wave-File to a SD-card using this library, send it over Blutooth and play it on the PC with a little script.

---
Tags: wifi, audio
---


# Question
Title: Convert character to Integer while leaving encoded
I have two characters, that I get by Bluetooth.
```
char a = SerialBT.read();
char b = SerialBT.read();

```

According to the Arduino Reference, decoded data stored in a char gets encoded to ASCII text.
I want to combine them in an Intenger, but the following methods don't work:

```
int c = a + b;

```

```
int c = (int)a + (int)b;

```

```
int c = (a - 48) + (b - 48);

```

and

```
String c;
c.setCharAt(0, a);
c.setCharAt(1, b);

```

Thank you

# Answer
OK, so after the lengthy requests for clarifications, it appears that you are receiving a number in ASCII decimal (`"12"`) and want to parse it into an integer.

You may use the `parseInt()` method of the serial object, like:

```
int c = SerialBT.parseInt();

```

This can however make you program quite slow, as `parseInt()` uses a timeout to know when to stop expecting more digits.

If you already have read the bytes, you can combine them with simple arithmetics:

```
int c = 10 * (a - '0') + (b - '0');

```

Note that `'0'` is the same as 48, only it makes more explicit the intent of your code.
> 2 votes

# Answer
Use an AND mask to convert the character to a digit:

```
int c = 10 * (a & 0x0F) + (b & 0x0F);

```

When ASCII was invented, the digits `0` to `9` were encoded in hexadecimal as `30` to `39` to enable easy conversion to/from digits and characters.

To convert a digit to ASCII, OR the byte with 0x30:

```
byte digit = 5;
char character = digit | 0x30;

```

To convert a character to a digit, AND it with 0x0F:

```
char character = '5';
byte digit = character & 0x0F;

```

These logical operators are faster and more efficient than mathematical operations + and -.
> 1 votes

---
Tags: bluetooth, variables, convert
---


# Question
Title: MD_Parola display issue when constructing test
I'm using ESP8266 and 4 dot Matrix Tiles, to display clock ( updates using NTP and WiFi ). Everything is working well, but only when I'm constructing text using a `const char*` type.

But, since I wish to construct text as `sprintf(temp, "12:00");` or `char temp[20]="12:00\n;` creates gibberish text.

```
MD_Parola dotMatrix = MD_Parola(HARDWARE_TYPE, CS_PIN, MAX_DEVICES);

void updateTime()
{
  char clk[10];
  char dat[10];
  char temp[10];
  sprintf(temp, "12:00"); // <---- this ways failes
  const char *t = "12:00"; // <---- this way succeeds
  dotMatrix.displayText(t, PA_CENTER, 0, 0, PA_PRINT, PA_NO_EFFECT);
}

```

link to library

Appreciate explanation how to construct text not as `const char*`

# Answer
> 1 votes
The library documentation states:

> The library does not allocate any memory for the text message

That suggests, that the buffer has to be valid beyond the execution of the `displayText()` function. But as you declare it inside of your `updateTime()` function, it the buffer gets out of scope, when exiting that function. The memory space can then be reused by the rest of the program. At that point the library will still have the pointer to the old location, though that pointer can now be considered invalid. Thus you are just reading, what the compiler decided to place in that memory location.

To solve that, you need to keep the buffer variable in scope. You can do this by moving the declaration to the global scope.

---
Tags: display
---


# Question
Title: How can I connect an arduino to a raspberry pi via an HC 05 bluetooth module and transmit data?
I am currently undertaking a project where I am attempting to build a bluetooth thermometer using an arduino. I have the temperature sensor working and returning temperature readings via a usb connection to the serial monitor in the Arduino IDE using the following code.

```
#include <OneWire.h>
#include <DallasTemperature.h>
#include "Timer.h"

Timer t;

// Data wire is plugged into pin 10 on the Arduino
#define ONE_WIRE_BUS 10

// Setup a oneWire instance to communicate with any OneWire devices
OneWire oneWire(ONE_WIRE_BUS);

DallasTemperature sensors(&oneWire);

DeviceAddress insideThermometer = { 0x28, 0x94, 0xE2, 0xDF, 0x02, 0x00, 0x00, 0xFE };

void setup(void)
{
  // start serial port
  Serial.begin(9600);
  // Start up the library
  sensors.begin();
  // set the resolution to 10 bit (good enough?)
  sensors.setResolution(insideThermometer, 10);
  int tickEvent = t.every(3000,doTempReading);

}

void loop()
{
    t.update();
}

void printTemperature(DeviceAddress deviceAddress)
{
  float tempC = sensors.getTempC(deviceAddress);
  if (tempC == -127.00) {
    Serial.print("Error getting temperature");
  } else {
    Serial.print("C: ");
    Serial.print(tempC);
  }
}

void doTempReading()
{
  delay(2000);
  Serial.print("Getting temperatures...\n\r");
  sensors.requestTemperatures();

  Serial.print("Inside temperature is: ");
  printTemperature(insideThermometer);
  Serial.print("\n\r");
}

```

I now want to try and transmit the readings via a bluetooth connection using the HC 05 module to a raspberry pi which will record the data.

I have done a lot of research and tried several different techniques and can't understand how to go about it.

What mode does the HC 05 need to be in? (Command AT/slave/data/etc.) How should it be wired (I have found several different methods using various resistors and capacitors and unsure which to follow). How should I pair it with the Raspberry pi?

Thanks in advance for any help.

# Answer
> 1 votes
I know this is old but to help out newcomers:

Here's a place you can begin https://create.arduino.cc/projecthub/millerman4487/view-serial-monitor-over-bluetooth-fbb0e5

The wiring depends on which arduino board you are using and the model of your HC-05 BT module. mine uses 4 pins VCC (5v) GND (ground) TX --\> TX and RX --\> RX

You should be able to google the wiring for your module, and connect to the raspberry pi after you install bluetooth on raspberry pi

```
sudo apt-get install bluetooth bluez blueman

sudo reboot

```

Navigate to new bluetooth interface in menu bar through

* preferences
* bluetooth

Add new device, turn arduino on with BT module plugged in and make sure your HC-05 module is blinking red, and you should see a pair connection named HC-05 on raspberry pi. Password is 1234

---
Tags: bluetooth, hc-05, raspberrypi
---


# Question
Title: Wrong documentation for Mega2560 SPI Pins?
This page https://store.arduino.cc/usa/mega-2560-r3 contains an image under the Documentation section which shows digital pins 10 to 13 with labels SS, MOSI, MISO, and SCK.

**EDIT:** The documentation page has since been updated with the correct pin assignment as discussed below. The image has been removed to stop it from showing up in "mega SPI pinout" searches and continuing to spread wrong information.

However, this page says that those are at pins 50 to 53 https://www.arduino.cc/en/reference/SPI.

Which page is correct?

# Answer
> 5 votes
The image is incorrect, unfortunately.

The SPI pins are below:

```
PB0 - #SS
PB1 - SCK
PB2 - MOSI
PB3 - MISO

```

---
Tags: arduino-mega, spi
---


# Question
Title: The analog read is not giving the correct waveform as that of an oscilloscope
I have code that fetches analog input values from terminals A0, A1 and A2 of an Arduino Mega 2560. When I plot the data, it does not give the desired waveform.

The desired waveform is also measured with a the digital storage oscilloscope.

I was thinking to make use of an Arduino Mega 2560 as an oscilloscope that can have 16 channels, because the DSO has only 4 and for a project, I urgently need 16 channels. Would be great if the community people suggest something.

Below is the desired data from the oscilloscope that is measured in parallel to avoid any confusion about the circuit.

```
%This is a script that will plot Arduino analogRead values in real time
%Modified from http://billwaa.wordpress.com/2013/07/10/matlab-real-time-serial-data-logger/
%The code from that site takes data from Serial

clear all
close all
clc

%User Defined Properties
a = arduino('Com5')             % define the Arduino Communication port
arduino=serial('COM5','BaudRate',9600);
s1 = serial('COM5');                                                       % Define here YOUR serial port
s1.BaudRate=9600;

plotTitle = 'Arduino Data Log';  % plot title
xLabel = 'Time (s)';     % x-axis label
yLabel = 'Voltage (V)';      % y-axis label
legend1 = 'Voltage 1'
legend2 = 'Voltage 2'
legend3 = 'Voltage 3'
yMax  = 5                           %y Maximum Value
yMin  = 0                       %y minimum Value
plotGrid = 'on';                 % 'off' to turn off grid
min = 0;                         % set y-min
max = 5;                        % set y-max
delay = .01;                     % make sure sample faster than resolution

%Define Function Variables
time = 0;
data = 0;
data1 = 0;
data2 = 0;
count = 0;

%Set up Plot
plotGraph = plot(time,data,'-r' )  % every AnalogRead needs to be on its own Plotgraph
hold on                            %hold on makes sure all of the channels are plotted
plotGraph1 = plot(time,data1,'-b')
plotGraph2 = plot(time, data2,'-g' )
title(plotTitle,'FontSize',15);
xlabel(xLabel,'FontSize',15);
ylabel(yLabel,'FontSize',15);
legend(legend1,legend2,legend3)
axis([yMin yMax min max]);
grid(plotGrid);

tic

while ishandle(plotGraph) %Loop when Plot is Active will run until plot is closed

%          dat = readVoltage(a,'A0')* 0.48875855327; %Data from the arduino
%          dat1 = readVoltage(a,'A1')* 0.48875855327;
%          dat2 = readVoltage(a,'A2')* 0.48875855327;

         dat = readVoltage(a,'A0')* 1; %Data from the arduino
         dat1 = readVoltage(a,'A1')* 1;
         dat2 = readVoltage(a,'A2')*1;

         count = count + 1;
         time(count) = toc;

         data(count) = dat(1);
         data1(count) = dat1(1)
         data2(count) = dat2(1)

         %This is the magic code
         %Using plot will slow down the sampling time.. At times to over 20
         %seconds per sample!
         set(plotGraph,'XData',time,'YData',data);
         set(plotGraph1,'XData',time,'YData',data1);
         set(plotGraph2,'XData',time,'YData',data2);

          axis([0 time(count) min max]);

          %Update the graph
          %pause(delay);
  end

delete(a);

disp('Plot Closed and arduino object has been deleted');`

```

# Answer
Your sampling rate is far too low for the signals you are looking at; you're not getting enough data points for drawing something that looks like the original signal.

The Arduino library's `analogRead()`, while slow, can do better, up to about 9000 samples/s; the ADC in the atmega2560 in free-running mode can do about 75000 samples/s at 8 bits resolution. This would require programming it at the register level.

There is only one ADC, so if you want 16 channels, this leaves about 4700 samples/s for each channel. In that configuration, however, the first measurements aren't valid and the second ones should be used, further reducing the sample rate per channel to about 2300 samples/s.

With a perfect reconstruction filter, this would limit you to measuring signals up to only 1150 Hz.

All this doesn't even consider the time it takes to store or transmit the results.

So, an Arduino Mega 2560 will not do for making a usable 16-channel oscilloscope for your signals; it's not even close.
> 3 votes

---
Tags: arduino-mega, analogread, oscillator-clock, matlab, analogreadresolution
---


# Question
Title: What is the proper wiring for relay module?
I want to know the recommended wiring for relay. I am setting it up as NO.

1. Where should I connect the relay, the hot wire or the ground wire?
2. Where should I connect the wire going to bulb, NO or C pins of relay? Where should I connect the wire going to AC, NO or C?

# Answer
> 1 votes
A relay is a simple switch controlled by an electromagnet coil. The "NO" (normally open) side is off until you apply power to the coil. The "NC" (Normally closed) side is on until you supply power to the coil, at which point it turns off. Switches don't have polarity. If you connect the common into one part of a circuit and the "NO" side into the other, it doesn't matter which goes where.

## Edit:

As another poster pointed out, you **should** wire the relay so it switches the hot leg from the plug, not the neutral (Assuming you're in the US or another country with polarized plugs.) That is much safer, since it means when the relay is off, the lamp is only connected to the neutral line. If, instead, you wire the relay to switch the neutral leg then the lamp will ALWAYS be connected to hot, and if somebody touches the wires they could get a shock.

## Important:

What **does** matter is how you power the relay. If you try to drive a simple relay directly from a logic pin, it will likely damage or destroy the Arduino.

If you're using a "digital" relay that takes a constant 5V source, and a logic level control, such relays have built in transistors and protection diodes that prevent the relay coil from destroying solid state electronics.

If you're using a simple relay, you'll need an appropriate transistor to boost the current to the coil, as well as a "flyback diode" to protect the transistor from back-EMF when the coil is disconnected.

# Answer
> 0 votes
**Connect the bulb to the NO pin of the relay.**

Image source from: https://ncd.io/relay-logic/

---
Tags: pins, relay
---


# Question
Title: How to save data in arduino when it's power goes off
I am doing a project 'arduino based switch operation'. Here the user needs to set a time to turn on relay and set time to turn it off. The problem is that I want to supply power to arduino using adapter connected to the ac supply (where the relay will also be connected). When the on time is set and if power goes off for some time then this system doesn't work. I want to save the data in arduino so that it will retain the data if power comes back.. So that my relay is operated on time.. How to do it guys???

# Answer
> 1 votes
Look up EEPROM. it is a memory that saves content even though power is off.

You can write data in EEPROM and when power comes back read it back.

there are safe ways to write in EEPROM without corrupting it.

# Answer
> 0 votes
Beside Georgi's answer, I would like to tell you some details.

## First :

a microcontroller **can** have a built-in EEPROM like the ATMega328 inside an Arduino UNO/Nano/mini, if not you would need to attach an external one, it can have may interfaces like SPI or IIC etc...

## Second :

an EEPROM can hold only a specified amount of data, it can be 512byte like one on the ATMega328 microcontrollers, it can be only 64byte on others.

## Third :

an EEPROM have **addresses** so for example in 8-bit EEPROM one address can hold only 8bits so values from (0-255) like on the ATMega328

## Fourth : how to use it

In the beginning of your code you should first include the eeprom library

```
#include <EEPROM.h>

```

Then you would for example assign value "24" to one of the address on the EEPROM let's say address "1"

So you will use

```
EEPROM.write(1,24);

```

Of course you can power off you board and repower it again and that particular address will have the assigned 8-bit value "24".

To read back

```
EEPROM.read(24);

```

I hope that might help you or anyone else.

And as a side note an EEPROM have defined write and read cycles ~10000 maybe ~100000 after that amount it May not work.

Original documentation : here

# Answer
> 0 votes
You Can do that by using RTC (Real Time Clock Module ) in your project.

---
Tags: power, timers, memory
---


# Question
Title: I want a bar type display for my Arduino Project
I am trying to make a smart table project. But I have stumbled upon one problem, that is I don't know which display should I use. I need a display that has roughly aspect ratio of 2:1 but also has a relatively high pixel density. I have purchased a 2.42 inch display based on SSD1309 but the display is way too pixelated for my use. Do you have any display recommendations for me?

This is the display that I have bought:

The display I am trying to achieve is like this:

It looked like the display that I'm trying to achieve uses a custom made display. Is there anyway I can achieve that kind of look (at least similar in quality) with displays on the market?

# Answer
As Majenko already stated, the second image shows a custom display. It is not pixelated, because each shown element/symbol has it's own element in the LCD. When you have one of these displays, you might be able to reuse it for your project, but that is advanced.

In the case of pixel based displays with a significantly higher resolution than the standard SSD1309 driven LCD or OLED displays, you are mostly out of luck. There might be fitting products, though they most likely will be expensive and are not as easy to drive, as the standard ones. AVR based Arduinos, like Uno, Nano or Mega, are also not really good for driving high res displays.

The way to go depends on your exact requirements.

* You could - as Majenko suggested - ditch the Arduino and use an old smartphone. If you need more control over the smartphone for your project, than the standard Andriod gives you, you could install an open source OS on the phone.
* You could move to a Single Board Computer, like the Raspberry Pi Zero, and buy a display for it. There are many displays for Raspberry Pis, that should have enough resolution. Though most of them are larger than a normal smartphone display.
> 3 votes

---
Tags: arduino-mega, lcd, display, tft, oled
---


title: What's wrong with my codes/

text:
# Question
Title: What's wrong with my codes/
My teacher gave us a performance output about doing a dancing christmas lights in tinkercad. But I don't know what to do about the codes. He left an instruction to us about what to do. I follow it but the tinkercad keep telling that...

```
Sorry, it seems like your code has some errors.
Close
 In function 'void setup()':
13:5: error: a function-definition is not allowed here before '{' token
21:7: error: a function-definition is not allowed here before '{' token
41:61: error: expected '}' at end of input
41:61: error: expected '}' at end of input
41:61: error: expected '}' at end of input
 exit status 1

```

**And here's the code that I've entered...**

```
int ledPins[]={3,4,5,6,7,8,9,10,11,12};
void setup()
{
  for(int i =0; i <11; i++)
  {
    pinMode(ledPins[i],OUTPUT);
}
  {
  void setup()
    {
     for (int i=0; i <11; i++)
     {
       pinMode(ledPins[i],OUTPUT);
     }
  }
    {
      void loop()
      {
        int i = 0;
        while (i<10)

        {
          {
            digitalWrite(ledPins{i],HIGH);
            delay(100);
            digitalWrite(ledPins[i],LOW);
            i++;
                                }
                         }
                         i = 10;
                         while (i >0
                                {
                                  digitalWrite(ledPins[i],HIGH;
                                               delay(100);
                                               digitalWrite(ledPins[i],LOW;
                                                            i--;
                                                            }
                                                            }

```

And here's the instruction of my teaher for the codes...

6. Initialize variables Use array to initialize variables. Set ledPin as the name of the variable and initialize the Arduino pins that you’re going to use. Never forget to end each statement with semicolon

7. Set all pin to output Use function void setup () Create a for () loop for array manipulation. Initialize the for loop with i=0; since we will start the dancing lights with all LEDs turned off. Initialize the condition i\<11; since we need to turn on the 10 LEDs.

Set the increment to i++ because we need to iterate until it reaches the last LED. Configure pin using pinMode(). Place a curly bracket before and after the for loop and pinMode(). 8. Create a loop Use function void loop(). Create a variable, i = 0. Use while() for continuous looping First while() is used to run your light from right to left.

Second while() is used to run your light from left to right. Place a curly bracket before and after your statement block Never forget to end each statement with semicolon

# Answer
> 1 votes
I changed it, so it at least compiles.

```
int ledPins[]={3,4,5,6,7,8,9,10,11,12};
void setup()
{
  for(int i=0; i < 11; i++)
  {
    pinMode(ledPins[i],OUTPUT);
  }
}

void loop()
{
  int i = 0;
  while (i < 10)
  {
    digitalWrite(ledPins[i],HIGH);
    delay(100);
    digitalWrite(ledPins[i],LOW);
    i++;
  }
  i = 10;
  while (i > 0)
  {
    digitalWrite(ledPins[i],HIGH);
    delay(100);
    digitalWrite(ledPins[i],LOW);
    i--;
  }
}

```

---
Tags: arduino-uno
---


# Question
Title: Need help: Cast from 'char*' to 'uint8_t {aka unsigned char}' loses precision [-fpermissive]
I'm trying to convert the string that I receive from the Websocket to uint8\_t that I can copy to the data bytes of CAN protocol frame. I'm using an ESP32 chip and programming it on an Arduino IDE. The string that it receives from the websocket is "0322F12155555555".

```
#include <WiFi.h>
#include <SPIFFS.h>
#include <ESPAsyncWebServer.h>
#include <WebSocketsServer.h>
#include <esp32_can.h>
#include <SPI.h>
#include <string.h>

uint8_t payload1;
char payload2[100];
...
AsyncWebServer server(80);
WebSocketsServer webSocket = WebSocketsServer(1337);
...
// Callback: receiving any WebSocket message
void onWebSocketEvent(uint8_t client_num,
                      WStype_t type,
                      uint8_t * payload,
                      size_t length) {
...
      Serial.printf("[%u] Received text: %s\n", client_num, payload);
      strcpy(payload2, (const char*)payload);
      payload1 = (uint8_t)(payload2);
...

```

Error:

```
error: cast from 'char*' to 'uint8_t {aka unsigned char}' loses precision [-fpermissive]
       payload1 = (uint8_t)(payload2);
                                    ^

```

I'm segmenting the data into an array later, but I'm not confident that my cast is correct. Can someone please help with this? Thanks

-- Keith

# Answer
You can't just cast a string to a numeric type - C just doesn't work that way. What you're actually casting is the *address in memory* that the string resides at.

Instead you need to take the *content* of the string and interpret it.

For instance, you might take each pair of characters and combine them into a HEX value in a string that you then interpret as a number. That could be done a number of ways.

For example:

```
char temp[3]; // Temporary space for the conversion string
// Copy two characters into the temporary string
temp[0] = payload[0];
temp[1] = payload[1];
// and terminate the string properly
temp[2] = 0;
// Convert the string using base 16
uint8_t val = strtol(temp, NULL, 16);

```

In your example string you have 16 characters, which would be 8 bytes of data. So you could put it in a loop:

```
char temp[3]; // Temporary space for the conversion string
uint8_t vals[8]; // Array to store your values

// Iterate over the values
for (int i = 0; i < 8; i++) {
    // Copy two characters into the temporary string
    temp[0] = payload[i * 2];
    temp[1] = payload[i * 2 + 1];
    // and terminate the string properly
    temp[2] = 0;
    // Convert the string using base 16
    vals[i] = strtol(temp, NULL, 16);
}

```

Of course there are "lighter" ways of doing it that don't involve an intermediate string or the `strtol()` function. For example I often use this little function:

```
uint8_t h2d(char hex) {
    if(hex > 0x39) hex -= 7; // adjust for hex letters upper or lower case
    return(hex & 0xf);
}

```

That takes a single character and converts it from hex to decimal. So you can combine that with bit shifting and OR to create a byte from two characters:

```
val = h2d(payload[0]) << 4 | h2d(payload[1]);

```

In your loop that would look like:

```
for (int i = 0; i < 8; i++) {
    // Convert the string using base 16
    vals[i] = h2d(payload[i * 2]) << 4 | h2d(payload[i * 2 + 1]);
}

```
> 2 votes

---
Tags: arduino-ide, c, esp32, data-type
---


# Question
Title: Input Capture with Sleep Enabled on ATM32u4 board only works every second reading in SLEEP mode
**In short:** I have an Input Capture code and a Power-Saving code combined into one program. Both are adapted from Nick Gammon's examples that work fine independently. When I combined them into one code it only reads the data every other time a **single pulse** is sent to be captured every 20 seconds. The board sleeps during one idle cycle between the 20 second readings, then wakes up but misses the first reading, and then it stays awake during the next idle cycle and reads the pulse correctly at the 40 second mark for the second reading. And repeats. The references of these two Nick Gammon codes are listed in the program.

**Details:** Adafruit BlueFruit Feather 32u4 w/nrf51 in the Arduino 1.8.10 IDE. Using Nick Gammon's example for Input Capture an external incoming pulse of around 800 us (micro sec) long pulse is being measured by (ICP3) Input Capture #3 (rewritten from ICP1) on Pin D13 (PC7) (removed the LED). Works good.

Then I had a separate program that puts the board into deep-sleep and using INT0 (D3) to wake it up with an external interrupt signal. Since I was not able to figure out how to use the Input Capture as an ISR Interrupt to wake up the board, I ran the same external pulse signal also to the D3 (INT0) pin. So when the pulse hits both D3 (INT0) and D13 (ICP3) at the same time, and D3 wakes up the board via INT0 and then the ICP3 can capture the pulse and measure it. Then right after that, or several seconds later, can go back to sleep until the next pulse arrives on D13 (ICP3). I spaced the external 800us single pulses 20 seconds apart to make it easier to diagnose. If I remove the line that places the board into sleep "sleep\_cpu ();" I get a nice single-shot signal pulse measurement every 20 seconds. Since I am not using the USB-detach and reconnect feature, after the board goes to sleep it disconnects, but I am monitoring the power usage via a Fluke mA meter and I can see when it sleep and when it wakes up, and also monitoring the external pulse going to D13 (ICP3) and D3 (INT0) on the Oscope.

Notes: The Input Capture is listed under the Interrupts, but at a much lower priority then INTo or INT1. I do not need an active USB during the readings or sleep, because using BLE to send the data. The code I posted has the BLE portion removed the make it simpler to troubleshoot. The 800us external single-shot pulse is rock solid I have it showing on the Oscope, at the proper magnitude (0 to 3.3V) and intervals. I am trying to have the CPU sleep between readings. Can be right after the reading or a few seconds later. Interrupts have to be alive and ready to capture in case the 20 seconds becomes 1 or 2 seconds intervals (in real life).

```
// Time the interval between two consecutive pulses.Frequency timer using input //capture unit #3 on 32u4
// Author: Nick Gammon
// Date: 31 August 2013  http://www.gammon.com.au/timers
//  References: here:  http://www.gammon.com.au/forum/?id=11504&reply=12#reply12    //and  here:  https://www.gammon.com.au/power Sketch J
// Info here: http://gammon.com.au/interrupts
//Freq (Hz)     Per (µs)
// 8,000,000*   0.125us  or 125ns per clock tick at 8mghz

#include "LowPower.h"
//part of work around for BOSD missing functionality in 32u4.
//Not needed for 328p MCUs for sleep.

#include <avr/sleep.h>
#include <avr/power.h>
#include <avr/interrupt.h>
#include "avr/io.h"
#include <math.h>
#include <Arduino.h>

// Input: Pin D13 (PC7, ICP3) adafruit 32u  which is Timer3 Capture Input pin ,   //removed D13 LED by cutting trace or by removing resistor before LED13

const int wakeUpPin = 3;
volatile boolean first;
volatile boolean triggered;
volatile unsigned long overflowCount;
volatile unsigned long startTime;
volatile unsigned long finishTime;
volatile unsigned long elapsedTime;

//////START: ISR TIMER/COUNTER PULSE ROUTINE ON D13 INPUT-CAPTURE #3 on 32u4 ////
//https://www.nongnu.org/avr-libc/user-manual/group__avr__interrupts.html   //http://medesign.seas.upenn.edu/index.php/Guides/MaEvArM-timer3

// timer overflows (every 65536 counts)
ISR (TIMER3_OVF_vect) //1 3

{
        overflowCount++;
}  // end of TIMER3_OVF_vect

ISR (TIMER3_CAPT_vect)   // 1 3
  {
       // cancel sleep as a precaution  (added here from Power Save)
      sleep_disable();

   // grab counter value before it changes any more
  unsigned int timer3CounterValue;
  timer3CounterValue = ICR3;
// see datasheet, page 117 (accessing 16-bit registers)
  unsigned long overflowCopy = overflowCount;

  // if just missed an overflow
  if ((TIFR3 & bit (TOV3)) && timer3CounterValue < 0x7FFF)  // 1 3     //http://medesign.seas.upenn.edu/index.php/Guides/MaEvArM-timer3
    overflowCopy++;

  // wait until we noticed last one
  if (triggered)
    return;

  if (first)
    {
    startTime = (overflowCopy << 16) + timer3CounterValue;
    first = false;
    return;
    }

  finishTime = (overflowCopy << 16) + timer3CounterValue;
  triggered = true;
  TIMSK3 = 0;    // no more interrupts for now   // 1 3    //http://medesign.seas.upenn.edu/index.php/Guides/MaEvArM-timer3
  }  // end of TIMER3_CAPT_vect

/////////////////////////ENF OF: TIMER/COUNTER PULSE MEASURE ROUTINE////////////

////////PREPARE FOR INTERRUPTS ROUTINE FOR TIMER/COUNTER CAPTURE////////////////

void prepareForInterrupts ()
  {

  noInterrupts ();  // protected code
  first = true;
  triggered = false;  // re-arm for next time
  // reset Timer 1
  TCCR3A = 0;   // 1 3
  TCCR3B = 0;    // 1 3

  TIFR3 = bit (ICF3) | bit (TOV3);  // clear flags so we don't get a bogus interrupt    // 1 3
  TCNT3 = 0;          // Counter to zero   // 1 3
  overflowCount = 0;  // Therefore no overflows yet

  // Timer 3 - counts clock pulses
  TIMSK3 = bit (TOIE3) | bit (ICIE3);   // interrupt on Timer 3 overflow and input capture
  // start Timer 1, no prescaler
  TCCR3B =  bit (CS30) | bit (ICES3);

// plus Input Capture Edge Select (rising on D13)
//TCCR1B &= ~(1<<ICES1);
//ICP set to trigger on falling/rising edge
//   Bit 6 - ICES1: Input Capture Edge select    Select edge detection for //input capture function.          0 = Capture on falling edge  1 = Capture on //rising edge

  interrupts ();
  }  // end of prepare For Interrupts

///END OF:   PREPARE FOR INTERRUPTS ROUTINE FOR TIMER/COUNTER////////////

///POWER SAVING -SIGNAL INTERRUPT WAKEUP ISR ON D3 on 32u4 or D2 on 328p///

void wakeUp ()
 {
  // cancel sleep as a precaution
     sleep_disable();
  // precautionary while we do other stuff
   detachInterrupt(digitalPinToInterrupt(wakeUpPin));
//D3 for 32u4 and D2 for 328p (INT0)
 }  // end of wakeUp
////POWER SAVING ROUTINE - WAKEUP ISR-END/////////////////

////////SET UP VOID ///////////////////////////////////////////

void setup(void)
{
 pinMode(wakeUpPin, INPUT); //this is pin D3 (INT0) on 32u4 and D2 (INT0) on 328p
digitalWrite (wakeUpPin, LOW);
// enable pull-down on D3 (on 32u4 D3 is INT0) for Wake INTERRUPT   - PART OF //POWER SAVING ROUTINE WITH INT0 SIGNAL on D3 on 32u4 (or D2 on 328p)

 Serial.begin(115200);

  pinMode(13, INPUT);
//This is the input/measure pin (LED taken off or LED13 resistor removed)
   analogWrite(13, LOW);  //must pull up or down to stop noise and floating

  // set up for interrupts
  prepareForInterrupts ();

}   // <= this is for the SET UP () ///////

////////////////////////END OF SETUP SEGMENT/////////////////

//////START OF MAIN LOOP/////////////

void loop(void)
{

   // wait till we have a reading
if (!triggered) //if "triggered" is NOT TRUE  (i.e. NOT TRIGGERED) then STOP HERE
 return;

unsigned long  elapsedTime = (finishTime - startTime);
//period count between start and stop times

Serial.print ("Start time: ");
Serial.print(startTime);
Serial.print (" counts.  ");
Serial.print ("Finish time: ");
Serial.print(finishTime );
Serial.print (" counts.  ");
Serial.print ("Elapsed time: ");
Serial.print (elapsedTime);
Serial.println (" counts.   ");

 // Delay before next measurement update
 delayMicroseconds(1000) ;

 prepareForInterrupts ();
//  goes back up outside LOOP to RESET conditions for next INPUT CAPTURE ISR AND //OVERFLOW ISR TIMER/COUNTER reading, clear registers, etc

///START: POWER SAVING ROUTINE USING D3 (INT0) on 32u4  (D2 is INT0 on 328p) //INTERRUPT FROM PULSE OR USER SWITCH////////////

//delayMicroseconds(3000000) ;
// DELAY SO SLEEP ONLY CAN HAPPEN EVERY 3 sec =>  3000000 us (micro sec)

 delay(500);// MUST have delay to allow power down process to proceed

      // disable ADC
      ADCSRA = 0;

      set_sleep_mode (SLEEP_MODE_PWR_DOWN);
      sleep_enable();

  // Do not interrupt before we go to sleep, or the ISR will detach interrupts and we won't wake.
      noInterrupts ();

  // will be called when INT0 (pin D2 for 328p) or D3 for 32u4 goes HIGH//
     attachInterrupt(digitalPinToInterrupt(wakeUpPin), wakeUp, RISING);

// [External Interrupts] //3 for 32u4 and 2 for 328p (INT0)  Use RISING as //trigger for (INT0 on D2 for 328p and) INT0 on D3 on 32u4 from op AMP.  Same //signal as the D13 INPUT CAPTURE TIMER from op Amp OUT
     EIFR = bit (INTF0);  // clear flag for interrupt 0
     EIFR = bit (INTF1);  // clear flag for interrupt 1
//  added just for good measure to cover both D2 and D3 INT pins

// turn off brown-out enable in software, BODS does not work with 32u4, only //328p.  Work around is to use "low-power.h" library, not implemented here
// BODS must be set to one and BODSE must be set to zero within four clock cycles
       // MCUCR = bit (BODS) | bit (BODSE);
       // The BODS bit is automatically cleared after three clock cycles
       // MCUCR = bit (BODS);

//We are guaranteed that the sleep_cpu call will be done as the processor //executes the next instruction after interrupts are turned on.
        interrupts ();  // one cycle
     // sleep_cpu ();   // one cycle    //*****DISABLED BECAUSE KEEPS DOUBLING
                                        //DATA SEND TIME, AND ONLY WAKES UP HALF
                                        //THE TIME

///////END OF POWER SAVING ROUTINE///////////////////////////////////////////////

}
///////////////////////END OF MAIN LOOP///////////////////

```

# Answer
It seems to me your problem lies here:

> `set_sleep_mode (SLEEP_MODE_PWR_DOWN);`

In this mode, all the synchronous peripherals are turned off, including your timer. However, you need this timer for generating the input capture interrupt. You also want it to be running in order to count the overflows, otherwise the values captured would be meaningless.

In order to keep the timer running, you have to use `SLEEP_MODE_IDLE`, which is the default sleep mode anyway. This mode puts the CPU to sleep while keeping the peripherals running. If you are afraid this may have too high a power consumption, you can selectively turn off all the peripherals you do not need. Note that you cannot selectively *enable* peripherals in other sleep modes.
> 2 votes

---
Tags: arduino-ide, timers, arduino-leonardo, sleep, atmega32u4
---


# Question
Title: is it necessary to include libraries that are specified in the header file already?
I am using the Adafruit BME280 library in my sketch. In the example sketches, they have included the Wire, SPI and the Adafruit\_Sensor library. However, I see that in the Adafruit\_BME280 library header file, these libraries are already included. So I tried commenting out them in my sketch and it still works. So I wonder if there are still cases or any specific reason to include them twice?

Additionally, if a library is included/referenced twice like mentioned above, wouldn't it increase the size of the sketch unnecessarily?

Example Sketch that comes with the library

```
#include <Wire.h>
#include <SPI.h>
#include <Adafruit_Sensor.h>
#include <Adafruit_BME280.h>

#define BME_SCK 13
#define BME_MISO 12
#define BME_MOSI 11
#define BME_CS 10

#define SEALEVELPRESSURE_HPA (1013.25)

Adafruit_BME280 bme; // I2C
//Adafruit_BME280 bme(BME_CS); // hardware SPI
//Adafruit_BME280 bme(BME_CS, BME_MOSI, BME_MISO, BME_SCK); // software SPI

unsigned long delayTime;

void setup() {
    Serial.begin(9600);
    while(!Serial);    // time to get serial running
    Serial.println(F("BME280 test"));

    unsigned status;

    // default settings
    status = bme.begin();
    // You can also pass in a Wire library object like &Wire2
    // status = bme.begin(0x76, &Wire2)
    if (!status) {
        Serial.println("Could not find a valid BME280 sensor, check wiring, address, sensor ID!");
        Serial.print("SensorID was: 0x"); Serial.println(bme.sensorID(),16);
        Serial.print("        ID of 0xFF probably means a bad address, a BMP 180 or BMP 085\n");
        Serial.print("   ID of 0x56-0x58 represents a BMP 280,\n");
        Serial.print("        ID of 0x60 represents a BME 280.\n");
        Serial.print("        ID of 0x61 represents a BME 680.\n");
        while (1) delay(10);
    }

    Serial.println("-- Default Test --");
    delayTime = 1000;

    Serial.println();
}

void loop() {
    printValues();
    delay(delayTime);
}

void printValues() {
    Serial.print("Temperature = ");
    Serial.print(bme.readTemperature());
    Serial.println(" *C");

    Serial.print("Pressure = ");

    Serial.print(bme.readPressure() / 100.0F);
    Serial.println(" hPa");

    Serial.print("Approx. Altitude = ");
    Serial.print(bme.readAltitude(SEALEVELPRESSURE_HPA));
    Serial.println(" m");

    Serial.print("Humidity = ");
    Serial.print(bme.readHumidity());
    Serial.println(" %");

    Serial.println();
}

```

# Answer
> 1 votes
Historically it was necessary, yes. In times past the IDE would look only in your sketch to find the list of libraries to compile and link. However much progress has been made in recursive library searching, whereby the IDE can now find libraries that are included by other libraries.

I am not sure when that change was implemented, but it was a long time coming and is only recently that it's worked.

So if you are distributing code for other people to use then it's a good idea to still add the libraries in the sketch - just in case they're using an older version of the IDE that can't find the libraries included by other libraries.

---
Tags: arduino-uno, library
---


title: Interrupts Within Critical Statements

text:
# Question
Title: Interrupts Within Critical Statements
I've redone a previous Arduino sketch I posted in which I was having trouble capturing encoder counts within critical statements, having no luck properly attaching and detaching interrupts. I've studied various ISR sketches but haven't been able to produce anything that caters to my needs.

I now have a switch case in which a DC motor with CPR encoder correctly rotates back and forth between specified boundaries if it alone is in the void loop. However, once enclosed within a critical statement (I want this action to occur only if a button is pressed), the DC motor continues to rotate only one direction.

I need assistance in where to properly attach and detach these interrupts and how to correctly pass the encoder value to the next action. Below is what I've done so far and any help would greatly be appreciated.

```
#define enA 9
#define in1 6
#define in2 7

const int button1Pin = 8;

int button1State = 0;

volatile long temp, counter = 0;

long local_counter=counter;

enum {IdleState, ForwardState, BackwardState} State;

void setup() {

  Serial.begin(9600);

  pinMode(enA, OUTPUT);
  pinMode(in1, OUTPUT);
  pinMode(in2, OUTPUT);

  Serial.begin (9600);
  pinMode(2, INPUT_PULLUP);
  pinMode(3, INPUT_PULLUP);

  attachInterrupt(0, ai0, RISING);
  attachInterrupt(1, ai1, RISING);

  pinMode(button1Pin, INPUT);

  State = IdleState;
}

void loop() {

  button1State = digitalRead(button1Pin);

   if( counter != temp ){
   Serial.print("counter = ");
   Serial.print (counter);
   Serial.print("     local counter = ");
   Serial.println(local_counter);
   temp = counter;
   }

   //if (button1State == HIGH) {

          switch (State) {

              case IdleState:
                halt ();

              if (counter<2000)
                State = ForwardState;
              break;

              case ForwardState:
                clockwise();

              if (counter>=2000)
                State = BackwardState;
              break;

              case BackwardState:
                counterclockwise();

              if (counter <=0)
                State = ForwardState;
              break;

          } // end switch
   //  }

}

void ai0() {
  if(digitalRead(3)==LOW) {
  counter++;
  }else{
  counter--;
  }
  }

void ai1() {
  if(digitalRead(2)==LOW) {
  counter--;
  }else{
  counter++;
  }
  }

void clockwise (){
    analogWrite(enA, 255);
    digitalWrite(in1, HIGH);
    digitalWrite(in2, LOW);
  }

void counterclockwise () {
    analogWrite(enA, 255);
    digitalWrite(in1, LOW);
    digitalWrite(in2, HIGH);
  }

void halt () {
    digitalWrite(in1, LOW);
    digitalWrite(in2, HIGH);
}

```

An explanation of my setup is as follows:

My button is a tactile button on breadboard (connected to pin 8 of an Arduino Uno), with 5V supply from Arduino. Pins 6 of the Arduino is connected input 1 of the L298N motor driver, pin 7 of Arduino connected to input 2 of the motor driver, and pin 9 of the Adruino connected to the enable of the motor driver. Them motor driver is being supplied by an external 12V supply which is also power the 12V DC geared motor with encoder. The encoder outputs are connected to pin 2 and 3 of the Arduino.

# Answer
The way I see it, the state should go back to IdleState if the button is not pressed. Just putting the switch-case inside the if-statement will result in the motor continue rotating the way it was rotating when the button is released.

```
if (button1State == LOW ) {
  State = IdleState;
  counter=2000;
}
else if(button1State==HIGH && State==IdleState ) {
  counter = 0;
}

switch(State) {
  ...

```

Depending on what it is you want to do, you might want to add another state (say `StoppedState`), where the motors are halted, just like IdleState, but you don't get a state change if `counter<2000`. Then you don't have to change the `counter` variable.

```
if (button1State == LOW ) {
  State = StoppedState;
}
else if(button1State==HIGH && State==StoppedState ) {
  State = IdleState;
}

switch(State) {
  case StoppedState:
    halt ();
    break;
  case IdleState:
    ...

```

PS please indent the if statements inside you `case`s.
> 2 votes

---
Tags: arduino-uno, motor, isr
---


# Question
Title: How I can send data information without work WiFi to LCD?
Hi everyone I am beginning learn coding and the second language English. I have small project I use **Arduino uno , esp8266 , dht11 , lcd I2C and use blynk app** in my project I have the code and work probably when WiFi ON but I have question How I can get the information data from dht to lcd without open the WiFi. Now I get information ( Temp and humidity ) on LCD when WiFi ON only. **How I can make Temp and humidity display on LCD with and without WiFi.**

```
#include <BlynkSimpleShieldEsp8266.h>
#include <DHT.h>
#include <LiquidCrystal_I2C.h>
LiquidCrystal_I2C lcd(0x3F, 20, 4);
char auth[] = "*******************************";
char ssid[] = "***********";
char pass[] = "*********";
#include <SoftwareSerial.h>
SoftwareSerial EspSerial(2, 3); // TX, RX
#define ESP8266_BAUD 9600
ESP8266 wifi(&EspSerial);
#define DHTPIN 8
#define DHTTYPE DHT22
DHT dht(DHTPIN, DHTTYPE);

void setup()
{
  Serial.begin(9600);
  lcd.init();
  lcd.backlight();
  EspSerial.begin(ESP8266_BAUD);
  Blynk.begin(auth, wifi, ssid, pass);
  dht.begin();
}

void loop()
{
  LCD();
  int h = dht.readHumidity();
  int t = dht.readTemperature();
  Blynk.virtualWrite(V1, t);
  Blynk.virtualWrite(V2, h);
}
void LCD()
{
  int h = dht.readHumidity();
  int t = dht.readTemperature();
  lcd.clear();
  lcd.setCursor(0, 0);
  lcd.print(" ******************");
  lcd.setCursor(3, 1);
  lcd.print("TEMP: ");
  lcd.print(t);
  lcd.setCursor(3, 2);
  lcd.print("HUM : ");
  lcd.print(h);
}

```

# Answer
`Blynk.connected()` returns true when hardware is connected to Blynk Server, so you can guard Blynk code with

```
if( Blynk.connected() ){
  // do Blynk things here
}

// Update the LCD anywhere outside of the above "if" statement.

```
> 1 votes

---
Tags: arduino-uno, esp8266, c++, c, blynk
---


# Question
Title: Use the stepper motor library with the A4988 driver?
I want to use this library: https://www.arduino.cc/en/Reference/Stepper

```
#include <Stepper.h>

```

The wiring for my driver is shown here:

https://www.pololu.com/product/1182

From the library, I'm stuck at the motor pins:

```
#define motorSteps 200
#define motorPin1 2    // STEP pin
#define motorPin2 3    // DIR pin

Stepper myStepper(motorSteps, motorPin1, motorPin2);

```

**Is this library not compatible with this stepper motor driver? Or what needs to be defined for it to work?**

More details on the library are here: http://www.tigoe.com/pcomp/code/circuits/motors/stepper-motors

The basic section of my code that works without the library is this:

```
digitalWrite(stepPin, HIGH);
delay(wait);
digitalWrite(stepPin, LOW);
delay(wait);

```

Yet, the two-wire circuit part of the library uses motorPin1 and motorPin2 in a way I don't understand:

```
switch (thisStep) {
  case 0:  // 01
    digitalWrite(motor_pin_1, LOW);
    digitalWrite(motor_pin_2, HIGH);
  break;
  case 1:  // 11
    digitalWrite(motor_pin_1, HIGH);
    digitalWrite(motor_pin_2, HIGH);
  break;
  case 2:  // 10
    digitalWrite(motor_pin_1, HIGH);
    digitalWrite(motor_pin_2, LOW);
  break;
  case 3:  // 00
    digitalWrite(motor_pin_1, LOW);
    digitalWrite(motor_pin_2, LOW);
  break;
}

```

https://github.com/arduino-libraries/Stepper/blob/master/src/Stepper.cpp

How should `motorPin1` and `motorPin2` be defined?

# Answer
That library is not compatible with the A4988. It is intended to do the same job that the A4988 does. You provide a step direction and an instruction to step, and it does the stepping for you.

To use the A4988 you just set a pin HIGH or LOW for the direction, then toggle another pin to make it step. You don't really need a library for that.

However if you do want to abstract it with a library and add lots of cool extra features then you should look at AccelStepper which supports 2-wire drivers like the A4988.
> 1 votes

---
Tags: stepper
---


# Question
Title: Arduino as ISP with serial monitor for ATmega328
I have an ATmeg328 TQFP on a board (in system). I use an Arduino Uno as an ISP to programm the chip. However, i would like to use Serial Communication with the chip through the Arduino board.

1. Is this possible?
2. If yes, how can i realize this?

EDIT: i have the tx and RX pins not available. The chip is on a board. With through arduino board, I mean that I would like to use the miso mosi sck pins to do this.

# Answer
> 1 votes
Just burn the arduino bootloader to your tqfp. Then connect the tx and rx on the tqfp to the tx and rx on your arduino, and pull the reset line on the arduino low.

Downside is you have to do a manual reset on the tqfp before programming. If you have an Uno you could remove the atmega from the socket, and connect the reset on the uno to the reset on the tqfp.

Another option is to connect the TX on the tqfp to the TX pin on the Arduino using a resistor. But for this to work you have to modify the ArduinoISP sketch to make it release TX pin (`UCSRnB &= ~_BV(UCSRnB);`) and set it to input. And reverse it when data is received on the RX. Not trivial, and only works one way (tqfp to PC).

# Answer
> 0 votes
In addition to my previous comment-suggestion that you could implement communication over SPI by adding functionality to both the ISP sketch and the target program, it now occurs to me that another approach would be to implement software serial functionality on both, assigned to some of the pins used for ISP during that process.

# Answer
> 0 votes
as here? Nick Gammon has a sketch which includes an ISP with serial control. Sketch is available on GitHub here

---
Tags: serial, atmega328, arduinoisp
---


# Question
Title: Timers, PWM pins and digital outputs on Arduino Mega
I'm using an Arduino Mega to control motors via PWM and Adafruit DRV8871 motor drivers. I also use TIMER1 for a timed interrupt. After adding the TIMER1 interrupt I discovered I had problems with motor control, which I finally tracked down to using pins 11 & 12 for PWM simultaneously with using TIMER1 for timed interrupts.

My initial thought was to change the timer used for the ISR to avoid the pin 11/12 conflict, but now I'm uncertain as to what the restrictions are for using pins associated with timers. I now realize that pins associated with a timer interrupt can't be used for PWM using analogWrite(int val), but can they be used as general purpose digital outputs?

For instance, if I change from TIMER1 to TIMER0 for my timer interrupt, that appears to change the pin dependency from 11/12 to 4/13. I don't use pin 13, but I do use pin 4 as a digital output. Will using pin 4 as a digital output still work properly?

TIA,

Frank

# Answer
> 2 votes
You can use them for any purpose other than PWM. You can even use them for PWM as long as the settings for the timer allow you to produce the waveform you want.

The reason PWM broke was that you had changed the settings for the timer. The timer is what controls the PWM. When you changed those settings you either turned the PWM function off or set some setting where it wouldn't work. Then the pins associated with that timer didn't get PWM anymore. You can do anything else you want that doesn't involve the timer including use the pin for input or output or any other special function it has not related to the timer.

If you change the timer interrupt to TIMER0, then you run the risk of delay, millis, and micros stop working right. They depend on the TIMER0 overflow interrupt running at a set interval to count time. It depends on how you set the timer up.

I would suggest you do some reading on how these timers work. The Datasheet for the ATMega328P chip is a great place to start.

---
Tags: arduino-mega, pwm, timers
---


# Question
Title: ArduinoJson is not adding string to JsonObject. ArduinoJson broken?
So I've got this code

```

String GetTimeString(){
    strftime(dateArray, 100, dateFormat, getTimeInfo());
    dateString = String(dateArray);
    Serial.println(dateString);
    return dateString;
}

```

Being called later like this:

```
document["Time"] = GetTimeString();

```

But the resulting object looks like this:

> September 12 2020 09:49:04 {"DryBulbTemp":80.762,"WetBulbTemp":72.74606,"Pressure":398.9942,"Humidity":68.32129,"Time":null}

So it behaves this way no matter if I print what comes out of the function immediately before the assignment to the "Time" property. Is ArduinoJson just broken?

# Answer
ArduinoJson 6 works with fixed memory allocation.

When you create a `JsonDocument`, you must specify its memory capacity.
If the capacity is too small, some parts will be missing.

The solution is to increase the capacity of the `JsonDocument`.
Use the ArduinoJson Assistant to know the memory requirements for your project.
> 0 votes

---
Tags: esp32, json
---


# Question
Title: Atmega328 and 4Digit 7 Segment ghost blinking!
I hooked up 4 7Seg leds (CC) with NPN transistors on the cathode of each digit. I am using 74HC595 shift register connected in the circuit in a pretty common fashion. The code I am running is the basic scanning code for the 7seg. The problem is that I see the scanned numbers on other LED digits too. Attached is the image. I call them "ghosts". The circuit I am using has an Atmega328 with an internal 8MHz Osc. The resistors on the segments are 220Ohm and 4 BC547's on the cathodes of the digits with 1kOhm resistors on their base.

**below is the code:**

```
void loop() {

      cathode_high(); // blank the screen

      break_number(number);

      display_number();
     delay(1);

}

void break_number(int num) { // seperate the input number into 4 single digits

  first_digit = num / 1000;
  digits[0] = first_digit;

  int first_left = num - (first_digit * 1000);
  second_digit = first_left / 100;
  digits[1] = second_digit;
  int second_left = first_left - (second_digit * 100);
  third_digit = second_left / 10;
  digits[2] = third_digit;
  fourth_digit = second_left - (third_digit * 10);
  digits[3] = fourth_digit;

}

void display_number() { //scanning

  cathode_high();
  digitalWrite(latch, LOW);
  shiftOut(data, clk, LSBFIRST, numbers[digits[count]]);
  digitalWrite(CAS[count], HIGH);
  digitalWrite(latch, HIGH);
  count++;
  if (count == 4) {
    count = 0;
  }
}

void cathode_high() { //turn off all 4 digit
  digitalWrite(CA_1, LOW);
  digitalWrite(CA_2, LOW);
  digitalWrite(CA_3, LOW);
  digitalWrite(CA_4, LOW);
}
```

Any help would be highly appreciated. Thanx in advance!

# Answer
You change cathodes (digits) before latching in the new data. So for a spit second the data for the previous digits is shown on the current digit.

Swapping `digitalWrite(CAS[count], HIGH);` and `digitalWrite(latch, HIGH);` should fix that.
> 4 votes

---
Tags: atmega328
---


title: ESP32 send UDP packets from both cores

text:
# Question
Title: ESP32 send UDP packets from both cores
Im using `AsyncUDP` in an ESP32 project, where I initialize `AsyncUDP udpSender` and call `udpSender.write(sendbuffer, sendbuffer_size)` from both cores, with different buffers on each core.

One core is continually collecting GY-91 (accel/gyro/magnet) sensor data many times a second and sending it via UDP multiple times a second (after every collection), and the other one is collecting some other data like temperature once a second, as well as responding to commands a server sends.

So I'm basically using one sender on both cores and wondering if this is "thread-safe", if that terminology even applies to this scenario.

Can this cause problems? Is there a specific way this should be done? Like using semaphores?

# Answer
> 2 votes
I don't know if it's thread safe or not. However I would be inclined to play it sage and use a queue and notifications.

1. Create a queue
2. Create a "sender" thread that waits for notification then sends anything in the queue through UDP
3. Create any number of "sensor" threads that place items into the queue then notify the sender thread.

---
Tags: esp32
---


# Question
Title: what is wrong with this code? It doesn't work
```
#include <DS1302.h>
#include <Servo.h>
Time t;
Servo myservo;
int Hour;
int Min;
int Sec;
// Init the DS1302
DS1302 rtc(2, 3, 4);

void setup()
{
myservo.attach(9);
myservo.write(45);
// Set the clock to run-mode, and disable the write protection
rtc.halt(false);
rtc.writeProtect(false);
Serial.begin(9200);
// The following lines can be commented out to use the values already stored in the DS1302
//rtc.setDOW(SUNDAY); // Set Day-of-Week to SUNDAY
//rtc.setTime(8, 59, 50); // Set the time to 12:00:00 (24hr format)
//rtc.setDate(8, 25, 2019); // Set the date to August 25th, 2019
}

void loop()
{
t = rtc.getTime();
Hour = t.hour;
Min = t.min;
Sec = t.sec;
 Serial.print(Hour);
 Serial.print(":");
 Serial.print(Min);
 Serial.print(":");
 Serial.println(Sec);

//set the time for fish feeding
if ((Hour== 2 && Min== 0 && Sec== 2)||(Hour== 21 && Min== 0 && Sec== 2)) {
myservo.write(0);
delay (300);
myservo.write(45);
delay (300);}
}

```

# Answer
**Explanation about the multiple time execution**

```
if ((Hour== 9 && Min== 14)||(Hour== 21 && Min== 0)) {
  for (pos = 0; pos <= 180; pos += 1) { // goes from 0 degrees to 180 degrees
    // in steps of 1 degree
    myservo.write(pos);              // tell servo to go to position in variable 'pos'
    delay(15);                       // waits 15ms for the servo to reach the position
  }
  for (pos = 180; pos >= 0; pos -= 1) { // goes from 180 degrees to 0 degrees
    myservo.write(pos);              // tell servo to go to position in variable 'pos'
    delay(15);                       // waits 15ms for the servo to reach the position
  }
 }

```
1. Assume the time is 9:14:00 (9 hours, 14 minutes, 00 seconds).. the `if` condition passes.
2. The for loop will get executed. The duration needed to complete the loop is roughly 5 seconds.
3. Later, it will again go to the if condition. The time will be now 9:14:06.. it means, the condition will pass again.. the motor will again rotate.. this will repeat for about 11 times.. until the time changes to 9:15:00 or more.
4. So the solution is to give a delay, before exiting the `if` loop if you wait for a minute with

delay(60000);

then, the next 'if' condition will fail and works as per your expectation.

---

**Part 2:**

debugging:

```
        if ((Hour== 9 && Min== 14)||(Hour== 21 && Min== 0)) {
          for (pos = 0; pos <= 180; pos += 1) { // goes from 0 degrees to 180 degrees
            // in steps of 1 degree
            myservo.write(pos);              // tell servo to go to position in variable 'pos'
            delay(15);
            Serial.println("moving");
    ....

```
> 1 votes

# Answer
I think the problem is that you have given the baud rate as 9200 but the minimum baud rate is 9600(Serial.begin(9600)). And change the baud rate in the serial monitor.
> -1 votes

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


# Question
Title: Serial Communication, if statement not working
```
#include <SoftwareSerial.h>
SoftwareSerial my (D6,D7); //(Rx,Tx)
String msg;

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

void gas()
{

  Serial.println(msg);
  if (msg == "0")
  {
    Serial.println("Gas Leakage !!");
  }
  if(msg == "1") {
    delay(1);
  }
}

void loop() {

  msg = my.readStringUntil('\n');
  gas();
}

```

//I am using software serial to exchange data from Arduino UNO to NodeMCU, i am receiving the data correctly but the "if statement condition" is not working with it. how can i make the if statement work?

# Answer
You are using `Serial.println()` to send the message. That function will add the combination `\r\n` as line ending to your message, which are the ASCII codes for return carriage and newline.

In your receiving code, you read until `\n`, so your message now reads `"0\r"`, which is of course not equal to `"0"`. Thus the if condition will never trigger.

When using `msg[0] == '0'` you are taking the first character out of the string and compare that to the character `'0'` (especially note the difference between `"0"`, which is a string, and `'0'`, which is a single character). Since you are only using the first character of the string, the `\r` is out of the picture; you aren't using it.

**What to do now?**

* You could send your message only with the `\n` character as line ending. For this only use `Serial.print()` instead of `Serial.println()` and add the line `Serial.print("\n");` directly after you send your message.
* You could write your own read-until code and just ditch every occurrence of the `\r` character.
* You can use `msg.trim()` to remove any white space characters at the start or end of your string, including the `\r` at the end. Then you can use the code, that you already wrote.

---

Note, that using `String`s on an Arduino is mostly considered evil. Especially if you want to use the code for a longer period or you are using `String` very often. The memory for a `String` is allocated dynamically, which can easily lead to heap fragmentation. For a better and longer explanation, look at The Evils of Arduino Strings, a blog entry from Majenko, who is one of our biggest contributors here.
> 2 votes

---
Tags: arduino-uno, nodemcu, softwareserial, serial-data
---


# Question
Title: Is there a way to get about a 10ns Timer resolution from an AVR CPU?
I have an 8Mhz ATM32u4 that is able to read external pulse inputs at 125ns ticks using InputCapture3 (PC7) on its 16-bit timer. Is there a magical way (bitbanging?) to get around 10ns tick resolution to read pulses? Edit: like ADC conversions to allow 16-bit systems 24-bit accuracy via creative coding, etc.

If there is no magic, I should use a faster CPU? I am limited in coding pretty much to AVR type CPUs in the Arduino IDE. So wondering what AVR CPU would be fast enough for a 10ns tick that is incorporated already into like a Nano, UNO, etc?

Unless I am able to use Pin Interrupts that are able to read at 10ns intervals, then I could use ARM CPU types with Arduino IDE code which does not require me to dive deep into register level language.

Or, is there a stand-alone analog or digital IC that is able to read at 10ns intervals pulses that an Arduino can process?

Thank you.

Edit: I would need to measure the length of a one-shot pulse only, not a continuous or changing signal. Down to 70us length with an accuracy of at least 18ns tick, but preferably 10ns to account for hardware, etc inaccuracies. This one-shot pulse could repeat not more frequently then 1 second apart, but likely several seconds apart. The signal is two positive square waves forming a pulse measuring not less than 70us from the positive rising edge to rising edge. The system measures the pulse length and sends it the user (serial, BLE, etc).

Edit 2: someone suggested a "one-shot pulse stretcher". Interesting concept... The more I am looking into it, the more I think it's a very viable hardware solution to the AVR's processing speed limitation. One may say that this is hardware "bitbanging" by streching out the short pulse to a proportionally longer one that the MCU capture process can measure reliably/accurately. An example is this old IC from Linear Tech. See Fig 12 and Fig 13. https://www.analog.com/media/en/technical-documentation/data-sheets/6752fc.pdf

http://www.anderswallin.net/2014/02/pulse-stretcher-v1/

The shortest expected pulse would be about 70us which needs to be measured at (around) a resolution of 18ns for the accuracy I need. So I went with 10ns for design to allow for some accuracy "overhead". That is between 4000-7000 counts/ticks (18ns-10ns ticks) for the 70us signal.

If I stretch this same 70us signal to be measured with the pulse-stretcher to 700us and use the currently available 125ns tick interval of the ATM32u4, I should arrive in theory to about the same accuracy as using an 18ns tick for a 70us signal to be measured.

Here is a similar problem that was answered: https://electronics.stackexchange.com/questions/46922/lengthening-a-5-ns-pulse

# Answer
> 3 votes
There is nothing you can do on the AVR processors that I know of, which can run on from a quite slow clock, and I think up to 24 MHz. Since your Uno / Leonardo / Micro run at 16 MHz that would be only an incremental speed improvement (to clock them at 24 MHz).

Your idea of bit-banging is interesting, but in general bit-banging is a last resort when you need extra things the hardware doesn't provide (like an extra SPI port) and in general will be slower, not faster, because it involves code rather than inbuilt hardware.

Running at 16 MHz each clock pulse is 62.5 ns which means that is the absolute most resolution it could count. I don't see why you can't count at the rate of 62.5 ns (rather than 125 ns), however that isn't 10 ns resolution.

> Or, is there a stand-alone analog or digital IC that is able to read at 10ns intervals pulses that an Arduino can process?

Very likely. There are probably dedicated counting chips that would do that for you. I haven't looked, but it is the sort of thing there would be a market for. Such a chip would probably use I2C or SPI to communicate, which is easy enough to interface to.

# Answer
> 3 votes
1 ns is a billionth of a second. A 1 gHz clock has a cycle time of 1 ns. If you have a timer that's able to count single clock pulses you'd need a 1 gHz clock to get to 1 ns resolution. for 10 ns, you'd need a 100 mHz clock.

You won't get close to 10 ns resolution with an 8 mHz clocked device.

---
Tags: programming, arduino-ide, timers, atmega32u4, oscillator-clock
---


# Question
Title: Knowing if ESP32 wakes up itself or manually
I have a project where I put an ESP32 to deep sleep for a certain amount of time, eg: 1h

To be able to self-awaken a cable must be connected from GPIO 16 to the reset pin, so basically the ESP pulls down pin 16 and causes itself to reset.

I also need the possibility to manually waken up the ESP, so in parallel to this cable I connect a button to GND, so I can manually reset the ESP and waken it up.

However I need to be able to tell if the ESP has awaken itself because one hour has passed or if it has been manually awaken.

I cannot connect the ESP to a internet time provider to check the time, so my first though wasto connect the button also to an input and read it when the ESP starts.

However the ESP won't start until the button forcing RST low is released and then it's too late to read it and see if it was pressed.

Is there a way that I can tell if the ESP was manually reset or if it woke up by itself?

# Answer
> 3 votes
I think you're getting confused between the ESP32 and the ESP8266. There is no need to connect GPIO16 to reset on the ESP32.

Instead the ESP32 has the "ULP" - Ultra Low-power Processor in it (essentially the RTC processor) which is what sends wakeup signals to the ESP32 cores. It is this which wakes the system up after an hour.

The ULP can also trigger a wakeup from other sources - most often used to wake up from an external signal, such as your button. But this only works if that signal is connected to one of the RTC input pins (GPIOs 34 to 39), or certain interrupt enabled pins (you can read more about what can wake the system up here).

Once a wakeup has happened you can then query the ULP to find out why it woke the ESP32 up using the `esp_sleep_get_wakeup_cause()` function.

---
Tags: esp32, sleep
---


title: Understanding Debounce code

text:
# Question
Title: Understanding Debounce code
I don't understand the following Debounce code. (The complete code is at the bottom.) From what I understand, when the pin reads something, we wait at least 50 milliseconds before performing anything. But doesn't the reading variable get reset every loop iteration, so `reading` equals zero in the inner if-condition in every iteration.

What I think is the sequence of events: loop(), loop(), loop(), "loop(), button press, reading=1, set lastDebounceTime, first if condition fails because we have to wait, set lastButtonState=1", loop(), loop(),loop(),"loop() enough time has passed, but since no button press at in this iteration and the last few, reading and lastButtonState equal zero", loop(), ... .

However, this code works.

Why do we save `reading` in a local variable? Won't the code virtually always be this, then:

```
if (reading != lastButtonState) {
    // reset the debouncing timer
    lastDebounceTime = millis();
  }

  if ((millis() - lastDebounceTime) > debounceDelay) {
    // whatever the reading is at, it's been there for longer than the debounce
    // delay, so take it as the actual current state:

    // if the button state has changed:
    if 0 != buttonState) {
      buttonState = 0;

...

```

Entire code:

```
/*
  Debounce

  Each time the input pin goes from LOW to HIGH (e.g. because of a push-button
  press), the output pin is toggled from LOW to HIGH or HIGH to LOW. There's a
  minimum delay between toggles to debounce the circuit (i.e. to ignore noise).

  The circuit:
  - LED attached from pin 13 to ground
  - pushbutton attached from pin 2 to +5V
  - 10 kilohm resistor attached from pin 2 to ground

  - Note: On most Arduino boards, there is already an LED on the board connected
    to pin 13, so you don't need any extra components for this example.

  created 21 Nov 2006
  by David A. Mellis
  modified 30 Aug 2011
  by Limor Fried
  modified 28 Dec 2012
  by Mike Walters
  modified 30 Aug 2016
  by Arturo Guadalupi

  This example code is in the public domain.

  http://www.arduino.cc/en/Tutorial/Debounce
*/

// constants won't change. They're used here to set pin numbers:
const int buttonPin = 2;    // the number of the pushbutton pin
const int ledPin = 13;      // the number of the LED pin

// Variables will change:
int ledState = HIGH;         // the current state of the output pin
int buttonState;             // the current reading from the input pin
int lastButtonState = LOW;   // the previous reading from the input pin

// the following variables are unsigned longs because the time, measured in
// milliseconds, will quickly become a bigger number than can be stored in an int.
unsigned long lastDebounceTime = 0;  // the last time the output pin was toggled
unsigned long debounceDelay = 50;    // the debounce time; increase if the output flickers

void setup() {
  pinMode(buttonPin, INPUT);
  pinMode(ledPin, OUTPUT);

  // set initial LED state
  digitalWrite(ledPin, ledState);
}

void loop() {
  // read the state of the switch into a local variable:
  int reading = digitalRead(buttonPin);

  // check to see if you just pressed the button
  // (i.e. the input went from LOW to HIGH), and you've waited long enough
  // since the last press to ignore any noise:

  // If the switch changed, due to noise or pressing:
  if (reading != lastButtonState) {
    // reset the debouncing timer
    lastDebounceTime = millis();
  }

  if ((millis() - lastDebounceTime) > debounceDelay) {
    // whatever the reading is at, it's been there for longer than the debounce
    // delay, so take it as the actual current state:

    // if the button state has changed:
    if (reading != buttonState) {
      buttonState = reading;

      // only toggle the LED if the new button state is HIGH
      if (buttonState == HIGH) {
        ledState = !ledState;
      }
    }
  }

  // set the LED:
  digitalWrite(ledPin, ledState);

  // save the reading. Next time through the loop, it'll be the lastButtonState:
  lastButtonState = reading;
}

```

(Debounce code taken from: https://www.arduino.cc/en/tutorial/debounce.)

# Answer
> 2 votes
loop() does not need any time and repeats permanently.

`lastButtonState` is `reading` from previous loop run.

As long as the button bounces, `lastDebounceTime` is updated.

Only when the button has settled (either pressed or released), the condition

```
  ((millis() - lastDebounceTime) > debounceDelay)

```

becomes `true` and the code is executed -\> if `buttonState` (the previous **debounced** state) and `reading` show a change to HIGH, the led state is toggled.

Not sure if this explanation makes anything clearer, as it is clear already as it stands, IMO.

---
Tags: programming, code-review, debounce
---


# Question
Title: PT2257 only gives me heavy buzzing sound
I have this project where I control a bluetooth audio module with an arduino. In this case, I have used an arduino nano. But then, I have been meaning to add volume control to the project so I use a pt2257. But the sounds that it gives to me is my audio plus heavy buzzing sound and no matter how much attenuation that I set the volume doesnt seems to change. Can anyone help me?

Here is the schematics that I use for the PT2257:

I have tried giving Vdd 5V from arduino, and also 5V from a seperate power supply. But it seems there is no difference.

Here is the code that i use:

```
    void setup() {
      delay(1000);
      Wire.begin();
      Serial.begin(115200);
    }
    void loop() {
      Wire.beginTransmission(Volume_address);
      Wire.write(0b011100000);    // set low attenuation
      Serial.print("result 1: ");
      Serial.println(Wire.endTransmission());
      delay(2000);
      Wire.beginTransmission(Volume_address);
      Wire.write(0b11111111);  // set full attenuation
      Serial.print("result 2: ");
      Serial.println(Wire.endTransmission());
      delay(2000);
    }

```

Here is the link to PT2257 datasheet if you need it

EDIT: Here is how I connect CSR8645 Output to my active speaker, before I add a attenuation IC. It works like a charm like this, but I need to add a volume control.

# Answer
many amps and BT audio chips use `differential` input/outputs. none of the inputs nor outputs are considered grounds.

the `Lp(left,postivie) Ln, Rp and Rn` on your audio chip should be connected to loads directly. Ln or Rn are not audio grounds. so you can't use simple POT volume controls or any processor or amplifier chip that doesn't support differential IOs. so, you can't use PT2257 in this circuit.

for better understanding here are two audio signal types:

1. the simple, well known one, which consists of `GND and an audio IN per channel`. you can use many amplifiers, processors (e.h. PT2257) and POT volume controls. and one end of the output (e.g. speaker) is connected to GND.
2. the differntial audio signal which consists of a GND and a pair of `IN+,IN- per channel`. you can't use the soulutions mentioned above. for example, if you wanted to amplify the output signal of the bluetooth chip, you have to use something like PAM8302, 2.5W mono class D audio amp **per channel**. note the IOs:
> 1 votes

---
Tags: arduino-nano, i2c, bluetooth, audio
---