# Question
Title: My ESP8266-01 doesn't want to respond to AT command after a successful flash!
Well hello, experts, I've been trying to fix my issue all time, but all in vain. I have an Esp8266-01 with 1MB memory. I've flashed it with an official AT firmware V2.0.0 of espressif with the help of this tutorial-arduino as a usb/TTL-: "https://www.allaboutcircuits.com/projects/flashing-the-ESP-01-firmware-to-SDK-v2.0.0-is-easier-now/", and it was a successful flash. However, when trying to send AT commands in the serial monitor at different baud rates nothing happens. I'll provide you with all the information down here:

1. Schematic for both flash and normal mode:

2. I used the official flasher tool from espressif
3. I used both Arduino IDE and Termite with no results
4. I've uploaded the blink sketch successfully into my module, but it never runs and blinks.
5. After lots of tries and resets I started to receive some information:

But still no answers from this module!!! Could you help me, please?

# Answer
> 2 votes
The tutorial is to flash SDK 2.0 AT firmware. The AT 2.0.0 firmware is build with RTOS SDK. The 2.0 AT firmware available on Espressif site was build with settings not compatible with esp-01. It is built for 2 MB flash and communicates over pins 13 and 15.

The latest NonOS SDK AT firmware is 1.7.1 (SDK 3), but it requires 2 MB flash too. It is possible to flash it to 1 MB module with the 2MB-c1 parameter with esptool.py. (The OTA update command will not work.)

GitHub user loboris (Boris Lovosevic) builds customized versions of AT firmware with SDK 3 for all flash sizes. You can download the files from his ESP8266\_AT\_LoBo GitHub repository. If you can't run his flash.sh utility, then for 1 MB flash you can Flash Download Tool with bin/upgrade/esp8266\_AT\_1\_2.bin file and the right addresses for 1 MB flash: boot\_v1.7.bin on 0x0; esp8266\_AT\_1\_2.bin on 0x01000; esp\_init\_data\_default.bin on 0xfc000 and blank.bin on 0x7e000 and 0xfe000.

# Answer
> 0 votes
You need pullup resistors, 10kΩ or so, on both the NRST and GPIO0 lines. After you press and release the reset button the NRST line will be floating, and its voltage (and logic level) will be undefined. It's not unusual to see the behavior of a board change just by waving your hand over it if you leave inputs floating, so it's not surprising that you will sometimes get it to work.

---
Tags: esp8266
---


# Question
Title: Execution of functions at the "same time"
everyone I'm designing a vehicle security system, basically I can already read amd i control all the components (GSM, GPS, Magnetic Sensor, Giroscop, buzzer...) connected to the microcontroller.

But then the functions are basically three main ones (at void loop) that I need to be working in "simultaneous", any idea of how I can do that?

Below the code, half long but that's all I need...

there are some comments in portuguese. i apologize for that, but the important thing is in the code thanks in advance

```
#include <SoftwareSerial.h>
#include <TinyGPS++.h>
SoftwareSerial sgsm(3,2);
String number = "25884xxxxxxx" ;
unsigned char Buff[250];
unsigned char BuffIndex;

#include<Wire.h>
int sensorMag = 5;  //SENSOR MAGNETICO

TinyGPSPlus gps;
double latitude, longitude;
String response;
int lastStringLength = response.length();
String link;

const int MPU6050_addr=0x68;
int16_t AccX,AccY,AccZ,Temp,GyroX,GyroY,GyroZ;

#include <IRremote.h>
int RECV_PIN = 4;   //REMOTE
IRrecv irrecv(RECV_PIN);
decode_results results;

int Sirene = 6;     //BUZZER
int Motor = 7;      //MOTOR

/////===================================================================== Inicializacao do sensores =============================================================================================================================
void setup()
{
Serial.begin(9600);
sgsm.begin(9600);
delay (1000);
Wire.begin();
Wire.beginTransmission(MPU6050_addr);
Wire.write(0x6B);
Wire.write(0);
Wire.endTransmission(true);
delay (1000);
pinMode(sensorMag, INPUT); //SENSOR MAGNETICO
pinMode(Sirene, OUTPUT);  //Sirene
pinMode(Motor, OUTPUT);   //MOTOR
irrecv.enableIRIn();
Serial.println("SISTEMA INICIALIZADO");
}

/////=====================================================================  Inicio do Loop  =============================================================================================================================
void loop()
{
 //GPS();
 remote ();
 ReceberComando();

 }

/////=====================================================================   Remote controle  =============================================================================================================================

void remote (){
 if (irrecv.decode(&results))
{
Serial.println(results.value, HEX);
Serial.println("  ");
if (results.value== 0xFF6897)
{
//while (results.value==0xFF5AA5){
Serial.println("SISTEMA INACTIVO");
digitalWrite(Motor, LOW);
Serial.println("  ");
//Acelerometro();
delay(500);
}
else
{
 while (results.value==0xFF10EF)
  {
    Serial.println("Sistema Armado");
    digitalWrite(Motor, HIGH);
    delay(1000);
    Serial.println("  ");
    SensorMagnetico();
    delay(1000);
    Acelerometro();
    delay(1000);
  }
}
}

irrecv.resume(); // Receive the next value
delay(1000);
}

void SensorMagnetico()
{
int EstadosensorMag = digitalRead(sensorMag);
if (EstadosensorMag = digitalRead(sensorMag)== HIGH){
 Serial.println("A porta N. 1 da sua viatura foi aberta!");
 digitalWrite(Sirene, HIGH);
 delay(1000);
 mensagem2();
 delay(1000);
 enviolink();
 delay (1000);
}
else
 Serial.println("Portas Fechadas");
 digitalWrite(Sirene, LOW);
 delay(100);
 //digitalWrite(Motor, HIGH);
}

void Acelerometro(){
Wire.beginTransmission(MPU6050_addr);
Wire.write(0x3B);
Wire.endTransmission(false);
Wire.requestFrom(MPU6050_addr,14,true);
AccX=Wire.read()<<8|Wire.read();
AccZ=Wire.read()<<8|Wire.read();
Serial.print("AccX = ");
Serial.print(AccX);
Serial.print(" || AccZ = ");
Serial.println(AccZ);
delay(1000);

if (AccZ > 2000){
digitalWrite(Sirene, HIGH);
delay(2000);
}
else
digitalWrite(Sirene, LOW);
}

/////====================  coordenadas/ GPS=============================

 void GPS(){
 if(Serial.available()) {
   gps.encode(Serial.read());
 }
 if(gps.location.isUpdated()) {
   Serial.print("latitude:");
   latitude = gps.location.lat();
   Serial.print("longitude:");
   longitude = gps.location.lng();
   link = "www.google.com/maps/place/" + String(latitude, 6) + "," + String(longitude, 6) ;
   Serial.println(link);

 }
}

/////=========  Receber Comandos de texto + localizacao ======================
void ReceberComando()
{
Serial.begin(9600);
sgsm.begin(9600);
Serial.print("Inicializado o GSM e apagando SMS");
clear_SMS_Memory();
delay(3000);
sgsm.println("AT+CMGF=1");
delay(3000);
sgsm.println("AT+CNMI=2,2,0,0,0");
memset(Buff, '\0', 250);// Initialize the string    BuffIndex=5;  }
delay (9000);

pinMode(Motor, OUTPUT); // controle do motor

while(1)
{
 if(sgsm.available()>0)
 {
  Buff[BuffIndex] = sgsm.read();
  if( (Buff[BuffIndex-2] == 'D') && (Buff[BuffIndex-1] == 'M') && (Buff[BuffIndex] == '1'))// Desativar Motor Agora
  {
  digitalWrite(Motor, HIGH);
  send2("Motor da sua viatura desligado! aguarde pelas coordenadas...");
  Serial.println ("Set sgsm Number");
  delay(10000);
  GPS();
  delay(10000);
  enviolink();
  Serial.println(" ");

  }
  if( (Buff[BuffIndex-2] == 'A') && (Buff[BuffIndex-1] == 'R') && (Buff[BuffIndex] == 'M'))//Ativar Motor Agora
  {
  digitalWrite(Motor, LOW);
  digitalWrite (Sirene, LOW);
  send2("Motor Ativo....A viatura esta segura!, Aguarde a localizacao!");
  Serial.println ("Set sgsm Number");
  delay(1000);
  GPS();
  delay(1000);
  enviolink();
  Serial.println(" ");

   }

   if( (Buff[BuffIndex-2] == 'L') && (Buff[BuffIndex-1] == 'O') && (Buff[BuffIndex] == 'C'))//Retorna coordenadas
  {
  send2("Buscado a localizacao actual!");
  GPS();
  delay(10000);
  enviolink();
  Serial.println(" ");
  delay(10000);

   }
       /// Pode se acrescentar mais condicoes
  BuffIndex++;
  if(BuffIndex>250)
   {
    BuffIndex=5;
    }
 }
}
}

/////===============  Mensagens de Texto =======

void send2(String SMS)
 {
 Serial.println ("Sending Message");
 sgsm.println("AT+CMGF=1");    //Sets the GSM Module in Text Mode
 delay(1000);
 Serial.println ("Set sgsm Number");
 sgsm.println("AT+CMGS=\"" + number + "\"\r"); //Mobile phone number to send message
 delay(1000);
 sgsm.println(SMS);
 delay(100);
 sgsm.println((char)26);// ASCII code of CTRL+Z
 delay(1000);
 }

void mensagem()// mensagens das variaveis; e inicializacao do carro
{
 Serial.println ("Sending Message");
 sgsm.println("AT+CMGF=1");    //Sets the GSM Module in Text Mode
 delay(1000);
 Serial.println ("Set sgsm Number");
 sgsm.println("AT+CMGS=\""+ number + "\"\r"); //Mobile phone number to send message
 delay(1000);
 String SMS = "Sistema de Alarme habilitado";   //sgsm content
 sgsm.println(SMS);
 delay(100);
 sgsm.println((char)26);// ASCII code of CTRL+Z
 delay(1000);
}

void mensagem2()// mensagens das variaveis; e inicializacao do carro
{
 Serial.println ("Sending Message");
 sgsm.println("AT+CMGF=1");    //Sets the GSM Module in Text Mode
 delay(1000);
 Serial.println ("Set sgsm Number");
 sgsm.println("AT+CMGS=\""+ number + "\"\r"); //Mobile phone number to send message
 delay(1000);
 String SMS = "Alerta de intrução! Verifique a sua viatura.";   //sgsm content
 sgsm.println(SMS);
 delay(100);
 sgsm.println((char)26);// ASCII code of CTRL+Z
 delay(1000);
}

////=========================   Apaga mensagens no cartao  ===========
void clear_SMS_Memory()
{
unsigned short i = 0;
for (i = 0; i <= 30; i++)
{
sgsm.print("AT+CMGD=");
sgsm.println(i);
delay(100);
}
while (sgsm.available() > 0) sgsm.read();
}

/////=====================  Leitura  de Inputs do GSM ==========

void updateSerial()
{
 delay(500);
 while (Serial.available())
 {
 sgsm.write(Serial.read());//Forward what Serial received to Software Serial Port
 }
 while(sgsm.available())
 {
 Serial.write(sgsm.read());//Forward what Software Serial received to Serial Port
 }
}

/////======= localizacao ========================================
void enviolink()
{
  sgsm.println("AT+CMGF=1");    //Sets the GSM Module in Text Mode
  delay(1000);  // Delay of 1000 milli seconds or 1 second
  sgsm.println("AT+CMGS=\"+25884xxxxxxx\"\r"); // Replace x with mobile number
  delay(1000);
  sgsm.println(link);// The SMS text you want to send
  delay(100);
  sgsm.println((char)26);// ASCII code of CTRL+Z
  delay(1000);
}

```

# Answer
Since you put "simultaneous" in quotes, I'm assuming you realize that one MCU can only do one thing at a time, but cleverly programmed, it can do small pieces of several things faster than you and I can perceive the difference. (I state this for completeness, for the benefit of readers who may not have thought this out yet.)

A couple of techniques will help you here.

One is what I call "maybedo" functions - functions you call frequently, that do or do not do something (depending on conditions such as time or input signals) but they *do it quickly and return immediately*. See my answer here for more explanation of "maybedo" functions.

Another and very important one is to avoid `delay()` calls. Try a timer library such as SimpleTimer. This lets your `loop()` function and those it calls, keep short. The SimpleTimer library entry is a "maybedo" for up to 10 timer-driven functions. All you have to do is call `mytimers.run()` frequently. Mostly it won't do much, but occasionally it will find one or more timers have expired and will call their associated functions for you. You just have to have set up the timers to call some simple - and again, *short* \- functions to do something. And to be clear, we're talking about software-based timers, not the MCU's hardware timers. The library's work is based on the `millis()` function, but it automates that for you.
> 4 votes

# Answer
Without analyzing the complete code, the steps to go are:

* Remove the `delay` function calls. These mostly delay the program in such a way that other parts are not executed in time or 'at the same time'.
* Instead use the `millis` command and check again time stamps (of `unsigned long int` type) to reach the delays you need.
* Create a state machine. This means in simple form that you use an enumeration (`enum` type) which can have one out of a set of values (like Stopped, Accelerating, Decelerating), for each 'states' you can define in your sketch.
* Use these state machines and times to move from one state to another, and while changing state (or during a state) you can perform the actions you need.
> 1 votes

# Answer
As others have said, Arduinos are single-threaded, real mode computers. They only do one thing at a time. However, they do that one thing fast enough that you can make your apps switch between things rapidly enough that they keep multiple tasks running, like a circus clown keeping lots of plates spinning on sticks.

You have to use "roll-your-own" cooperative multitasking, where each time through your app's loop, you look for work to do on each of the tasks you're juggling. You have to make each pass through the loop fast so you don't miss things.

You should avoid the `delay()` function entirely if at all possible. The `delay()` and `delayMicros()` functions bring your app to a complete halt for the entire duration of the delay.

Search on "Arduino blink without delay" and look at the sample app that points to. It shows how to use `millis()` to manage timed actions without using `delay()`. You should apply that approach to everything you do.
> 0 votes

---
Tags: arduino-uno
---


# Question
Title: Nesting loops - if statement in a while loop
I have been trying many variations of code like this, cannot seem to get this to work with how I logically would think it would work. Am I missing something with syntax or breaking some rules? Everything works independently but not jointly.

```
int switchS = 0;
int var = 1;

void setup() {
    pinMode(1,INPUT);
    pinMode(7,OUTPUT);
    digitalWrite(7,LOW);
}

void loop() {
    switchS = digitalRead(1);
    while(var == 1)
    {
        digitalWrite(7,HIGH);
        delay(100);
        digitalWrite(7,LOW);
        delay(100);
        if(switchS == HIGH)
        {
            var = 0;
        }
    }
    delay(5000);
    var = 1;
}

```

# Answer
> 1 votes
I guess you want the while loop to exit, when the switch goes to HIGH. (You didn't explain this in your question)

Currently the variable `switchS` cannot ever change while the code is in the while loop. The variable `var` only changes, when `switchS` is HIGH. So, if `switchS` is LOW at the start of the while loop, you have an infinite loop.

Instead, you can actually read the switch state inside the while loop, not outside of it. The variable `switchS` will not automatically track the state of the switch. You have to explicitly read it. Like this variant of your code:

```
int switchS = 0;
int var = 1;

void setup() {
    pinMode(1,INPUT);
    pinMode(7,OUTPUT);
    digitalWrite(7,LOW);
}

void loop() {
    while(var == 1)
    {
        digitalWrite(7,HIGH);
        delay(100);
        digitalWrite(7,LOW);
        delay(100);
        switchS = digitalRead(1);  // I moved this line in the while loop, to read the switch on every loop iteration
        if(switchS == HIGH)
        {
            var = 0;
        }
    }
    delay(5000);
    var = 1;
}

```

---

Note: You are using pin 1 as input pin. On the Uno this is a Serial (UART) pin, which is used to communicate with the PC. If you have enough pins, that are free, you should not use pins 0 and 1, so that you don't block the serial communication, unless you really need it and know, what you are doing.

---
Tags: arduino-uno
---


title: Lock screen if I leave my seat?

text:
# Question
Title: Lock screen if I leave my seat?
Background: I change the job and in the new company you need to pay pizza for the whole team if you forget to lock your screen :-)

I want it to be automated: I walk away and the screen should lock. No additional action should be required. Keyboard shortcuts, special mouse movements or unplugging devices from USB are not valid solutions.

How could this be solved (with or without arduino)?

Please write slowly, I never worked with sensors or arduino before :-)

I need this for Mac and Ubuntu.

# Answer
Sorry, no Arduino required, but you probably already have a web cam on your desktop. If you don't mind being observed like Schrodinger's Cat, you can use a small utility like YawCam in Windows or Motion on Linux to trigger the screen lock when you are no longer visible at your console.
> 14 votes

# Answer
### Bluetooth!

In the same vein as Gerben's comment, it is quite easy to use your phone for this, assuming that both your PC and your phone have bluetooth (and you take your phone with you, when you leave your seat). Moreover, if your PC does not have BT, cheap BT dongle will solve this.

Next step is writing a script that gets a list of all nearby/found BT devices and if your phone is not on that list, it just sends system call to lock.

As I have actually tried this once (although with a WIN PC), I can say it works more reliably than I would have initially expected (YMMV, obviously).

The great thing is that you (potentially) do not need any extra hardware, just a bit of code.
> 9 votes

# Answer
RFID (NFC) might be the way to go. Have an RFID tag in a wristband and an RFID reader by the side of (or under) your keyboard. As long as you keep your hands close to the keyboard the RFID reader should detect your wristband. When it doesn't sense it for a pre-defined period of time send a signal to the PC to trigger it to lock. It could then trigger the unlock when your wristband is back in range again.
> 8 votes

# Answer
If you chair has a gas cylinder to adjust height, it sinks a bit when sat in. My dip is about a centimeter. That's more than enough for a beam-interruption or reflection sensor, a hall effect sensor, or even a dead-simple magnetic reed switch, like those used by home alarms to monitor windows.

You could have the reed switch turn on/wake up a micro like an ESP8266, which uses ESP-NOW to talk to another ESP plugged into a usb serial on the desktop. Once the message is sent, the micro can go into deep sleep. The desktop's serial port is read by the lang of your choice; node.js, python, c#, etc, and runs a command or fires a key combo to lock the workstation.
> 6 votes

# Answer
At a previous job we also had the rule that the screen had to be locked (usually done by pressing Win+L).

However, there was no pizza; instead, the computer was used to send mass e-mails to colleagues. The topics of the e-mails was as varied as the imaginations of people:

* invitations to various events;
* invitations to various celebrations at the desk of the not locked computer;
* selling of expensive items for very low prices, providing whatever reasons;
* etc etc

Many times, the content of the e-mail was the result of team-work.

The only limit was that the messages should use a decent language and not be (very) offensive. Also, I have never heard of e-mails sent in order to really harm the forgetful person (e.g. termination notice, offensive language to bosses or cutomers...).

---

The easiest and cheapest method is to just use Win+L. After you buy pizza for everybody for a few times, and have to endure their jokes / sarcasm at the same time, you will never forget to lock it again.

It is like learning to not pee in the bed during the night. It happens a few times, until you get it right.

---

For a technical solution, the sky is the limit.

As an (impractical) joke, you may want to have a look at the OMGWTF and the winners.

Example: configure the screensaver to kick in and lock the screen after ~ 5 seconds of inactivity (that is roughly the time you need to stand up and walk away, before any colleague has a chance to start typing without you noticing). It will create some trouble for you also, but you are sure that the computer will never remain unlocked. No additional software, hardware or work required - besides moving the mouse and hitting buttons on the keyboard. At the same time, you will become the most productive employee in the company. :)

---

**On a more serious note**, the purpose of that rule is to make people more aware of the security needs, and the need of them being involved in the process. Usually, locking the screen is the least one can do towards security, even before choosing good passwords - screen not locked, password not needed at all.

If one fails to do even that (lock the computer screen when the computer remains unattended), then there is a big chance that the other security rules are not followed either.
> 5 votes

# Answer
A single distance sensor, properly placed, should be enough to detect when you leave. That's the arduino part.

With python you can then use the serial over USB to read the output from the arduino. And run the command to activate the screen lock, according to your reading.
> 4 votes

# Answer
Place a ultrasonic distance sensor HC-05 close to your monitor, facing towards your chest. Check the distance measured against a defined threshold (potentiometer?) and send a key press to your PC to lock it if it is exceeded.

I can go into more details if wanted, it's actually a project I thought about implementing before.

Edit: Whoops, @Eduardo Trápani suggested it already, but I think I can add to that.

I would use a digispark-like chip that can emulate key presses (WIN + L), this won't get you into trouble for installing software on your PC.
> 2 votes

# Answer
The simplest solution would be using a pressure sensor (pressure pad) in your seat. Or a pressure mat if you use a standing up desk.

Ideally, you can calibrate it with an Arduino and send a "Windows Key + L" or a "Ctrl + Cmd + Q" if it is an Apple.

I reckon no other solution can be simpler to implement nor to maintain.

If you want a slightly more refined solution you can connect a scale, tare it with your weight and set a weight threshold for the Arduino to send the signal.

Edit: In ubuntu, you can set up any key combination to lock the screen. But the rest of the answer stands.
> 1 votes

# Answer
Use an obscure window manager which other people don't know how to use.

I use i3 and like to deliberately leave my workstation unlocked, because it's funny when I come back and find people pressing various key combinations to try and activate the group chat window (sending a funny message in my name is how they would prove they've 'hacked me') which I put into a hidden buffer.

Two and a half years in this role and they still haven't figured it out...all they need to do is RTFM...
> 1 votes

---
Tags: sensors
---


title: Binary message formatter

text:
# Question
Title: Binary message formatter
I am currently developing an IoT device with arduino and i want to minimise the data payload. First i used json which is not very efficent in fixed messages (the format will always be the same). Then i found something like messagepack which also sounds nice but i think you could do even better with just binary. I hope to find something like that:

I have a message for example:

```
#BOOL#INT#INT#FLOAT#BOOL#STRING#

```

The position of this variables never change so i could represent the message in binary and i could save a lot of bytes. Is there any library which can de/encode such formats and generate messages from given values?

If not i think it would be very useful in further IoT devices!

# Answer
> 8 votes
Passing messages across computers and/or microcontrollers with different architectures can be a real pain (endianness...). So do not fall into NIH / reinventing the wheel traps but keep standing on the shoulders of giants! Several message serialization protocols exist.

Several implementations of such protocols exist (even for Arduino).

I suggest to have a look in a search engine for such protocols and add `Arduino`.

I've found:

PS: You might read https://scottlocklin.wordpress.com/2017/04/02/please-stop-writing-new-serialization-protocols/ and have a look at https://xkcd.com/927/ Just choose a giant compatible with your requirements ;-)

https://en.wikipedia.org/wiki/Comparison\_of\_data\_serialization\_formats may help

# Answer
> 2 votes
No such library is needed, since basic C++ can handle this on its own. Create a packed struct with the fields, fill the fields with assignment or memory copying, and cast to a `char*` in order to send. Reverse the order of operations in order to receive. Beware the string though, since they need to/should specify a length somewhere.

# Answer
> 1 votes
A good choice to send sensor data is **CayenneLPP**. LPP stands for **"Low Power Payload"**. It is a sensor type aware encoding that uses as few bytes as possible.

A key feature is that recipient must not be aware of content as it is encoded into message, so you can build a generic gateway using that.

You can read more about CayenneLPP here: https://developers.mydevices.com/cayenne/docs/lora/#lora-cayenne-low-power-payload

It is recommended for using it on TTN to minimize payload weigth.

There is an Arduino library for enconding and decoding. For decoding it outputs JSON object so it is ready to be used in platforms like NodeRed or any python or web based application.

Check it here: https://github.com/ElectronicCats/CayenneLPP

# Answer
> 0 votes
use a struct organize the data and when transmit the struct, use a char pointer pointing to it so everything is sent in binary format.

you will need to come up with a way to determine when the pointer ends.

---
Tags: programming, library, c
---


title: Making Serial act as an interrupt

text:
# Question
Title: Making Serial act as an interrupt
I am trying to make a program to control a stepper motor with serial inputs, and in writing a function to jog it, I am having trouble figuring out how to make a serial input stop the loop that steps the motor without making the time per step inconsistent. Is there a way where I can have a new serial input act like an interrupt and break any loop that's in progress.

```
void jog() {
  if(input[1] == 0) sd.setDirection(0);
  else sd.setDirection(1);
  while(true){
    if(Serial.available() > 0) break;
    sd.step();
    delayMicroseconds(10);
  }
  sd.setDirection(0);
}

```

Right now I have this (I'm using a Pololu library that defines the steps), but for some reason this does nothing or at least moves so slow it's imperceptible (a single step only moves the motor 0.007 degrees). It moves the motor very smoothly if I delete `if(Serial.available() > 0) break;` but then I can't stop it.

```
void loop() {
  getData();
  switch(input[0]){
    case 'r':
      Serial.write('r');
      ramp();
      break;
    case 'c':
      Serial.write('c');
      cycle();
      break;
    case 'j':
      //Serial.write('j');
      jog();
      break;
    default:
      break;
  }
}
void getData(){
if(Serial.available() > 0){
  for(int i = 0; i < 200; i ++){
    input[i] = 0;
  }
  for(int i = 0; i < Serial.available(); i++){
    input[i] = Serial.read();
    Serial.print(input[i]);
  }
}
Serial.flush();
//Serial.print(input[0]);
}

```

This is the relevant code that calls jog()

# Answer
How do you know, that there is nothing in the Serial buffer, when you enter the `jog()` function? You don't check for this.

I think your problem is actually in your `getData()` function. The for loop

```
for(int i = 0; i < Serial.available(); i++){

```

might not work as you think, because i increases in every loop iteration while `Serial.available()` decreases in every iteration. So you actually read less data, than is available on the buffer. For example let's assume, that you have 2 Bytes on the buffer. `Serial.available()` returns 2. In the first for loop iteration `i` is 0, while `Serial.available()` is 2. When you read from the Serial buffer in the iteration, `Serial.available()` decreases to 1 (since you removed one byte from the buffer by reading it). At the end of the iteration, the for loop will increase `i` by 1 (due to the `i++`). Now in the condition of your for loop, you have `1 < 1` (because both `i` and `Serial.available()` are 1), thus the for loop will exit without any further iterations. But you still have 1 Byte left in the buffer, that you didn't read.

As I read from the documentation of `Serial.flush()` (though the documentation is notoriously bad) and from this question, I see, that it will only wait until the output buffer is emptied by the interrupt routines. It does nothing with the input buffer. So you still have data in your RX buffer after this line.

That means, that you really have data in your RX buffer, when you get into the `jog()` function. Thus it will directly exit without doing any step.

---

To solve the issue, you should first correct your `getData()` function to read all the available data from the RX buffer. You can change your for loop like this:

```
for(int i = 0; Serial.available() > 0 && i < INPUT_BUFFER_SIZE; i++){

```

This will loop until the RX buffer is empty (when `Serial.available()` returns 0) or until your `input[]` array is full (Please add a constant or a define for the input buffer size. Maybe you already have it. You didn't include the full code. But I guess it is 200).

After the for loop, you can empty the buffer by reading from it, until there is nothing left (Please see the linked question for that). You can even do this at the start of your `jog()` function. This ensures, mostly, that no data is in the buffer at the start of the `jog()` function (mostly, because the timing of data reception could be, that you receive a byte between the emptying of the RX buffer and the loop. Little probability, but not impossible).

Though - as Nick Gammon states in the linked answer - it is not the best way to empty the RX buffer and use every serial input as interrupt (sometimes you don't have exact control, when exactly the data is received). A better solution is to implement a message protocol, where the end of a full message is marked with a special character. Then you read from serial, until a full message is received (you can even do this non-blocking, so that you can do other things until the message is complete), and only then act upon the message. This would need bigger changes in your code. You would have to rewrite your `getData()` function and then remove all blocking code from the sketch (for example all delays) and work with non-blocking code instead (for example using the `micros()` function. The principle is explained in the `BlinkWithoutDelay` example, that comes with the Arduino IDE (though it uses `millis()` instead of `micros()` it is the same principle). You would call the `jog()` function repeatedly, which would only do a step, if it is time to do one. In the meantime the rest of the code can receive new messages. This makes you more flexible and independent of the exact timing of data reception. Since this would be a big rewrite of your code, you have to decide yourself, if you want to go this way, or stay with the simpler and more imperfect solution.
> 1 votes

---
Tags: serial, stepper-motor
---


title: 24v LED strip with common anode?

text:
# Question
Title: 24v LED strip with common anode?
I have a 5m strip of 24v tunable white LEDs and I'm trying to figure out what I need set it up. There's a pad for V+ and then one for brightness and one for warmth. If I plug the V+ in V+ on a 24v supply and the two others to V-, the whole thing lights up full intensity. The strip draws 16 Watts per meter (80 for the whole thing). As I understand it, you vary the two anodes by varying the resistance to ground. I've seen some instructions that this can be done with PWM pins, but I'm assuming that given the voltage and current, no arduino or similar can handle that much. Do I need transistors then? What specs do I look for to understand the limitations?

# Answer
> 2 votes
Your strip has 2 LEDs with different color temperature directly besides at the same spot for every element of the strip. So the adjusting of the overall color temperature is done by changing the relative brightness of both LEDs. If the LED with the warmer light is brighter, the overall color temperature will also be warmer. Common Anode means, that V+ is the connected to the positive pin (anode) of both LEDs, so it has to be connected to +24V. The electrical circuit is completed by connecting the pins W and C (Warm and Cold) to ground. To control the individual brightness of the warm and cold LED groups, you have to use PWM.

You are right, that an Arduino cannot handle currents this big. You need a transistor for this. I would suggest using a MOSFET, since this is the easiest and most efficient possibility. By one MOSFET for every channel (Warm and Cold), which is capable of handling the needed power (Important! Or you will fry the MOSFET). Also it should be a logic level MOSFET, that is well in saturation of the gate voltage for the output voltage of your Arduino. Connect the MOSFETs Drain pin to the channel on the strip, the Source pin to ground of your power supply and the Gate pin to a PWM pin of the Arduino. Also connect the ground of the power supply with the ground of the Arduino.

Now you can control the brightness of the Warm and of the Cold LEDs by adjusting the PWM duty cycle with the Arduino.

---
Tags: power, led, transistor
---


# Question
Title: Arduino Uno + cc3000 breakout board - read DOM instead of HTML
Is there a way to make the CC3000 read the DOM of a website instead of the HTML on the file?

I'm using the WebClient file which works fine and prints the HTML of the webpage, but the website I'm trying to read from has its HTML different from its DOM (ie: Javascript modifies the HTML once the page loads).

Can I use something other than `www.read()`?

# Answer
> 1 votes
To get a (programatically changed) DOM you need an HTML parser to construct the initial DOM (and something that runs Javascript to modify it).

The server only sends a file and does not store or send a DOM; a DOM is built by the receiving application, usually a browser.

# Answer
> 0 votes
The DOM is something related to browsers. A web server merely serves up stored HTML and any accompanying JS to the client CC3000. It's up to a browser to parse the document, execute any JS to construct the DOM tree and finally render the webpage based on the DOM--not something an Arduino is built for.

I'm not an expert but you will have to forward the HTML from your Arduino to a browser and then somehow scrape the results after it renders the page. Or use a website that implements server-side rendering.

---
Tags: arduino-uno
---


title: Keeping Adafruit Feather charged

text:
# Question
Title: Keeping Adafruit Feather charged
I'm creating a keyboard for someone using an Adafruit Feather 32u4 Bluetooth LE as the brains. The case I want to put in into would be hard to remove to charge the battery.

Can I use this USB LiIon/LiPoly charger to charge the LiPo battery and keep power to the board? And then unpluging from the USB mini-B would switch over to the battery?

# Answer
> 2 votes
From the very page you linked to:

"... we added a connector for any of our 3.7V Lithium polymer batteries and built in battery charging. You don't need a battery, it will run just fine straight from the micro USB connector. But, if you do have a battery, you can take it on the go, then plug in the USB to recharge. The Feather will automatically switch over to USB power when its available. We also tied the battery thru a divider to an analog pin, so you can measure and monitor the battery voltage to detect when you need a recharge."

So, the board has a charger and battery connector already built in.

---
Tags: battery, feather
---


# Question
Title: Arduino code for turning an led on by one clap and then off by one clap
I want my Arduino to turn on a LED when sound sensor detects a clap (noise) and keeps the LED on until the sound sensor detects another clap (noise) which turns the LED off.

```
int Sensor = A0;
boolean status_lights = false;

void setup() {
  pinMode(Sensor, INPUT);
  pinMode(13, OUTPUT);
}

void loop() {
  int status_sensor = digitalRead(Sensor);
  if (status_sensor == 0)
  {
    if (status_lights == true)
    {
      status_lights = false;
      digitalWrite(13, LOW);
    }
    else {
      status_lights = true;
      digitalWrite(13, HIGH);
    }
  }
}

```

My sound sensor has 3 pins. sound sensor details

EDIT: My code only turns on the led but dosen't turn it off when I clap.

# Answer
> 1 votes
If the sound level is below the threshold, the DO pin of the sensor signals a high value. If the sound level exceeds the threshold, i.e you clap you hands, the DO is pulled to GND and the signal gets LOW for a short while. After this short while the signals gets HIGH again.

Now look at you loop:

```
void loop()
{
  int status_sensor = digitalRead(Sensor);

  if (status_sensor == 0)
  {
    // you enter this block if you clap your hands and the
    // mcu is fast enough to capture the signal / DO pin (LOW)
    // within the short time interval
    // I'm sure it is fast enough to enter this block multiple
    // times in the interval the clap is active.
    if (status_lights == true)
    {
      status_lights = false;
      digitalWrite(13, LOW);
    }
    else
    {
      status_lights = true;
      digitalWrite(13, HIGH);
    }
  }
}

```

You see, the LED is toggled as long as the LOW interval of the sensor is active (DO=LOW).

I interpret you statement "My code only turns on the led but dosen't turn it off when I clap." so, that the LED is on, when the program starts without a clap. That means that the environmental noise is loud enough to activate the sensor. Then the loop above is iterated permanently and you switch on and off the LED at a very fast speed. That's like you would apply a PWM waveform on the LED pin. The LED is on but dimmed to about 50%.

To find out if I'm right, just add a delay in the loop. My assumption seems to be correct, if the LED blinks with one herz (one time per second). The you can adjust the sound threshold until the LED stops blinking.

```
void loop()
{
  int status_sensor = digitalRead(Sensor);

  // Add the delay here ..........
  delay(500);

  if (status_sensor == 0)
  {

```

If you have calibrated the sensor, remove the delay from the code and add a new delay after changing the LED states. That should be much shorter, because it's only there to ensure that you don't toggle the LED while the sensor is active.

```
    if (status_lights == true)
    {
      status_lights = false;
      digitalWrite(13, LOW);
    }
    else
    {
      status_lights = true;
      digitalWrite(13, HIGH);
    }
    // wait until the clap is over
    delay(100);

```

---
Tags: arduino-uno, sensors, sound
---


title: STM32 as keyboard

text:
# Question
Title: STM32 as keyboard
I would like to use a STM32F105xx to build my own computer keyboard. That MCU has support to USB OTG (FS). So, I have 2 questions:

1. Can I flash microcontroller with usb or I need a external programer?
2. How to do the computer recognize stm32 as a keyboard?

# Answer
The STM32F105xx series is not yet supported by either Arduino core (STM32 core or maple core) and neither mbed-os.

The chip is still usable with the STM32 provided framework, the STM32HAL, (e.g. through STM32CubeMX). There you can select your chip and generate a template project. The program lets you easily configure the chip for "USB Device" role and HID (Human-Interface-Device) class.

Note that from a hardware side, you must provide the chip with an external crystal oscilator (usually 8MHz) so that the HSE+PLL can generate the 48MHz USB clock. This will not work on the internal HSI clock due to low precision. Activate the HSE Crystal in the RCC section of CubeMX and see the clock configuration tab.

From there on you'll have to read the STM32F1 HAL documentation to figure out how to send keystrokes. There are also external resources here and here.

Programming the board via USB is possible. Just set the BOOT0 and BOOT1 pins accordingly and reset the board to get into bootloader mode. It will then appear as a USB device which is flashable by given tools. See e.g. here. The more direct way is to buy a cheap STLinkv2 and program it via the SWD pins (SWDIO + SWCLK), which also enables debugging, which USB flashing does not.
> 3 votes

---
Tags: usb, arduino-micro, keyboard
---


title: light leds from an array

text:
# Question
Title: light leds from an array
I have the project to build a robot for my school. It will record button pushes then move according to this record.

Before usig motors, i'm trying to do this using leds.

Thanks from posts from this community, I've succeed in recording button pushes in an array.

Now I'm trying to light the leds according to this array. I have 4 buttons with 4 leds and one button tu run the recording when it's ready.

I'm stuck in lighting the leds when I push the play\_button.

I hope someone can help me...

Here's my script :

```
int arr[10];
boolean previous = LOW;
unsigned long time1 = 0;
int debounce = 200;
unsigned long time2 = 0;
int index_state = 0;

int play_button = 13; //define pin # for play button

int button[4] = {2,4,6,8}; //store button pins in an array
int leds[4] = {3,5,7,9}; //store led pins in an array

void setup()
{
  for(int n=0;n<10;n++) arr[n] = 0;//initialisition
 Serial.begin(9600);
}

void loop(){
 boolean mode = digitalRead(2) || digitalRead(4) || digitalRead(6) || digitalRead (8);
 while(mode == LOW) mode = digitalRead(2) || digitalRead(4) || digitalRead(6) || digitalRead (8);//wait here till one of the pushbutton goes high;
 //Serial.println("value");
 if( mode == HIGH && previous == LOW && millis() - time1 > debounce) {
 //find out which one is high and store that value in array;
 if(digitalRead(2)) arr[index_state] = 2;
 else if(digitalRead(4)) arr[index_state] = 4;
 else if(digitalRead(6)) arr[index_state] = 6;
 else if(digitalRead(8)) arr[index_state] = 8;
 else ;

 //print the value and the index;
 Serial.print(arr[index_state]);
 Serial.print(" Stored in index: ");
 Serial.println(index_state);
 index_state = (index_state + 1) % 10;
 //update value of time1 for button debouncing
 time1 =  millis();
}

  //update the value of previous button state
  previous = digitalRead(2) || digitalRead(4) || digitalRead(6) || digitalRead(8);

  }

```

Thank you

# Answer
> 0 votes
You have problems in including the further functionality (the playback), since your `loop()` function is solely written for providing the first part of functionality (the recording). You need an overall structure, that will execute the correct functionality at the correct time/logic order.

For this, an Finite State Machine (FSM) is the best way. It will help you to structure your code and the logic. It is an important principle to learn.

First you would have to divide your program logic into different states and transitions between them (don't look too close at the actual code at this point, but with a higher abstraction). Currently I see 2 states in your project: A state, where you are recording the button presses in an array, just like you already did. And a state, where the array is used for playback. The transition from the first to the second state happens, when the playback button is pressed. The transition back happens, when the playback is finished. It helps to draw a graph for this, to visualize the the states and their transitions. In my answer to this question I explained this further including an example of such a graph.

When you are finished creating the states and transitions, you can create the necessary code structure. The easiest way for a beginner is to use a simple state variable (simply an integer, or - if you want to use names for the states - an enum) in a `switch()`-`case` statement. You can also see this in the linked answer. Your code then goes into the case statements. The switch statement will only execute the code for the current state. To do a transition to another state, you simply change the state variable. So in the case statement of the first state, you put the code that you already have for reading the buttons, and an if statement, that checks the playback button. If the playback button was pressed, change the state variable to the second state.

You could also solve this problem without an FSM, but the structure won't be that good and easy to expand. Also you might get some extra points for implementing an FSM :D

---

Currently your code is blocking. That means, that it will block any further operation, until something happened, in this case, that one of the 4 buttons gets pressed. Often this is only a hindrance, when adding functionalities. It is better to use `do-maybe` code, means code, that will only do something, if some condition is met (like time). You are already doing this in the if statement

```
if( mode == HIGH && previous == LOW && millis() - time1 > debounce) {

```

(it only triggers the recording of a new button, if a button was pressed and the debounce time has passed) so why are you blocking before this with the while loop? You could just write to `mode` without the while loop.

---
Tags: arduino-uno, button, array
---


# Question
Title: fatal error ESP8266WiFi.h: No such file or directory
I want to turn my ESP8266 into an access point so that I can connect directly to it.

I use the following sketch, but when I select GENERIC module ESP8266 from menu, the libraries `ESP8266WiFi.h` and `ESP8266WebServer.h` become available but I was unable to upload the sketch.

Also when I select board as Arduino Uno (Which i have really) and then what to upload then the above two files becomes unavailable and says fatal error no such file... no idea what to do next.

```
#include <ESP8266wifi.h>
#include <WiFiClient.h>
#include <ESP8266WebServer.h>
#include<WiFi.h>
#include<SoftwareSerial.h>
SoftwareSerial esp(2,3);
IPAddress local_IP(192,168,4,22);
IPAddress gateway(192,168,4,9);
IPAddress subnet(255,255,255,0);
 String ssid="Wisal";
 String pass="12345678";
 ESP8266WebServer server(80);
 boolean isAccessPointCreated=false;
void setup(){
  esp.begin(115200);
  Serial.begin(115200);

  WiFi.mode(WIFI_AP);
  Serial.print("Setting soft-AP configuration ... ");
  Serial.println(WiFi.softAPConfig(local_IP, gateway, subnet) ? "Ready" : "Failed!");

  Serial.print("Setting soft-AP ... ");
  Serial.println(WiFi.softAP("ESPsoftAP_01") ? "Ready" : "Failed!");
  Serial.print("Soft-AP IP address = ");
  Serial.println(WiFi.softAPIP());

}

void loop(){
  while(esp.available()>0){
    char a = esp.read();
      if(a == '\0')
        continue;
      if(a != '\r' && a != '\n' && (a < 32))
        continue;
      Serial.print(a);
   }
}

```

# Answer
The ESP8266 core for Arduino that you're trying to use is for programming ESP8266 directly. You are trying to program an Uno with an ESP8266 connected to it for use as a WiFi module. For that application the ESP8266 core is of no use. For your application it's most common to run the AT firmware on the ESP8266 and communicate via serial. If you're doing that I recommend the WiFiEsp library:

https://github.com/bportaluri/WiFiEsp

Since you're uploading to the Uno you should have Arduino/Genuino Uno selected in the **Tools \> Board** menu.
> 2 votes

# Answer
There are two ways to use an ESP8266.

Method 1

You seem to say you are using it as a slave to your UNO. You program you Uno from the IDE. The program will have code in it to send 'AT' commands to the ESP and this will make the ESP handle all the WIFI stuff.

Method 2

You remove you Uno and use the ESP as the main processor. This means you get to program the ESP with C++ like code through the IDE, just as if it was an UNO. HOWEVER you will need to install the ESP package from the board manager and there are certain limitations. You also have access to less IO ports, but you can connect the Uno (over serial or I2C) and use it as a slave (which you program through the IDE separately).
> 0 votes

# Answer
You have imported `ESP8266wifi.h` and not `ESP8266WiFi.h`
> 0 votes

---
Tags: arduino-uno, esp8266
---


# Question
Title: Arduino I can't make this statement work
```
int val1 = 0;
byte val2 = 10;
int buttonPin = A0;
byte result = 0;

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

void loop() {
    val1 = digitalRead(buttonPin);

    if (buttonPin == HIGH) {
        result = result + val2;
        result = result + 10;
    }
    else
    {
        digitalWrite(val1, LOW);
    }

    Serial.print("STATE   ");
    Serial.print(val1);
    Serial.print("    ");
    Serial.print(result);
    Serial.println();

    delay(100);
}

```

# Answer
I appears you want to increment the result by val2 each time the button is pressed. If you want to wire it up this way you can but there are potential issues with this, such as not catching each time you press the button, or thinking you pressed the button twice when you accidentally held it down for more than 100ms. The code for this method is below:

```
const int buttonPin = A0;
bool buttonState = LOW;
int val = 10;
int result = 0;

void setup()
{
  pinMode(buttonPin,INPUT);
  Serial.begin(115200);
}

void loop()
{
    buttonState = digitalRead(buttonPin);

    if (buttonState == HIGH)
    {
        result = result + val;
    }

    Serial.print("STATE:   ");
    Serial.print(buttonState);
    Serial.print("\t");
    Serial.print("RESULT:  ");
    Serial.print(result);
    Serial.println();

    delay(100);
}

```

The way to prevent double counts or missing counts would be to use interrupts. Later I may write that one up if you need that instead.

Good Luck!
> 3 votes

---
Tags: arduino-uno
---


# Question
Title: How to get text to flash on ssd1306 i2c screen
I am trying to alternate a string back and forth on the SSD1306 oled screen. So I want the display to show "test1" for 0.5 seconds, then "test2" for 0.5 seconds, repeating. the code below is just showing "test1" for 0.5 seconds then going blank... I am using a ssd1306 128\_32 i2c screen, and using the adafruit library.

```
#include <SPI.h>
#include <Wire.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>

#define SCREEN_WIDTH 128 // OLED display width, in pixels
#define SCREEN_HEIGHT 32 // OLED display height, in pixels

// Declaration for an SSD1306 display connected to I2C (SDA, SCL pins)
#define OLED_RESET     4 // Reset pin # (or -1 if sharing Arduino reset pin)
Adafruit_SSD1306 display(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, OLED_RESET);

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

  // SSD1306_SWITCHCAPVCC = generate display voltage from 3.3V internally
  if(!display.begin(SSD1306_SWITCHCAPVCC, 0x3C)) { // Address 0x3C for 128x32
    Serial.println(F("SSD1306 allocation failed"));
    for(;;); // Don't proceed, loop forever
  }

  // Show initial display buffer contents on the screen --
  // the library initializes this with an Adafruit splash screen.
  display.display();
  delay(2000); // Pause for 2 seconds

  // Clear the buffer
  display.clearDisplay();

  // Show the display buffer on the screen. You MUST call display() after
  // drawing commands to make them visible on screen!
  display.display();
  delay(2000);

  display.setTextSize(4);             // Draw 2X-scale text
  display.setTextColor(SSD1306_WHITE);

}

void loop() {
 testdrawstyles1();
 testdrawstyles2();
}

void testdrawstyles1(void) {
 display.clearDisplay();
 display.print(F("test1"));
 display.display();
 delay(500);
}

void testdrawstyles2(void) {
 display.clearDisplay();
 display.print(F("test2"));
 display.display();
 delay(500);
}

```

# Answer
> 3 votes
As approved by the OP, the error was caused by not having reset the cursor to a visible position on the display. The text was written outside of the OLED.

It seems as the `clearDisplay()` method does not reset the cursor.

The solution is to change the following methods

```
void testdrawstyles1(void)
{
  display.clearDisplay();
  display.setCursor(0,0);
  display.print(F("test1"));
  display.display();
  delay(500);
}

void testdrawstyles2(void)
{
  display.clearDisplay();
  display.setCursor(0,0);
  display.print(F("test2"));
  display.display();
  delay(500);
}

```

---
Tags: arduino-uno, i2c, display
---


title: Arduino and DAC

text:
# Question
Title: Arduino and DAC
this might be more general electronics question, forgive me if this is not the correct place to ask.

I am atempting to use the arduino and MCP4725 breakout board to inject 4 different voltages into an existing line that comes from V1.

V1 is the analog signal from an existing unit and varies between 2v, 3v and 4v. VM1 responds to those voltages and switches to a different working modes. 2v == Mode A, 3v == Mode B, 4v == Mode C.

My plan is to have MCP4725(represented as V2 below)hooked up to Arduino to simulate Modes A, B, C when needed.

MBR0540 D2 is there to prevent sending the voltage back to the sending unit, MBR0540 D1 is to do the same for DAC.

I am worried that if the D2 fails for whatever reason, I might loose the sending unit functionality.. is there a better way to do it?

simulate this circuit – Schematic created using CircuitLab

Thanks for any help/comments you might have.

# Answer
Unless you are really stressing it, it is highly unlikely that D2 would fail.

You could, though, replace both diodes with a simple SPDT switch to select between the two voltage sources.

Whatever you do, though, it probably has about the same chance (or more so) of failing (and the same end result) as having the diodes.

You could always add an "emergency override" switch that both bypasses D2 and isolates V2 in case of failure.
> 0 votes

---
Tags: dac
---


# Question
Title: How can I make YX5300 MP3 player play song in a loop?
I am doing a Christmas project and I have an ultrasonic sensor that detects if a person is In front of it. I want that if someone is in front of it, it lights up LEDs, which it does, and it also has to play a Christmas song, which it doesn't. I tried to make it play the Christmas song but nothing happens. Also the LEDs are only blinking when you put ur hand in front of the ultrasonic sensor. I want it to light up the lEDs for the same amount of time the song is, 28 seconds, and than the lEDS should stop and the ultrasonic sensor should wait for another person and it repeats. I am new to this so please be specific in your reccomendations. Here is my code:

```
#define trigPin 10
#define echoPin 13
#include <SoftwareSerial.h>
#define ARDUINO_RX 7//should connect to TX of the Serial MP3 Player module
#define ARDUINO_TX 6//connect to RX of the module
SoftwareSerial mySerial(ARDUINO_RX, ARDUINO_TX);
static int8_t Send_buf[8] = {0} ;
#define CMD_SEL_DEV 0X09
#define DEV_TF 0X02
#define CMD_PLAY_W_VOL 0X22
#define CMD_PLAY 0X0D
#define CMD_PAUSE 0X0E
#define CMD_PREVIOUS 0X02
#define CMD_NEXT 0X01

int red1 = 5;
int red2 = 4;
int green1 = 3;
int green2 = 2;

long lCnt = 0;
unsigned long lStart;

void setup(){
  Serial.begin (9600);
  mySerial.begin(9600);
  pinMode(trigPin, OUTPUT);
  pinMode(echoPin, INPUT);
  pinMode(red1,OUTPUT);
  pinMode(red2,OUTPUT);
  pinMode(green1,OUTPUT);
  pinMode(green2,OUTPUT);
  delay(500);//Wait chip initialization is complete
  sendCommand(CMD_SEL_DEV, DEV_TF);//select the TF card
  delay(200);//wait for 200ms

}

void loop(){
  float duration, distance;
  digitalWrite(trigPin, LOW);
  delayMicroseconds(2);

  digitalWrite(trigPin, HIGH);
  delayMicroseconds(10);
  digitalWrite(trigPin, LOW);

  duration = pulseIn(echoPin, HIGH);
  distance = (duration / 2) * 0.0344;

  if(distance > 0 && distance <=60){

    digitalWrite(red1,HIGH);
    delay(50);
    digitalWrite(red2,HIGH);
    digitalWrite(green1,HIGH);
    delay(50);
    digitalWrite(red1,LOW);
    delay(50);
    digitalWrite(red2,LOW);
    digitalWrite(green2,HIGH);
    delay(50);
    digitalWrite(green1,LOW);
    digitalWrite(green2,LOW);
    delay(50);
    sendCommand(CMD_PLAY_W_VOL, 0X1E01);
  }

}

void sendCommand(int8_t command, int16_t dat)
{
  delay(20);
  Send_buf[0] = 0x7e; //starting byte
  Send_buf[1] = 0xff; //version
  Send_buf[2] = 0x06; //the number of bytes of the command without starting byte and ending byte
  Send_buf[3] = command; //
  Send_buf[4] = 0x00;//0x00 = no feedback, 0x01 = feedback
  Send_buf[5] = (int8_t)(dat >> 8);//datah
  Send_buf[6] = (int8_t)(dat); //datal
  Send_buf[7] = 0xef; //ending byte
  for(uint8_t i=0; i<8; i++)//
  {
    mySerial.write(Send_buf[i]) ;
  }
}

```

Thanks

# Answer
> 1 votes
I think you want to use the command `[Single cycle play]` which is `7E FF 06 08 00 00 01 EF` (the `00 01` towards the end is the song number to play).

All the commands are detailed in the manual.

---
Tags: sensors
---


title: Audio Zero not responding on MKR Zero

text:
# Question
Title: Audio Zero not responding on MKR Zero
I have a Arduino MKR Zero set up with a sd card in it and a speaker hooked up to the ground and DAC0. I have a .wav file on it called "test.wav" and it is 8 bit mono 88200hz recording. I am using the AudioZero example to try to play this audio file off the speaker but it is not working. When I upload and run the code and open the Serial Monitor to check to see if it has any errors or sucesses reading the files it is just blank. It uploads the code all fine, but the Serial Monitor says nothing at all and the speaker doesnt play anything. Did I set it up wrong somehow?

Here is the code that it is running:

```
  Simple Audio Player for Arduino Zero

 Demonstrates the use of the Audio library for the Arduino Zero

 Hardware required :
 * Arduino shield with a SD card on CS4
 * A sound file named "test.wav" in the root directory of the SD card
 * An audio amplifier to connect to the DAC0 and ground
 * A speaker to connect to the audio amplifier

 Arturo Guadalupi <a.guadalupi@arduino.cc>
 Angelo Scialabba <a.scialabba@arduino.cc>
 Claudio Indellicati <c.indellicati@arduino.cc>

 This example code is in the public domain

 http://arduino.cc/en/Tutorial/SimpleAudioPlayerZero

*/

#include <SD.h>
#include <SPI.h>
#include <AudioZero.h>

void setup()
{
  // debug output at 115200 baud
  Serial.begin(115200);

  // setup SD-card
  Serial.print("Initializing SD card...");
  if (!SD.begin(SDCARD_SS_PIN)) {
    Serial.println(" failed!");
    return;
  }
  Serial.println(" done.");
  // hi-speed SPI transfers
  SPI.setClockDivider(4);

  // 88200 sample rate
  AudioZero.begin(2*44100);
}

void loop()
{
  int count = 0;

  // open wave file from sdcard
  File myFile = SD.open("test.wav");
  if (!myFile) {
    // if the file didn't open, print an error and stop
    Serial.println("error opening test.wav");
    while (true);
  }

  Serial.print("Playing");

  // until the file is not finished
  AudioZero.play(myFile);
  AudioZero.end();

  Serial.println("End of file. Thank you for listening!");
  while (true) ;
}

```

# Answer
To use the Serial monitor with Arduino MKRZERO, use SerialUSB instead of Serial, i.e. SerialUSB.println("something");
> 0 votes

---
Tags: audio, arduino-zero
---


# Question
Title: Why does command line BOSSA not recognize Arduino Due?
Running Ubuntu 12.04.4 LTS (64 bit) I try to upload my code to the Arduino Due through the Native port. I have tried both the `bossac` that ships with the Arduino IDE (which is a modified version of BOSSA), and the master BOSSA branch.

Running this command:

```
sudo ./bossac -p /dev/ttyACM0

```

I get this error:

```
No device found on /dev/ttyACM0

```

However, it works perfectly inside the Arduino IDE.

What can the problem be?

# Answer
> 5 votes
from the IDE's menu you can activate the verbose upload (and compile) mode, that will print all the command executed; Probabibly what you miss is the necessity to open the serial at 1200baud, that will trigger the reboot and consequent bootloader's start ont DUE chip, and bossac need to find the bootloader. see autoReset

edit: i've now a pc with a physical Serial, so i've tryed to upload in verbose mode:

```
Sketch uses 10,380 bytes (1%) of program storage space. Maximum is 524,288 bytes.
Forcing reset using 1200bps open/close on port /dev/ttyS0
/home/xxx/arduino-1.5.6-r2/hardware/tools/bossac -i -d --port=ttyS0 -U false -e -w -v -b /tmp/build8035422101690460839.tmp/sketch_apr14a.cpp.bin -R

```

as you can see he is resetting the board by opening the serial at 1200, forcing the bootloader to start. You have to do the same on your script befor launching bossac. How this can be done depends on your OS

Please note that the reset is triggered by the 8u2 chip used as USB to serial adapter on the arduino board, so bypassing it by connecting through tx/rx pin (like using your own conversor, like in my example with hardware serial) won't work unless you do a manual reset at the right time

# Answer
> 3 votes
Easiest way I've found to do this purely from the terminal:

```
stty -f /dev/cu.usbmodemfa121 1200;stty stop /dev/cu.usbmodemfa121;./bossac -i -d --port=tty.usbmodemfa121 -U false -e -w -v -b Blink.cpp.bin -R

```

Swap out the serial device for whatever /dev you are using; in Linux you may have to sudo to get direct access to the device. This is assuming you are in the directory where bossac lives and your .bin file is there too. Adjust to suit your needs. If using the native USB port you should change -U to *true*

# Answer
> 1 votes
The Arduino CLI uses a slightly different version of bossa from the one that is on master:

https://github.com/shumatech/BOSSA/tree/arduino

On Linux, I was able to do the following:

```
$ git clone git@github.com:shumatech/BOSSA.git
$ cd BOSSA
$ make bin/bossac -j4
$ stty -F /dev/ttyACM0 1200
$ ./bin/bossac --port=/dev/ttyACM0 --force_usb_port=true -e -w -v -b /path/to/my/firmware.bin -R

```

(I got the answer from this Arduino forum thread.)

---
Tags: arduino-due, bossa, ubuntu
---


title: Mixed structure with int and string

text:
# Question
Title: Mixed structure with int and string
I want to create a structure like this:

```
 struct commands
{
  int   cmd;
  char  descr[25];
};

commands cmds[] =
{
  {16, "Hammond Organ"},
  {17, "Percussive Organ"},
  {18, "Rock Organ"},
  { 0, "" }                   // end of list marker
};

```

The compiler doesn't protest, but in a simulator the values of cmds\[i\].descr are all zeros.

And the line

```
Serial.write(cmds[1].descr);

```

prints nothing.

Please recommend how to rewrite the code.

Thanks.

**EDIT**

Thanks for your answer. It helped me a lot.

There is something wrong with the simulator (Simulator for Arduino - version 1.11E Designed by Virtronics). In the meantime I received the Mega 2560 board and the code works well with the board.

# Answer
There must be something wrong with the simulator you're using, because your code works for me (Arduino IDE 1.8.9, OSX, Arduino Uno).

```
struct commands
{
  int   cmd;
  char  descr[25];
};

commands cmds[] =
{
  {16, "Hammond Organ"},
  {17, "Percussive Organ"},
  {18, "Rock Organ"},
  { 0, "" }                   // end of list marker
};

void setup(){
  Serial.begin(9600);
  Serial.write(cmds[1].descr);
}

void loop(){}

```
> 2 votes

# Answer
Try to use char pointer notation (char \*) instead of array notation (char\[\]) in structure declaration:

```
struct commands
{
    int   cmd;
    char*  descr;
};

```
* OR -

use struct declaration as-is, but change the array initialization like below:

```
commands cmds[] =
{
    {16, {"Hammond Organ"}},
    {17, {"Percussive Organ"}},
    {18, {"Rock Organ"}},
    { 0, {""}}                   // end of list marker
};

```

Additionally, it seems that it always should be written as:

```
struct commands cmds[] =
{
    // here your code
};

```

If you have disabled warnings in your compiler, enable them again - and try to write program the way that you will newer receive warnings.

Thanks for your answer. It helped me a lot.

There must be something wrong with the simulator (Simulator for Arduino - version 1.11E Designed by Virtronics). In the meantime I received the Mega 2560 board and both char pointer notation (char *) and array notation (char\[\]) work well with the board. The compiler (Arduino IDE v. 1.8.10) really produces warnings: ISO C++ forbids converting a string constant to 'char*' \[-Wwrite-strings\]. Perhaps the simulator is more meticulous than the compiler and therefore refuses to work with a code thar generates warnings.
> 0 votes

---
Tags: arduino-mega, programming, c, string
---


# Question
Title: How to use a potentiometer to access data within a 2 dimensional array?
I'm trying to create a 2D array of notes that are split into 3 scales. There are 3 notes in each scale. There are 3 buttons to play each note and I want to use an available potentiometer to select each of the scales to be played.

Despite my searching I cannot understand how to achieve this correctly. So far this is what I have.

Using an Arduino Uno:

```
// musical notes
int C = 1046;
int D = 1175;
int E = 1319;
int F = 1397;
int G = 1598;
int A = 1760;
int B = 1976;
int C1 = 2093;
int D1 = 2349;

const int numScales = 3;
const int numNotesPerScale = 3;

const int  notes[numScales][numNotesPerScale] = {
  {C, D, E},
  {F, G, A},
  {B, C1, D1}
};

const int numberOfButtons = 3;
int buttonPin[numberOfButtons] = {2, 7, 4};
//int notes[numberOfButtons] = {C, D, E};
int ledPin[numberOfButtons] = {11, 10, 9};

int buttonState = 0;         // variable for reading the pushbutton status
int speaker = 3;                 // name of the speaker key

void setup() {

  for (int i = 0; i < numberOfButtons; i++) {
    pinMode(buttonPin[i], INPUT);
    pinMode(ledPin[i], OUTPUT);
  }
  pinMode(speaker, OUTPUT);     // set speaker to be an output
}

void loop() {
  int numScales = map(analogRead(A2), 0, 1023, 0, 2);
  //int numScales = analogRead(A2 / 341);

  for (int i = 0; i < numberOfButtons; i++) {
    checkButton(buttonPin[i], notes[i], ledPin[i]);
  }
}

void checkButton(int buttonPin, int note, int ledPin)
{
  // read the state of the pushbutton value:
  buttonState = digitalRead(buttonPin);

  // check if the pushbutton is pressed. If it is, the buttonState is HIGH:
  if (buttonState == HIGH){
    digitalWrite(ledPin, HIGH);
    tone(speaker, note);                 // play the note
    delay(100);                       // wait for 1/10th of a second
  }  } else {
    digitalWrite(ledPin, LOW);
    noTone(speaker);                  // stop playing the note
  }
}

```

# Answer
> 3 votes
Using the Arduino `map()` function seems a reasonable approach to this, however you have a problem with the indexing.

```
if (numScales == 3); {

```

Is probably *not* what you want, as that condition can never be true since you set it to something in the range of 0-2 before you reach this check.

Considering only the relevant dimension, you a 3-element array, which will have legal elements numbers 0, 1, and 2

You call `map(analogRead(A2), 0, 1023, 0, 2);` which can produce an output in the range of 0-2, so far so good.

But then check for a value 3 which is not only illegal as in index to a 3-element array, but unable to be produced by your code.

Additionally you should probably stop trying to use the `numScales` variable to do double duty holding both the initial size and later also the *current index*. And you should probably pass that as an argument, rather than make it a global variable.

You are also failing to ever use the current scale as an index into the notes array. The syntax of double array indexing would be `notes[x][y]` but of course this should only be done with indicies to elements that exist.

It would probably also be a good idea to add some debug output of the internal logic, for example print both the raw ADC reading and the result of mapping that to the selected "scale".

# Answer
> 1 votes
```
// musical notes
int C = 1046;
int D = 1175;
int E = 1319;
int F = 1397;
int G = 1598;
int A = 1760;
int B = 1976;
int C1 = 2093;
int D1 = 2349;

const int columns = 3;
const int scales = 3;
int potVal = 0;
const int  notes[scales][columns] = {
  {C, D, E},
  {F, G, A},
  {B, C1, D1}
};

const int numberOfButtons = 3;
int buttonPin[numberOfButtons] = {2, 7, 4};
int ledPin[numberOfButtons] = {11, 10, 9};

int buttonState = 0;         // variable for reading the pushbutton status
int speaker = 3;                 // name of the speaker key

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

  for (int i = 0; i < numberOfButtons; i++) {
    pinMode(buttonPin[i], INPUT);
    pinMode(ledPin[i], OUTPUT);
  }
  pinMode(speaker, OUTPUT);     // set speaker to be an output
}

void loop() {
  int potVal = map(analogRead(A2), 0, 1024, 0, 3);
  Serial.println(notes[2][2]);
  for (int i = 0; i < numberOfButtons; i++) {
    //checkButton(buttonPin[i], notes[scales][columns], ledPin[i]);
    checkButton(potVal,i);
  }
}

void checkButton(int scaleNum, int buttonNum)
{
  // read the state of the pushbutton value:
  buttonState = digitalRead(buttonPin[buttonNum]);

  // check if the pushbutton is pressed. If it is, the buttonState is HIGH:
  if (buttonState == HIGH) {
    digitalWrite(ledPin[buttonNum], HIGH);
    tone(speaker, notes[scaleNum][buttonNum]);                 // play the     note
    delay(100);                       // wait for 1/10th of a second
  } else {
    digitalWrite(ledPin[buttonNum], LOW);
    noTone(speaker);                  // stop playing the note
  }
}

```

---
Tags: programming, potentiometer
---


# Question
Title: SIM808 module: GSM location command (AT+CIPGSMLOC=1,1) giving wrong value after execution of sending message command (AT+CMGS=+91xxxxxxxx)
I wrote the code that if an interrupt is generated, get GSM location and send a message.

The first time the interrupt is generated, I got the correct GSM location using `AT+CIPGSMLOC=1,1` and successfully sent a message using the `AT+CMGS=+91xxxxxxxx`command.

But the next time an interrupt was generated, `AT+CIPGSMLOC=1,1` gave a wrong location. When I commented out the code to send a message, on every interrupt generated I am getting the correct GSM location. So it seems like the problem is occurring after sending a message. But I have no clue what exactly is going wrong. Following is my code.

Note: on restarting the module, I'm again getting the correct location the first time, before sending a message.

```
void setup() {
  mySerial.begin(9600);
  Serial.begin(9600);
  while (!Serial) {
  }
  // initialize the pushbutton pin as an input:
  pinMode(sensorPin, INPUT);
  // Attach an interrupt to the ISR vector
  attachInterrupt(0, pin_ISR, FALLING);
}

/////////***GSM RESPONSE***///////////
String DisplayGSMResponse() {
  if(mySerial.available()) {
    String gsm_input="";
    while(mySerial.available()) {
      gsm_input+= (char)mySerial.read();
    }
    gsm_input.trim();
    delay(1000);
    Serial.println(gsm_input);
    return gsm_input;
  }
}

void SendMessage(String mobNum,String Location) {
  Serial.println("Sending message..");
  mySerial.println("AT+CMGF=1");
  //Sets the GSM Module in Text Mode
  delay(2000);
  // Delay of 1000 milli seconds or 1 second
  DisplayGSMResponse();
  mySerial.println("AT+CMGS=\""+mobNum+"\"\r");
  // mobile Number
  delay(4000);
  DisplayGSMResponse();
  cleanBuffer();
  mySerial.print("test");
  // The SMS text you want to send
  delay(100);
  mySerial.println((char)26);
  // ASCII code of CTRL+Z
  delay(8000);
  DisplayGSMResponse();
}

void gprsInit() {
  if (isGPRSInit) {
    return;
  }
  Serial.println("GPRS INITIALIZING");
  mySerial.println("AT+SAPBR=3,1,\"CONTYPE\",\"GPRS\"");
  delay(2000);
  DisplayGSMResponse();
  mySerial.println("AT+SAPBR=3,1,\"APN\",\"INTERNET\"");
  delay(2000);
  DisplayGSMResponse();
  mySerial.println("AT+SAPBR=1,1");
  delay(8000);
  DisplayGSMResponse();
  mySerial.println("AT+SAPBR=2,1");
  delay(2000);
  DisplayGSMResponse();
  isGPRSInit = true;
}

void gprsterm() {
  mySerial.println("AT+SAPBR=0,1");
  delay(1000);
  DisplayGSMResponse();
  isGPRSInit = false;
}

String getGPS() {
  Serial.println("GETTING GPS LOCATION");
  String loc = "";
  String location = "";
  mySerial.println("AT+CIPGSMLOC=1,1");
  delay(3000);
  loc = DisplayGSMResponse();
  return location;
}

void loop() {
  if (buttonState == 1) {
    detachInterrupt(0);
    gprsInit();
    location = getGPS();
    SendMessage(mobileNumber, location);
    gprsterm();
    Serial.println("location = " + location);
    buttonState = 0;
    location = "";
    attachInterrupt(0, pin_ISR, FALLING );
  }
}

void pin_ISR() {
  buttonState = 1;
  Serial.println("interrupt");
}

```

EDIT: added gprsterm function.

Note: I removed the interrupt and called the code inside the loop function twice. The first time I got a correct result. The second time a wrong result. So it seems like the interrupt is not be causing the problem.

EDIT2: One interesting thing I found is that at my home it is showing correct results every time, but in the office it is showing a wrong location on second location call i.e after the SMS was sent and we get the GSM location using `AT+CIPGSMLOC=1,1`.

# Answer
It might be due to the command giving the nearest cell tower location. And for sending SMS it might be shifting to a different cell tower depending on your network. This could maybe be easily checked using a different cell provider or as you said its working at your home so I believe I am correct in assuming this is the answer
> 1 votes

# Answer
```
Serial.println("location = " + location);

```

I think in upper line you should `remove + sign` from the code.
> -1 votes

---
Tags: serial, arduino-mega, gsm, gps
---


# Question
Title: How to (optimally) fetch a button press?
For my hardware, I need to check if the button was pressed, but I need to do things only once every half a second.

`if (digitalRead(pin) == HIGH)
{
 doStuff();
 delay(500);
}`

The above does not work, because I have to check other things in the main loop as well.

# Answer
> 0 votes
You should use the `millis` function (see millis).

Create a variable of type `unsigned long` and check it against the current time, with some offset.

See also the debouncing example, how to use this function and maybe you want to implement the debouncing too.

---
Tags: programming, button
---


# Question
Title: LCD Blinking after inserting code : A medication reminder system using Arduino Uno
RTC DS3231,Arduino Uno and 4 push buttons, 10K potentiometer, 4 of 10K resistor and a buzzer. I decided to follow from an online source and encounters a few problems which already fixed but this one puzzles me. Would really appreciate your help. The RTClib.h library is already installed.LCD Blinking after inserting code and it shows blocks instead of characters.

There's other picture in this link too.

https://drive.google.com/open?id=1OzHqZlS7mnkngMx-EIiqIgzdHZaTsHr8

```
#include <LiquidCrystal.h>
#include <Wire.h>
#include <RTClib.h>
#include <EEPROM.h>

RTC_DS3231 rtc;

const int rs = 12, en = 11, d4 = 5, d5 = 4, d6 = 3, d7 = 2;                 // lcd pins
LiquidCrystal lcd(rs, en, d4, d5, d6, d7);

int buzz = 13;
int addr=17;

const int buttonPin2 = 9;
const int buttonPin3 = 8;
const int buttonPin1 = A0;
const int buttonPin4 = 7; // the pin that the pushbutton is attached to
int val2 = 0;
int val3=0;
int pushVal;
int bS1 = 0;         // current state of the button
int lBS1 = 0;     // previous state of the button

int bS2 = 0;         // current state of the button
int lBS2 = 0;

int bS3 = 0;         // current state of the button
int lBS3 = 0;

int bS4 = 0;         // current state of the button
int lBS4 = 0;

// configure the pins to the right mode
int buzz8amHH = 8;          //    HH - hours         ##Set these for reminder time in 24hr Format
int buzz8amMM = 00;          //    MM - Minute
int buzz8amSS = 00;          //    SS - Seconds

int buzz2pmHH = 8;          //    HH - hours
int buzz2pmMM = 1;          //    MM - Minute
int buzz2pmSS = 00;          //    SS - Seconds

int buzz8pmHH = 8;          //    HH - hours
int buzz8pmMM = 2;          //    MM - Minute
int buzz8pmSS = 00;          //    SS - Seconds

int nowHr, nowMin, nowSec;

void gwsMessege(){               // print get well soon messege
    lcd.clear();
    lcd.setCursor(0, 0);
    lcd.print("Stay Healthy :)");     // Give some cheers
    lcd.setCursor(0, 1);
    lcd.print("Get Well Soon :)");// wish
}

void helpScreen() {              // function to display 1st screen in LCD
    lcd.clear();
    lcd.setCursor(0, 0);
    lcd.print("Press Buttons");
    lcd.setCursor(0, 1);
    lcd.print("for Reminder...!");
 }

void timeScreen() {              // function to display Date and time in LCD screen
  DateTime now = rtc.now();             // take rtc time and print in display
    lcd.clear();
    lcd.setCursor(0, 0);
    lcd.print("Time:");
    lcd.setCursor(6, 0);
    lcd.print(nowHr = now.hour(), DEC);
    lcd.print(":");
    lcd.print(nowMin = now.minute(), DEC);
    lcd.print(":");
    lcd.print(nowSec = now.second(), DEC);
    lcd.setCursor(0, 1);
    lcd.print("Date: ");
    lcd.print(now.day(), DEC);
    lcd.print("/");
    lcd.print(now.month(), DEC);
    lcd.print("/");
    lcd.print(now.year(), DEC);
    delay(500);
}

void setup()
{
Wire.begin();
  rtc.adjust(DateTime(F(__DATE__), F(__TIME__)));            // uncomment this to set the current time and then comment in next upload when u set the time
  //rtc.adjust(DateTime(2019, 1, 10, 7, 59, 30));                // manual time set

  lcd.begin(16, 2);
  lcd.clear();
  lcd.setCursor(0, 0);
  lcd.print("Welcome To Our");                                      // print a messege at startup
  lcd.setCursor(0, 1);
  lcd.print("Medicine Reminder");
  delay(1000);
  gwsMessege();
  delay(3000);
  helpScreen();
  delay(2000);
  timeScreen();
  delay(3000);
  lcd.clear();

  pinMode(buttonPin1, INPUT);
  pinMode(buttonPin2, INPUT);
  pinMode(buttonPin3, INPUT);
  pinMode(buttonPin4, INPUT);
  pinMode(buzz, OUTPUT);
  Serial.begin(9600);
}

void ValSet(){
  Serial.println(EEPROM.read(addr));
  val2 = EEPROM.read(addr);                         // read previosuly saved value of push button to start from where it was left previously
  switch (val2) {
    case 1:
      lcd.clear();
    lcd.setCursor(0, 0);
    lcd.print("Reminder set ");
    lcd.setCursor(0, 1);
    lcd.print("for Once/day !");
      pushVal = 1;
      delay(500);
      break;
    case 2:
      lcd.clear();
    lcd.setCursor(0, 0);
    lcd.print("Reminder set ");
    lcd.setCursor(0, 1);
    lcd.print("for Twice/day !");
      pushVal = 2;
      delay(500);
      break;
    case 3:
      lcd.clear();
    lcd.setCursor(0, 0);
    lcd.print("Reminder set ");
    lcd.setCursor(0, 1);
    lcd.print("for Thrice/day !");
      pushVal = 3;
      delay(500);
      break;
  }
}

// the main loop will constantly check to see if the button has been pressed
// if it has, a counter is incremented, and then some action can be taken
void loop()
{                                         //call to set thrice/day
    if (pushVal == 1) {                                // if push button 1 pressed then remind at 8am
    at8am();                                           //function to start uzzing at 8am
  }
  else if (pushVal == 2) {                             // if push button 2 pressed then remind at 8am and 8pm
    at8am();
    at8pm();                                           //function to start uzzing at 8mm
  }
  else if (pushVal == 3) {                             // if push button 3 pressed then remind at 8am and 8pm
    at8am();
    at2pm();                                            //function to start uzzing at 8mm
    at8pm();
  }
  // read the state of the button
  bS1 = digitalRead(buttonPin1);
  bS2 = digitalRead(buttonPin2);
  bS3 = digitalRead(buttonPin3);
  bS4 = digitalRead(buttonPin4);

  // check to see if it different than the last time we checked

if (bS2 != lBS2) {
    // either the button was just pressed or just released
    if (bS2 == HIGH) {
      // it was just pressed
      Serial.println("n02");
      EEPROM.write(17,1);
      push1();
      delay(1000);
    }
  }
  lBS2 = bS2;

if (bS3 != lBS3) {
    // either the button was just pressed or just released
    if (bS3 == HIGH) {
      // it was just pressed
      Serial.println("no3");
      EEPROM.write(17,2);
      push2();
      delay(1000);
    }
  }
  lBS3 = bS3;

if (bS4 != lBS4) {
    // either the button was just pressed or just released
    if (bS4 == HIGH) {
      // it was just pressed
      Serial.println("no4");
      EEPROM.write(17,3);
      push3();
      delay(1000);
    }
  }
  lBS4 = bS4;

if (bS1 != lBS1) {
    // either the button was just pressed or just released
    if (bS1 == HIGH) {
      val3=EEPROM.read(addr);
      EEPROM.write(17,0);
      digitalWrite(buzz, LOW);
      pinstop();
      EEPROM.write(17,val3);
    }
  }
  lBS1 = bS1;

  timeScreen();
  ValSet();
}
void push1() {                   // function to set reminder once/day                                           //save the state of push button-1
    lcd.clear();
    lcd.setCursor(0, 0);
    lcd.print("Reminder set ");
    lcd.setCursor(0, 1);
    lcd.print("for Once/day !");
    delay(1200);
    lcd.clear();
  }

void push2() {                      //function to set reminder twice/day
    lcd.clear();
    lcd.setCursor(0, 0);
    lcd.print("Reminder set ");
    lcd.setCursor(0, 1);
    lcd.print("for Twice/day !");
    delay(1200);
    lcd.clear();
  }

void push3() {                    //function to set reminder thrice/day
    lcd.clear();
    lcd.setCursor(0, 0);
    lcd.print("Reminder set ");
    lcd.setCursor(0, 1);
    lcd.print("for Thrice/day !");
    delay(1200);
    lcd.clear();
  }

void pinstop(){                   //function to stop buzzing when user pushes stop push button
    lcd.clear();
    lcd.setCursor(0, 0);
    lcd.print("Take Medicine  ");
    lcd.setCursor(0, 1);
    lcd.print("with Warm Water");
    delay(5000);
    lcd.clear();
  }
void at8am() {                      // function to start buzzing at 8am
  DateTime t = rtc.now();
  if (int(t.hour()) == buzz8amHH && int(t.minute()) == buzz8amMM  && (int(t.second()) == buzz8amSS || int(t.second()) < buzz8amSS+10)) {
        /////////////////////////////////////////////////////
        digitalWrite(buzz,HIGH);
        lcd.clear();
        lcd.setCursor(0, 0);
        lcd.print("Time to take ");
        lcd.setCursor(0, 1);
        lcd.print("Morning medicines.");
        delay(5000);

        /////////////////////////////////////////////////////
      }
}

void at2pm() {                          // function to start buzzing at 2pm
  DateTime t = rtc.now();
  if (int(t.hour()) == buzz2pmHH && int(t.minute()) == buzz2pmMM  && (int(t.second()) == buzz2pmSS || int(t.second()) < buzz2pmSS+10)) {
        /////////////////////////////////////////////////////
        digitalWrite(buzz,HIGH);
        lcd.clear();
        lcd.setCursor(0, 0);
        lcd.print("Time to take ");
        lcd.setCursor(0, 1);
        lcd.print("Afternoon medicines.");
        delay(5000);

        /////////////////////////////////////////////////////
      }
}

void at8pm() {                           // function to start buzzing at 8pm
DateTime t = rtc.now();
  if (int(t.hour()) == buzz8pmHH && int(t.minute()) == buzz8pmMM  && (int(t.second()) == buzz8pmSS || int(t.second()) < buzz8pmSS+10)) {
        /////////////////////////////////////////////////////
        digitalWrite(buzz,HIGH);
        lcd.clear();
        lcd.setCursor(0, 0);
        lcd.print("Time to take ");
        lcd.setCursor(0, 1);
        lcd.print("Night medicines.");
        delay(5000);

        /////////////////////////////////////////////////////
      }
}

```

# Answer
> 1 votes
Some troubleshooting ideas:

**1**. does turning the potentiometer change the brightness of the LCD?

A. If not, there is a (1) power problem (2) wiring problem.

**2**. Do you ever get strange characters on the LCD or just the "shows blocks instead of characters"?

A. If you only get the blocks. THe data is probably not making it to the LCD. THe LCD will display blocks by default.

B. If you get strange character data too, then data lines probably are't wired properly.

**3**. Upload a program which only does the following:

A. Initializes the LCD

B. prints one line of output every time in the loop() This is the easiest way to determine if it is your wiring. If you don't see anything on the LCD then there is a high probability you have a wiring problem. This is also very easy to try because you just open up a new sketch, create it and upload it to your device.

**LCD Example**

Try this official Arduino LCD Example (just make sure your data lines match -- you can change the values in the sample code so they are appropriate for your situation.

If it is a wiring problem I'd start looking at

1. if you are getting the needed amount of current / voltage to the LCD
2. is each data line connected properly. Unhook power and use a meter to check continuity from your Arduino to your LCD pins.

# Answer
> 0 votes
Your wiring image is difficult to see. I recommend checking one by one.

Firstly, you connect Arduino with LCD only, make it work first. And then try the next.

I took at a glance at your code. There are some points you should check or change:

1. DO NOT use delay() function, if you uses delay() function, many pressing events will be missed. You should use timestamps instead. I recommend using ezButton library to avoid the blocking or implement timestamp by yourself (refer to BlinkWithoutDelay example).
2. Seemingly, you are using the external pull-up/pull-down for buttons. I recommend using the internal pull-up to reduce the complexity of wiring.

For LCD, please refer to this tutorial

---
Tags: arduino-uno, lcd, rtc
---


# Question
Title: How to link a computer processor to an Arduinno on a board?
I am completely new to Arduinno, so please forgive if the question is stupid.

Here is the problem: I have a project where I want an Arduino (or similar microchip board) to handle some sensors and actuators. But I need very advanced "artificial intelligence" to handle the data provided by those sensors. There are two major obstacles for placing this intelligence on the Arduinno, according to my researches.

* First, the Arduinno is coded in a language similar to C: I could of course find a way to write the intelligence, but it will be a time-consuming task for the developper
* Second, I might encounter a problem with memory: I will store heavy matrix of data, do complicated calculation, and this might be too much for an Arduinno
* Third, I read on stackexchange that there are some ways to compile Python code on Arduinno boards, such as the Arduinno Mega. So I can code this intelligence in Python (which is an easy task), and compile the resulting code on Arduinno. However, I will reach a caveat: some libraries I will use will be entirely compiled, and this will take too much memory on an Arduinno (such as the second issue I mentionned)

So I have another solution, but I am not sure if it is state-fo-the-art, or even a feasible solution: I would like to separate two tasks:

* Write an Arduinno code to handle the sensors and create numeric data
* Write a Python code on my computer and compile it as an executable file on my computer
* Then somehow, I "extract" the processor of my comouter (Intel, by the way) and I plug it on the Arduinno board. The Arduinno sends the data to the processor, and the processor runs permanently the Python file and gives back data

So question:

* Is it possible overall?
* Was it ever made?
* What communication links are good for exchanging data between processor and Arduinno microchip: USB, Serial, Ethernet?
* How can I handle the input of the processor, so that it collects data from the Arduinno and then uses it in the Python code?

# Answer
It sounds like you need a lot of compute power. You can either put the sensors and AI on one device (and @majenko's suggestion of a Raspberry Pi would be a direction to pursue) or you need two devices, one to manage the data collection - Arduino, perhaps - and one to do the AI. We don't know enough about your post-processing and AI to make a good recommendation, but, as you already have a PC with Python running on it, an Arduino talking to the PC would be a good start.

You didn't say which Arduino you're considering, but as most people mean "Uno" when the speak of a generic Arduino, I'd just suggest that an Uno is far too under-resourced for the post-processing part of your project, but probably ideal for the data collection. Cross-compiling your Python code for an Uno still doesn't address its processing speed and memory size limitations.

There are, of course, a lot of "Arduino" products, some with considerably more resources, that may approach your needs - I'm thinking of the Arm-based boards, here - but I've no way of evaluating your project needs at that level.

My own first approach would be to use what you have, to start with: an Uno collecting data and sending it to your PC. Once you have something running, you'll understand the needs and issues better and if you still want a stand-alone solution at that point, you'll be much better able to make that choice.
> 2 votes

# Answer
I may handle this case like using pyserial library I just log the data to my laptop and then using python to do your Advance AI code part.

1. Send the sensor data as a combined String via Arduino serial port.
2. read it using pyserial library
3. add a data logging mechanism if you need or parallel process the data you gathered serially by cast them to their own data type.

Hope this may help you.

Thank you
> 1 votes

# Answer
For AI use there is the K210 based sipeed maix board. Dual core 400MHz, plus an AI coprocessor.
> 1 votes

# Answer
I suggest that you use a different family of processor than the 8-bit AVR chips that are supported by the Arduino IDE (and please fix your spelling errors, all the double-letter words are very distracting). A good example might the the Teensy 3.2 or Teensy 3.6 offered here https://www.pjrc.com/ "Version 3.6 features a 32 bit 180 MHz ARM Cortex-M4 processor with floating point unit" Arduino is programmed in C++, see if your code can be exported in C++ and import it into the IDE for compiling for the selected uC.
> 0 votes

---
Tags: arduino-mega, programming, python, datalogging, c-preprocessor
---


# Question
Title: Scope of RtcDateTime object when declared outside of a function
I'm trying to merge 2 Arduino samples, in order to be able to use DS3231 RTC module with ESP8266 WiFi simple web server.

My RTC library is this: https://github.com/Makuna/Rtc/wiki

Generally, to code runs ok (I have the Web server responses to my browser calls, and I think the DS3231 RTC code also works). But when I'm trying to use a variable from within the RTC object into the Web server function - I get nothing.

I thought declaring the 'now' object outside any function (Setup() nor Loop()) will make it global, and when I'll update it in the Loop() function using

```
now = Rtc.GetDateTime();

```

It will be available to other functions as well, but all I get is "0" when I try to print it.

My code is here: Definitions part:

```
#include <ESP8266WiFi.h>
#include <WiFiClient.h>
#include <ESP8266WebServer.h>

/* This block is for I2C protocol for DS3231 module (for normal hardware wire use below) */
#include <Wire.h> // must be included here so that Arduino library object file references work
#include <RtcDS3231.h>
RtcDS3231<TwoWire> Rtc(Wire);
/* The above block is for I2C protocol and DS3231 module  (for normal hardware wire use above) */

ESP8266WebServer server(80);
RtcDateTime now;

```

My Loop():

```
void loop(void) {
  now = Rtc.GetDateTime();
  Serial.println(now.Minute());
  server.handleClient();
  delay(500);

}

```

And all I get is "0" printed.

Any help would be appreciated!

# Answer
> 2 votes
As was suggested by more 'native' friends here - I'm 'Answering my question' to make things clear.

After a check and debug - I've found a mysterious behavior that happened to my DS3231 module. Probably a mistaken initializing set of calls - made it stop working - not getting time updates and not counting the time at all. (Freeze at 1/1/2000, 00:00:00).

Disconnecting it from power source, and taking out the battery - returned it to normal behavior, able to get time updates, and answering the calls from the library.

When that part solved - everything else went as easy as it should.

The code sample I posted in my question (declaring the 'now' object outside of setup() and loop() functions) made that object global, so another function (WebServer) can read its current value and use it internally.

Thanks everyone who looked at my problem and helped, It was a great lesson about how not to take anything as 'known' without double-checking.

---
Tags: c, rtc, variables
---


# Question
Title: NodeMCU second HARDWARE serial TX as a debug port
I'm using a NodeMCU board to send commands to my home electricity switching box - using RS485 communication.

For that, I've connected MAX485 TTL-to-RS485 converter module to my TX and RX pins.

Currently, I can see the serial commands (that my program sends via RS485) also on my Serial monitor (in Arduino IDE), because the CH341 on the NodeMCU is bridged to the serial pins of it.

My problem is that if I want to send debug strings to my Serial monitor (like 'time was updated using NTP') - the RS485 bus will get them also.

I found some documentation about second TX pin available that can be used for debug messages, but I have 2 questions:

1. Will it be a HARDWARE port? I don't want to load another library and deal with software Serial ports.
2. Is there a way to get its output via the USB cable connected between the NodeMCU and my computer? Or will I have to connect another USB converter externally to that port to get its output into computer?

Many thanks!

# Answer
ESP8266 Arduino core has Serial1 as write only hardware Serial on io 2 as TX. IO 2 is D4 on NodeMcu and Wemos D1 mini.

To use the USB chip of the NodeMcu/Wemos with Serial1 you could wire io 2 (D4) to TX. This would not disturb the flashing mode, because bootloader would still listen on standard Serial pins. I tested it.

And for RS485 adapter swap the Serial to io 13 (D7) as RX and io 15 (D8) as TX with the Serial.swap() command.
> 2 votes

---
Tags: serial, esp8266, arduino-ide, nodemcu
---


# Question
Title: about receiving float on matlab from ATmega32 Avr
\****i am using ATmega32 to send float and want to receive it on matlab,i send 4.85 from ATmega32 but on matlab i receive 4.260233679216239e-31...can any one help me..thanks in advance\** \**

```
    //Atmel studio code++++code for sending float from Atmega32
    union abc{ float fo; unsigned long lo; };
 union abc data;
int main(void)
 { usart_init();
 data.fo=4.85;
 while(1) {
for(int i=0; i<=24; i+=8)
{
    uart_send(data.lo>>i); }}}

 //Matlab code for receiving float
s=serial('COM1','BaudRate',9600);
fopen(s);
out=fread(s,1,'single');
 fclose(s);

```

# Answer
> 2 votes
i found the solution for this problem, i set a header before sending the data from ATmega32,and on Matlab i check the frame ,if it received correctly,i receive the data

```
//ATmega32 code
    float x =215.5;
    unsigned char *ptrx;
    int main(void)
    {   usart_init();
        //data.fo=12.85;

        ptrx=( unsigned char *) &x;
          while(1)
       {
        uart_send(0xAA);//equals to 170
        for(int i=0;i<4;i++){
        uart_send(*(ptrx+i));}

        x++;}}
    //on Matlab
    s=serial('COM1','BaudRate',9600);
    fopen(s);
     i=1;
    while i<1000
        header =fread(s,1,'uint8');

        if header==170//equal to 0xAA

     out=fread(s,1,'float');
    data(i)=out;

     i=i+1;
        end
     end
    fclose(s);

```

# Answer
> 0 votes
The binary representation of 4.260233679216239e-31 is `0x0d0a40a3`. The first two bytes (in big endian format) are `0x0d` and `0x0a`, which happen to be the ASCII characters CR and LF. These characters, in tandem, are often used as line terminators. My guess is that `uart_send()` is not doing what you think...

I suggest using `Serial.write()` instead. This way you won't have unwanted line terminators. And it will also make your problem on-topic with respect to this site.

Also, do not send the bytes repeatedly, send them only once, on demand. If you send them continuously, Matlab may catch the serial stream in the middle of a number, and assemble the bytes in the wrong order.

---
Tags: arduino-uno, arduino-ide, avr, matlab
---