# Question
Title: RFID with Adafruit fingerprint together not working in Arduino Uno
I have edited my Ccde and now the issue is both are working but not together.

```
#include <Key.h>
#include <Keypad.h>
#include <Adafruit_Fingerprint.h>
#include <SD.h>
#include <SPI.h>
#include<SoftwareSerial.h>

SoftwareSerial mySerial(0, 1);
SoftwareSerial mySerials(2, 3);

int read_count = 0, tag_count = 0;
int j = 0, k = 0; // Variabvles to iterate in for loops
char data_temp, RFID_data[12], data_store[12];
boolean disp_control;
char filename[4], fileText[30], names[10];
int atm[5];
uint8_t n, num, p;
char key;
int p1, p2, p3, p4, z;
char fid;

File myFile;
Adafruit_Fingerprint finger = Adafruit_Fingerprint(&mySerials);

const byte ROWS = 4; //four rows
const byte COLS = 4; //four columns
char keys[ROWS][COLS] = {
  {'1', '2', '3', 'A'},
  {'4', '5', '6', 'B'},
  {'7', '8', '9', 'C'},
  {'*', '0', '#', 'D'}
};

byte rowPins[ROWS] = {5, 4, 3, 2}; //connect to the row pinouts of the keypad
byte colPins[COLS] = {9, 8, 7, 6}; //connect to the column pinouts of the keypad

Keypad keypads = Keypad( makeKeymap(keys), rowPins, colPins, ROWS, COLS );

void setup() {
  finger.begin(57600);
  mySerial.begin(9600);
  Serial.begin(9600);

  while (!Serial) {
    ; // wait for serial port to connect. Needed for native USB port only
  }

  Serial.print("Initializing SD card...");

  if (!SD.begin(4)) {
    Serial.println("initialization failed!");
    while (1);
  }
  Serial.println("initialization done.");

  Serial.println("Please Place Your Card");

}

void RecieveData()
{

  if (mySerial.available() > 0)
  {
    data_temp = mySerial.read();
    RFID_data[read_count] = data_temp;
    read_count++;
  }
}
void ReadData()
{
  if (read_count == 12) {
    disp_control = true;
    for (j = 0; j < 12; j++) {
      data_store[j] = RFID_data[j];
    }

    int x = 0;
    for (int i = 9; i < 12; i++) {
      filename[x] = data_store[i];
      x++;
    }
    filename[3] = '.';
    filename[4] = 't';
    filename[5] = 'x';
    filename[6] = 't';
    filename[7] = '\0';

    myFile = SD.open(filename, FILE_READ);
    if (myFile) {

      // read from the file until there's nothing else in it:
      while (myFile.available()) {

        for (int i = 0; i < 20; i++) {
          fileText[i] = myFile.read();
        }

        int a, n = 0;
        for (int i = 0; i < 4; i++) {
          atm[a] = fileText[i];
          a++;
        }
        for (int i = 5; fileText[i] != '\0'; i++) {
          names[n] = fileText[i];
          n++;
        }
        fid = fileText[4];

        validate();

        myFile.close();
      }
    } else {
      // if the file didn't open, print an error:
      Serial.println("error opening test.txt");
    }
    read_count = 0;
    tag_count++;

  }
}
void validate() {

  Serial.print("Hello ");
  Serial.print(names);
  Serial.println();
  Serial.println();
  Serial.println();

  pin();

}

void pin() {
  Serial.println("Please Enter Your ATM PIN");

  p1 = keypads.getKey();
  while (p1 == NO_KEY) {
    p1 = keypads.getKey(); //UPDATE VALUE

  }
  Serial.print(p1 - 48);

  p2 = keypads.getKey();
  while (p2 == NO_KEY) {
    p2 = keypads.getKey(); //UPDATE VALUE
  }
  Serial.print(p2 - 48);

  p3 = keypads.getKey(); //UPDATE VALUE
  while (p3 == NO_KEY) {
    p3 = keypads.getKey(); //UPDATE VALUE
  }
  Serial.print(p3 - 48);

  p4 = keypads.getKey(); //UPDATE VALUE
  while (p4 == NO_KEY) {
    p4 = keypads.getKey(); //UPDATE VALUE
  }
  Serial.print(p4 - 48);
  Serial.println();

  if ((p1 == fileText[0]) && (p2 == fileText[1]) && (p3 == fileText[2]) && (p4 == fileText[3])) {
    Serial.println("Please verify Fingerprint");
  }
  else {
    Serial.println("Invalid. Buzzer!!!!");
  }
}
uint8_t getFingerprintID() {
  uint8_t p = finger.getImage();
  switch (p) {
    case FINGERPRINT_OK:
      Serial.println("Image taken");
      break;
    case FINGERPRINT_NOFINGER:
      Serial.println("No finger detected");
      return p;
    case FINGERPRINT_PACKETRECIEVEERR:
      Serial.println("Communication error");
      return p;
    case FINGERPRINT_IMAGEFAIL:
      Serial.println("Imaging error");
      return p;
    default:
      Serial.println("Unknown error");
      return p;
  }

  // OK success!

  p = finger.image2Tz();
  switch (p) {
    case FINGERPRINT_OK:
      Serial.println("Image converted");
      break;
    case FINGERPRINT_IMAGEMESS:
      Serial.println("Image too messy");
      return p;
    case FINGERPRINT_PACKETRECIEVEERR:
      Serial.println("Communication error");
      return p;
    case FINGERPRINT_FEATUREFAIL:
      Serial.println("Could not find fingerprint features");
      return p;
    case FINGERPRINT_INVALIDIMAGE:
      Serial.println("Could not find fingerprint features");
      return p;
    default:
      Serial.println("Unknown error");
      return p;
  }

  // OK converted!
  p = finger.fingerFastSearch();
  if (p == FINGERPRINT_OK) {
    Serial.println("Found a print match!");
  } else if (p == FINGERPRINT_PACKETRECIEVEERR) {
    Serial.println("Communication error");
    return p;
  } else if (p == FINGERPRINT_NOTFOUND) {
    Serial.println("Did not find a match");
    return p;
  } else {
    Serial.println("Unknown error");
    return p;
  }

  // found a match!
  Serial.print("Found ID #"); Serial.print(finger.fingerID);
  Serial.print(" with confidence of "); Serial.println(finger.confidence);

  return finger.fingerID;
}

int getFingerprintIDez() {

  uint8_t p = finger.getImage();
  if (p != FINGERPRINT_OK)  return -1;

  p = finger.image2Tz();
  if (p != FINGERPRINT_OK)  return -1;

  p = finger.fingerFastSearch();
  if (p != FINGERPRINT_OK)  return -1;

  Serial.print("Found ID #"); Serial.print(finger.fingerID);
  Serial.print(" with confidence of "); Serial.println(finger.confidence);
  return finger.fingerID;

  // found a match!

  /*z = finger.fingerID;
    if ((fid - 48) == z) {
    Serial.println("Success");
    }
    else {
    Serial.println("Fail");
    }*/
}

void loop() {
  RecieveData();
  ReadData();
  getFingerprintIDez();
  delay(50);
}

```

If I initialize in this format, then fingerprint works:

```
mySerial.begin(9600);
  finger.begin(57600);
  Serial.begin(9600);

```

And if I do it this way, then RFID works:

```
finger.begin(57600);
  mySerial.begin(9600);
  Serial.begin(9600);

```

I want both of them to work i.e I first scan the card, then verify the PIN and then it checks the validity of the fingerprint. But the issue is only one of them works at a time. If RFID works, then fingerprint doesn't even blink and if fingerprint works, RFID doesn't read.

# Answer
No surprise there. Your function says:

```
uint8_t p = finger.getImage();
if (p == FINGERPRINT_OK)
  z = finger.fingerID;

```

So what happens if `p` isn't `FINGERPRINT_OK`? This runs:

```
  if ((fid - 48) == z) {
    Serial.println("Success");
  }
  else {
    Serial.println("Fail");
  }

```

So `z` is uninitialized and so probably 0, `fid` was assigned some value along the way (and it doesn't seem to be 48). So what you get is the expression in the IF condition evaluates to false, 'Fail' is printed and the function returns.

Neglecting the poor structure of your code, magic numbers and all, you've failed to account for the case where there's *no* finger on the module. Aside from that, you're not even performing a fingerprint search (as I assume you intend); even when someone places their finger, all you're doing is grabbing the image and then reading the default value of `fingerID` which I believe is `0xffff` -- no template conversion or database search. Bottom line, you need to go back and study the original example, which is well commented with self-explanatory method names, before making any changes and writing your own stuff.
> 1 votes

---
Tags: arduino-uno, adafruit, rfid
---


title: MIFARE RC522 I2C Library

text:
# Question
Title: MIFARE RC522 I2C Library
I was looking at this link on RFID I2C interface. I added the library to arduino, but in `main.cpp`, I see an error:

> In function 'void setup()':
>
> sketch\_mar27a:16: error: no matching function for call to 'TwoWire::begin(int, int)'
>
> Wire.begin(SDA\_PIN, SCL\_PIN); // Initialize I2C

I looked at `Wire.cpp` file and found that there is no such member function overloaded with two parameters.

How should I fix the problem? Even if I fix this one problem, I am not sure if this code is working code.

Where can I find working code with I2C interface? I have resource problem and SPI PORT cannot be used.

The code:

```
#include <Wire.h>

#include "MFRC522_I2C.h"

#define SDA_PIN 5
#define SCL_PIN 6
#define RST_PIN 3

MFRC522 mfrc522(0x28, RST_PIN);  // Create MFRC522 instance.

void ShowReaderDetails();

void setup() {
  Serial.begin(9600); // Initialize serial communications with the PC
  Wire.begin(SDA_PIN, SCL_PIN); // Initialize I2C
  mfrc522.PCD_Init();   // Init MFRC522
  ShowReaderDetails();  // Show details of PCD - MFRC522 Card Reader details
  Serial.println(F("Scan PICC to see UID, type, and data blocks..."));
}

void loop() {
  // Look for new cards
  if ( ! mfrc522.PICC_IsNewCardPresent()) {
    return;
  }

  // Select one of the cards
  if ( ! mfrc522.PICC_ReadCardSerial()) {
    return;
  }

  // Dump debug info about the card; PICC_HaltA() is automatically called
  mfrc522.PICC_DumpToSerial(&(mfrc522.uid));
}

void ShowReaderDetails() {
  // Get the MFRC522 software version
  byte v = mfrc522.PCD_ReadRegister(mfrc522.VersionReg);
  Serial.print(F("MFRC522 Software Version: 0x"));
  Serial.print(v, HEX);
  if (v == 0x91)
    Serial.print(F(" = v1.0"));
  else if (v == 0x92)
    Serial.print(F(" = v2.0"));
  else
    Serial.print(F(" (unknown)"));
  Serial.println("");
  // When 0x00 or 0xFF is returned, communication probably failed
  if ((v == 0x00) || (v == 0xFF)) {
    Serial.println(F("WARNING: Communication failure, is the MFRC522 properly connected?"));
  }
}

```

# Answer
SPI is a multi-slave bus. Unless you've run out of free pins to use for CS, or you have slaves that don't play nice, you can connect your RFID module to the SPI bus as well. Also your sketch will most likely compile if you only correct the offending line to simply `Wire.begin()`. Your library uses the standard Wire library but assumes the target is an ESP8266, whose version of Wire has an extended `begin()` method.

But this may all be no use since the MFRC522 you have (assuming it's the cheap blue module) is hardwired to use only the SPI interface. Unless you're ready to modify the PCB (cut traces, etc) as others have done.
> 1 votes

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


# Question
Title: servo.read() starts at negative value, no matter where servo actually is
I don't like how my servo quickly jumps to the default middle position, so I commented out the line where `DEFAULT_PULSE_WIDTH` is set in `Servo.cpp`:

```
//servos[this->servoIndex].ticks = usToTicks(DEFAULT_PULSE_WIDTH);

```

Unfortunately while this stopped the servo from moving on execution of `attach`, the position of the servo is now showing up as `-52`!

Just running the following in `setup()` is enough to generate the bug:

```
int servo_pin = 53;
servo.attach(servo_pin);
Serial.print("Initial position: ");
Serial.println(servo.read());  //returns -52

```

This last line returns `-52` no matter what position the servo is actually in, which has bad consequences (its initial movement is way off).

Note I get the same behavior when I set the `DEFAULT_PULSE_WIDTH` to `0` in `Servo.h`.

I am using a Mega -- an Elegoo clone -- on Windows 10.

Note I got the ideas for stopping the servo from moving on initialization from these threads:

# Answer
> 4 votes
You seem to be starting from a fundamental misunderstanding of RC hobby type PWM servos. To put it simply, they do not electronically output any position information.

Until you have commanded a position and the servo loop has had a fair chance to seek to that, the position of the servo is utterly and entirely unknowable.

This is stated in the documentation of the Arduino servo system:

```
read()

Description

Read the current angle of the servo (the value passed to the last call to write()).

```

As this explains, the returned value is not the *physical* position, but rather the last *commanded* position.

Until you have commanded a position (something your code does not do) the return value of this call is physically meaningless.

---
Tags: arduino-mega, servo
---


# Question
Title: Multiple power supply for arduino controlled dc motor
I’m working on a project where I want to control a motorized fader with an arduino. I have a dual H-Bridge board to control the motor, but the thing is that it is a 10V motor. I’m thinking of using a secondary power supply on the H-Bridge to power the motor with a proper voltage. So here is where my lack of electrical knowledge comes into play. My H-Bridge has the following connections: a set of +/- poles to provide the power to the motors, 4 motor control pins (2 per motor to control their direction) and 4 motor power pins (2 per motor).

If I was using the Arduino as the power source for the DC motor, I would connect the +5v rail to the + terminal ot the H-Bridge and the Gnd rail to the - terminal, which would, in turn act as the ground return for the control pins.

If I am to use an external power supply, how do I wire it properly so I don’t blowup the arduino or the h-bridge? I’m guessing that my secondary power supply will be connected to the +/- poles of the H-Bridge and the the - pole will also get connected to the Gnd rail of the arduino?

Is that correct?

# Answer
> 1 votes
According to the datasheet on the L298 IC the connections you described should be right. First I would recommend to connect 10v to the + and - rails and measure the voltage on the logical inputs if it is 0 or lower than 3v than that should be ok to connect an arduino. Also now you can connect an additional 5v power supply with an the -5v connected to the - rail on the board and try to connect the +5v volts to the inputs and measure the voltages on the output (or connect an motor) if everything is ok you can try to connect your Arduino.

---
Tags: arduino-uno, power, motor, h-bridge
---


# Question
Title: LCD Weather Station - "Press To Start" Function
I've been trying to make a weather station using a I2C LCD Display and a DHT11, I know, the DHT11 is a bit low res and all that, but it came with the kit I ordered, so it's okay.

However, I'm trying to have it display like a "title" screen, and after a 2sec delay it should proceed to say "Welcome!" and "Press to Start", and wait there until the button is pressed, and after the button is pressed it should proceed to show the temp and humidity.

However it doesn't seem to mind any of the functions added, unless I set the "if" statement at the beginning of the loop to "LOW", then for some reason, the program stops at "Welcome!" and "press to start". If I change the "if" statement condition to "HIGH" it just proceeds straight through to the temp and humidity.

```
#include <DHT.h>
#include <Wire.h>
#include <LiquidCrystal_I2C.h>

//CONSTANTS
#define DHTPIN 3
#define DHTTYPE DHT11
DHT dht(DHTPIN, DHTTYPE);

LiquidCrystal_I2C lcd(0x27, 16, 2);

//Variables
int chk;
float hum;  //Stores humidity value
float temp; //Stores temperature value

const int buttonPin = 6;

int buttonState = 1;

void setup()
{
  pinMode(12, OUTPUT);
  pinMode(13, OUTPUT);
  pinMode(buttonPin, INPUT);
  Serial.begin(9600);
  dht.begin();
  lcd.begin();
  lcd.clear();
  delay(1000);
  lcd.setCursor(0, 0);
  lcd.print("WeatherMate");
  lcd.setCursor(0, 1);
  delay(250);
  lcd.print("Press 'Start'");
  delay(1000);;
  if (buttonState = 0)
  {
    lcd.clear();
    lcd.setCursor(0, 0);
    lcd.print("Welcome!");
    lcd.setCursor(0, 1);
    lcd.print("Press Start");
  }
}

void loop() {
  buttonState = digitalRead(buttonPin);
  if (buttonState = 1) {
  delay(500);

  hum = dht.readHumidity();
  temp = dht.readTemperature();
  if (temp <= 25) {
    digitalWrite(13, LOW);
    digitalWrite(12, HIGH);
  }
  if (temp >= 25) {
    digitalWrite(13, HIGH);
    digitalWrite(12, LOW);
  }
  Serial.print("Humidity: ");
  Serial.print(hum);
  Serial.print(" %, Temp: ");
  Serial.print(temp);
  Serial.println(" Celsius");

  lcd.setCursor(0,0);
  lcd.print("Temp: ");
  lcd.print(temp);
  lcd.print(" ");
  lcd.print("C");
  lcd.setCursor(0,1);
  lcd.print("Hum:  ");
  lcd.print(hum);
  lcd.print(" %");

  delay(500); //Delay 2 sec.

}
}

```

Anyone? I'm stuck on this one.

# Answer
> 1 votes
As Majenko points out in his comment, a couple of your `if` statements have the assignment operator (ie. `=`) whereas you are actually after the comparison operator (ie. `==`).

```
if (buttonState = 0)

```

should be:

```
if (buttonState == 0)

```

And

```
if (buttonState = 1) {

```

should be:

```
if (buttonState == 1) {

```

When an assignment is used, the `if` statement will execute if the value being assigned is a non-zero. For more information see Using assignment as a condition expression? over on Stack Overflow.

---
Tags: arduino-uno, lcd, arduino-uno-smd
---


title: Ultrasonic sensor confusion

text:
# Question
Title: Ultrasonic sensor confusion
Here is a code snipet for ultrasonic sensor

```
digitalWrite(trigpin,HIGH);
delayMicroseconds(10);
digitalWrite(trigpin,LOW);

duration=pulseIn(echopin,HIGH);

```

Assume `trigpin` and `echopin` pins are already defined.

Now according to Arduino reference guide `pulseIn` funcion:

> Reads a pulse (either HIGH or LOW) on a pin. For example, if **value** is **HIGH**, `pulseIn()` waits for the pin to go **HIGH**, starts timing, then waits for the pin to go **LOW** and stops timing. Returns the length of the pulse in microseconds or 0 if no complete pulse was received within the time out.

So shouldn't I be getting 10 microseconds as my answer, since since initial state of echo pin is low, now when the reflected sound hits receiver, echo pin goes high, the timer gets started and when and when the pulse ends the echo pin goes low again and since pulse sent was of 10 microseconds of length, the ans should be 10, but any ultrasonic program I have seen uses this code to find the duration the ultrasonic wave takes since it gets emitted to the time it gets into the receiver.

# Answer
What happens is:

* You send a pulse of 10 ms with TTL signal. This is the first line in the picture below.
* Than you call pulseIn. This waits for the echo pulse.
* The echo pulse will become high when reflected. This happens internally in the module. This is the second line.
* The echo pulse will stay high depending on the time it took to be echoed back and makes a pin high (echo pin). This is the third line.
* Than your pulseIn command returns with the time (of the echo pin length).
> 2 votes

---
Tags: arduino-uno, arduino-ide, pulsein
---


# Question
Title: keypad storing problem (void value not ignored as it ought to be)
I am trying to input 11 numbers only by the use of keypad but the problem is whenever i use this code. It gave me this error.

Here's my code. Help please.

```
#include <SoftwareSerial.h>
#include <LiquidCrystal.h>
SoftwareSerial mySerial(6, 5);
int table[] = { 0, 0, 0 };
#include <Keypad.h>
#include <Wire.h>
LiquidCrystal lcd(7, 8, 9, 10, 11, 12);
const byte ROWS = 4; //four rows
const byte COLS = 3; //three columns

char keys[ROWS][COLS] = {
    { '1', '2', '3' },
    { '4', '5', '6' },
    { '7', '8', '9' },
    { '*', '0', '#' }
};
byte rowPins[ROWS] = { 2, 3, 17, 16 }; //connect to the row pinouts of the keypad
byte colPins[COLS] = { 15, 14, 13 }; //connect to the column pinouts of the keypad
int count = 0;
Keypad kpd = Keypad(makeKeymap(keys), rowPins, colPins, ROWS, COLS);
char entryStr[13]; // This can hold up to 4 digits
int i = 0;
char n1, n2, n3;
char buf[15]; // i put here***
void setup()
{
    Wire.begin();
    Serial.begin(9600);
    Serial.begin(9600);
    lcd.begin(20, 4);
    ask();
}

void loop()
{
    Wire.requestFrom(2, 3); // request 6 bytes from slave device #2 for(int i=0;i<3;i++) {

    int c = Wire.read(); // receive a byte as character
    Serial.print(c);
    table[i] = c;
    Serial.print('\t');
    // print the character } Serial.print('\n'); Serial.print(table[0]); Serial.print('\t'); Serial.print(table1); Serial.print('\t'); Serial.print(table[2]); Serial.print('\n');

    //if(table[0]<=8) //{ //Serial.print("Flame Detected!"); //Serial.println("Level1");
}
void ask()
{

    lcd.clear();
    lcd.setCursor(0, 0);
    lcd.print("Enter no1.:");
    lcd.setCursor(0, 1);
    lcd.print("(starts with 0)");
    lcd.setCursor(1, 2);
    n1 = GetNumber(buf, sizeof(buf) - 1);

    Serial.print(n1);

    delay(1);

    lcd.clear();
    lcd.setCursor(0, 0);
    lcd.print("Enter no2.:");
    lcd.setCursor(0, 1);
    lcd.print("(starts with 0)");
    lcd.setCursor(1, 2);
    n2 = GetNumber(buf, sizeof(buf) - 1);

    Serial.println(n2);
    delay(1);
    lcd.clear();
    lcd.setCursor(0, 0);
    lcd.print("Enter no3.:");
    lcd.setCursor(0, 1);
    lcd.print("(starts with 0)");
    lcd.setCursor(1, 2);
    n3 = GetNumber(buf, sizeof(buf) - 1);

    Serial.println(n3);
    delay(1);
    Serial.println(n1);
    Serial.println(n2);
    Serial.println(n3);
    lcd.clear();
    lcd.setCursor(0, 0);
    lcd.print("list of numbers ");
    lcd.setCursor(0, 1);
    lcd.print("will be shown press");
    lcd.setCursor(1, 2);
    lcd.print("reset if wrong");

    delay(7000);
    lcd.clear();
    lcd.setCursor(0, 0);
    lcd.print("Numbers Stored:");
    lcd.setCursor(0, 1);
    lcd.print("no1.:0");
    lcd.print(n1);
    lcd.setCursor(1, 2);
    lcd.print("no2.:0");
    lcd.print(n2);
    lcd.setCursor(2, 3);
    lcd.print("no3.:0");
    lcd.print(n3);
}
void GetNumber(char* result, const int maxLength)
{
    char key = kpd.getKey();
    int i = 0; // how far through buffer we are
    while (key != '#') {
        switch (key) {
        case NO_KEY:
            break;

        case '0':
        case '1':
        case '2':
        case '3':
        case '4':
        case '5':
        case '6':
        case '7':
        case '8':
        case '9':

            lcd.print(key);
            if (i < maxLength) {
                result[i++] = key;
                result[i] = 0; // terminating null
            }
            break;

        case '*': // backspace
            if (i > 0) {
                i--;
                result[i] = 0; // terminating null
            }

            break;
        }

        key = kpd.getKey();
    }

} // end of GetNumber

```

# Answer
The `GetNumber()` function is coded in such a way as to pass the collected value back through the `result` parameter.

> ```
> void GetNumber(char* result, const int maxLength)
>
> ```

So, when you use the `GetNumber()` function, you pass it `buf`, and after the call returns, you will find the result in the `buf` char array.

However, you appear to be trying to store the result in `n1`, `n2`, and `n3`, which are `char` type variables, and can hold only one character, or a number between `0` and `255`, neither of which can hold an 11-digit string of numbers like you wish.

A `char` is an 8-bit variable. An `int` (on Arduino Uno) is a 16-bit value and can hold at most `32,768`. Even an `unsigned long`, a 32-bit variable of all positive numbers, can hold a maxiumum value of `4,294,967,295`, which gets at most all 9-digit numbers, and some 10-digit numbers.

You would probably be better off holding the numbers as character arrays just like `buf`, and passing those as the first parameter of `GetNumber()` instead of `buf`:

```
char n1[15], n2[15], n3[15];
...
GetNumber(n1, sizeof(n1) - 1);
...
GetNumber(n2, sizeof(n2) - 1);
...
GetNumber(n3, sizeof(n3) - 1);

```

If you do that, then you can get rid of `buf` entirely.

Alternatively, you can keep `buf` as the temporary holder of the incoming string and use `strncpy()` to copy the string from `buf` to `n1` (etc.):

```
GetNumber(buf, sizeof(buf) - 1);
strncopy(n1, buf, sizeof(n1));

```

This method uses more memory, as you have `buf` taking up space, but it has an advantage that you can later do validation or error checking on the user input before you overwrite `n1` or the others with the new value.
> 1 votes

# Answer
Your `GetNumber` function is defined to return void (nothing) while you use it as if it returns the number typed.

change GetNumber to return a int and the end of it do a `atoi` using the buffer and return the result.
> 2 votes

---
Tags: arduino-ide, c++
---


# Question
Title: SH1106 - Transferring long buffer via SPI
I am using an SH1106 and am creating my own driver for it. Nearly everything is doing great with about 2/3ms send time using **transfer16**. I did notice however that I can use **transfer** with a buffer and length to give a 1ms display time; something that'd be extremely useful.

For reference before here is the datasheet: http://support.technologicalarts.ca/docs/Components/OLED13-SPI/SH1106.pdf

So the working solution is this:

```
SPI.beginTransaction(settings);
//
for (int page = 0; page < 8; page++)
{
    digitalWrite(DC, LOW);
    SPI.transfer(0xB0 + page);
    SPI.transfer(0x02);
    SPI.transfer(0x10);
    digitalWrite(DC, HIGH);

    for (int column = 0; column < 128; column += 2)
        SPI.transfer16(buffer[(page * 128) + column]);
}
digitalWrite(DC, LOW);
//
SPI.endTransaction();

```

This for each of the 8 pages writes the 128 bytes 2 at a time. I want to write the 128 bytes in a single call. This would be something like this:

```
SPI.transfer(buffer + (page * 128), 128);

```

This however sort of inverts the display. It literally turns every pixel on for some reason and I can't figure out why. I am just using a few bytes set to **255** for testing and with the original method this works perfect.

Am I using the call wrong? Is there a limit to the buffer size I could use, I haven't really seen anything about that at the moment. I tried changed the pointer arithmetic but wasn't successful. I tried moving the 128 bytes into a temporary location and use that but still nothing.

Obviously this isn't major and maybe I could somehow improve the transfer in other ways but if you have any advice I'd love to have it

**----- EDIT -----**

I have had some luck now with using the transfer with buffer method when I changed the page datatype to a uint8\_t. It also caused a few more issues however and I am not sure what is causing them.

* Firstly with a fast display rate the display inverts itself once again with all pixels on.
* With a delay between display calls, it works! But after a few seconds those pixels slowly go away, something I have never experienced before.

Here is the edited code:

```
SPI.beginTransaction(settings);
//
for (uint8_t page = 0; page < 8; page++)
{
    SPI.transfer(0xB0 + page);
    SPI.transfer(0x02);
    SPI.transfer(0x10);

    digitalWrite(DC, HIGH);
    SPI.transfer(buffer + (page * 128), 128);
    digitalWrite(DC, LOW);
}
//
SPI.endTransaction();

```

It's hard to explain whats actually happening. But without a large delay between the calls of the buffer transfer method the screen freaks out and will maybe invert completely if it's too often. Even with the large delay the pixels randomly vanish over time, something I have never actually seen.

The 2 byte send method doesn't have any of these problems. No delay will work fine.

# Answer
> 1 votes
You seem to have understood the following but just for clarification:

`transfer16(uint16_t word)`, as the name implies, shifts 16bits/2bytes instead of just 8bits/1byte like `transfer(uint8_t byte)`.

`transfer(uint8_t* buffer, unsigned int size)` on the other hand takes a pointer and the amount of **bytes** to shift.

Now to pointer arithmetic. Operations on pointer variables are dependent on their explicit data type(as well as processor architecture!). Therefore, in our case, a `+1` on `uint8_t* val` will advance the pointer by 8bits. `+1` on `uint32_t* val` will do so by 4bytes/32bits.

**Check `buffer`'s data type**

It should be any of `char, unsigned char, uint8_t, int8_t`

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


# Question
Title: Max current per pin is 40 mA. But it is always 40 mA?
I need to calculate resistor for a PNP transistor.
To do this I need to know the voltage and current.
I know voltage is 5 volts as it is easy to find in the internet, but how about current? I mean people say the maximum current is 40 mA, but will it be 40mA? Does the arduino supply 40mA as long as it is able to? Or for example if i just connect a single diode it magically "calculates" the current it needs and supplies, let's say, 20mA?

# Answer
> 2 votes
It means that a pin can give (source) at max. 40 mA. However, if a components uses more, than the Arduino cannot give it and as a result the pin becomes unusable.

So you never should exceed 40 mA. And 20 mA is adviced.

+5V and GND pins can take more, however there is also a maximum on 'groups' of GPIO pins. See more information here, below is an excerpt of the page.

However, I doubt that your transistor needs so much, most (if not all) are directly controllable from a GPIO pin and if you need to calculate a resistor value, just make sure you are safely above the minimum current needed to switch the transistor.

# Answer
> 1 votes
Figure on driving the PNP hard so it turns in into full saturation. To do that, you want to pull as much current from the base as you can. Treat the PNP like it is one diode drop of voltage away from 5V when on. So 4.3V generally (maybe 4.5, check your part specs). Then you want the Arduino to sink 20 mA. 4.3V/20mA = 215 ohm resistor. Use a 200, 220, both are standard values and should well to protect the Arduino output transistors and drive the PNP into saturation. Maybe go as low as 150 ohm to drive a little harder. If the PNP needs less to turn on full, go a little higher resistance value.

---
Tags: power, current, voltage
---


# Question
Title: Optical Incremental Encoder Reading using Arduino UNO
I have a HP Optical Incremental Encoder (256 CPR) in which

* Pin 1 = A,
* Pin 2 = VCC,
* Pin 3 = GND,
* Pin 8 = B.

I already read and see tutorials for rotary encoder such this one:
https://playground.arduino.cc/Main/RotaryEncoders

I have written a program that is supposed to print out the position of my encoder, however I am only getting zeros in my serial monitor. I want to be able to use interrupts. I would like to actually return the position in degrees of my encoder as we rotate it.

**I was able to get it to work. I wasn't connecting my pin properly to my Arduino.**

```
    #include <LiquidCrystal.h>

LiquidCrystal lcd(8, 9, 4, 5, 6, 7);

#define encoderPinA 2
#define encoderPinB 3
#define CPR 256
volatile int counter =0;
volatile boolean flag;

volatile int var_degrees =0;

void setup() {

  pinMode(encoderPinA, INPUT);
  pinMode(encoderPinB, INPUT);
  Serial.begin (9600);
  attachInterrupt(digitalPinToInterrupt(encoderPinA), isr, RISING);
  lcd.clear();

}

void loop() {

   if(flag == true){
        var_degrees = ((360/256.0)*counter);
        Serial.println(var_degrees);
        lcd.setCursor(0, 1);
        lcd.print("Degrees: ");
        lcd.setCursor(9, 1);
        lcd.print(var_degrees);
        flag = false;
  }

}
//Interrupts

void isr_2(){
flag = true;
  if(digitalRead(encoderPinA) == HIGH){
    if(digitalRead(encoderPinB) == LOW){
      counter = counter -1; //COUNTER CLOCK WISE
    }
    else{
      counter = counter +1; //CW
    }
  }
  else{
    if(digitalRead(encoderPinB) == LOW){
      counter = counter + 1; //CW
    }
    else{
      counter = counter - 1 ; //CCW
    }
  }
}

```

# Answer
You are attaching your interrupt incorrectly. You should not pass in the pin number, but the interrupt number. There is also a handy function that converts a pin to the right interrupt number:

```
attachInterrupt(digitalPinToInterrupt(pin), ISR, mode);

```

So, your code should be:

```
attachInterrupt(digitalPinToInterrupt(encoderPinA), isr,CHANGE);

```

Also, you should declare your `counter` variable to be `volatile`, since it is modified within an ISR, and thus the compiler should not assume that it doesn't change even though the `loop()` never changes it:

```
volatile int counter = 0;

```
> 1 votes

---
Tags: arduino-uno
---


# Question
Title: ATMega328P receiver and transmitter pins
I am trying to connect Bluetooth, GSM and GPS to the ATMega328P, but since it has only 1 RX and 1 TX, can I use the digital pins of ATMega328P as RX/TX pins.

# Answer
It sounds like you are after the SoftwareSerial library.

> The SoftwareSerial library has been developed to allow serial communication on other digital pins of the Arduino, using software to replicate the functionality (hence the name "SoftwareSerial"). It is possible to have multiple software serial ports with speeds up to 115200 bps. A parameter enables inverted signaling for devices which require that protocol.

Although, SoftwareSerial does come with limitations. The major one is that only one serial port can receive data at a time.
> 1 votes

# Answer
Sounds like you need something with 4 hardware serial ports. 2560 processor.
> 1 votes

# Answer
You can use SoftwareSerial as mentioned above, and just wire the TX/RX to the desired digital pins. You will have to enable and disable the serial ports when you want to read/write to a specific port (Bluetooth/GSM), but that is not terribly difficult. I wrote a blog post on SoftwareSerial with an HM-10 Bluetooth module - there you can see how I wired and coded the SoftwareSerial via digital pins.

Arduino IoT with Bluetooth
> 0 votes

---
Tags: atmega328
---


# Question
Title: 6 wire 3 digits 7 segment display and arduino question
Here's a brain teaser for you:

I have the following 3 digit 7 segment display that has only 6 wires

Experimentally I found out how it works, even though I don't understand it, but anyways every segment is lit by a combination of HIGH and LOW of certain two pins, the combinations are below:

So I tried to make it work, but encountered the following problem (as you can see in the first picture): if, for example, I want to activate the segment that requires pin 5 high and pin 6 low, it also activates the other segments that require 5 to high, because apparently if a digital output is not high, it's automatically pulled to ground, and that's a problem. I tried by setting the other pins I don't use in a segment to high, but then the segments that require 6 low are being activated, so that didn't work.

Other option I have would be transistors or a tri-state buffer, but for that I need all 12 digital inputs of arduino for the two states of each pin of the display.

Hope you understand what my problem is and maybe you have some advice on how to solve it.

Thanks in advance!

Edit: I managed to drive every segment individually using a small delay, and it works if the sketch has only the code for the display, but as soon as I add more code (for the temperature sensor I want to use) it starts to malfunction. You can find the code below.

LE: I managed to make it work by leaving only the display function in the loop and calling every 5 seconds the function for the temperature sensor. It still refreshes the display when it is called, but that doesn't bother me.

Here's the code: http://www.mediafire.com/file/2bs5r8u5rkzpu8g/6w\_3D\_7S\_display.rar

# Answer
What you have is a Charlie-Plexed display like the one in the picture below. You need one more wire than this example because your display also includes the decimal point. If you go through the electrical paths where for each pair one line is driven high, the other is driven low and all other lines are set to input, only one LED at a time will be forward biased.
> 1 votes

---
Tags: arduino-nano, 7-segment
---


# Question
Title: What is the lowest resistance pot that is useful with an analog input?
## Background

I've dabbled in electronics since my parents gave me a 150-in-1 kit in the 1970's but never had formal training. My dad repaired Honeywell mainframes so taught me to solder when I was 8. I have a decent set of equipment like irons, parts, meters, etc. and realize I know enough to be dangerous, which is why I avoid mains-powered stuff. I'm not a newbie but am all too aware of the many holes in my knowledge. I'm doing this for fun and in a way that allows for failures to be expected, cheap, and educational.

## Project

I have a WS2812b LED strip connected to an Arduino Uno and am using various animation libraries to drive it. The goal is to move to a pro mini once the hardware is more settled and use it for creative lighting inside my house or garage. I started with just the strip and let it display different animations in a sequence based on time but then wanted to attach a button which would advance to the next animation. After implementing debouncing it worked fine and I moved on to adding a potentiometer to select the speed of the current animation; increasing or decreasing the delay between each 'frame'. Of interest here is I was using old pots (panel mount not for typical board use - hence I had to solder wires to them just to use them in any configuration) and not doing any ohms law calculations, just hooking up the hardware and tuning the values for mapping the detected voltage to the desired delay by checking printed output from the serial monitor.

I'm happy with the general setup when using a breadboard but when I went to solder something more permanent on perfboard I ran into a problem; the speed control wouldn't work. I'm sure the first pot I used was 10k but when I checked it with the meter it registered as completely open so I figured I had blown it. Thinking that I needed to control the current I read posts like this one and this one about limiting current I felt better and proceeded to replace the pot with a 25 ohm version thinking that the only difference would be in calibrating the values for mapping the detected voltage to the desired delay. The behavior I got was randomly fluctuating values for the delay and when I hooked up the prototype using USB to my laptop I could see that the analogread() values were fluctuating wildly within a range even when I wasn't manipulating the pot yet nothing I did could get it to be consistent. My first thought was that there was a problem with ground so I rechecked the connections but they all tested fine, including still reading 25 ohms along the outside terminals and varying values on the wiper consistent with rotating it along its path from end to end. When I gave up on my protoboard and returned the circuit back to the breadboard I replaced the full size pot with a 10k small one meant for breadboards and the speed control works again. This leads to my question.

## Question

Is there a minimum value for a potentiometer connected to an analog input of an arduino, or is it more likely that there was an issue with my soldering job on the protoboard? I don't have a picture of the board because I've already desoldered components from it but I can tell you that it was my first attempt at perfboard soldering and it would not win any prizes, sort of the 'face only a mother could love' sort of thing. If it matters, I was using analog input A2.

# Answer
> 3 votes
Assuming you wired it correctly (ie. you put the wiper to the analog input) your first setup looked like this:

Your big problem here is the current flow through the pot. Using Ohms Law the current would be:

```
I = V / R
I = 5 / 25
I = 0.2A  (200 mA)

```

That is too much to be drawing from the 5V pin and it could easily drag down the voltage to the rest of the board. Also the power would be:

```
W = I * V
W = 0.2 * 5
W = 1W

```

One watt is a lot to put through a pot, and you may well have burned the track inside it.

---

> So, if I included a 10k resistor on either side of the pot that should address the current issue but it leaves the question of whether the remaining 25-ohm range is too small for the ADC to register distinct values, ...

The 10k resistor will stop the current problem, but now the range in the voltage divider will be ridiculously small. The setup will now look like this:

Unfortunately the range you are going to read with the analog input is going to be (voltage divider formula):

```
Vout = Vin * (R2 / (R1 + R2))

```

With the wiper at one end R1 will be 10000 and R2 will be 10025 and with the wiper at the other end it will be vice-versa. So the voltage you get will be:

```
Vout = 5 * (10000 / (10025 + 10000))
Vout = 5 * 0.499
Vout = 2.497

```

Or:

```
Vout = 5 * (10025 / (10025 + 10000))
Vout = 5 * 0.501
Vout = 2.503

```

In other words you will always be reading about 2.5V and therefore your analog read will always return around 512, which won't be much use to you.

---

> I'm going with a larger value pot (10k or 25k) ...

That sounds like a sensible value. A 10k pot will only draw:

```
I = V / R
I = 5 / 10000
I = 0.5 mA

```

That is a reasonable current draw and the analog input will still read it fine.

---

As Majenko points out in his answer you don't want a whole lot more than that resistance because of the optimal input impedance of the ADC converter (10k). A very high resistance would mean only a small current would flow into the analog input pin.

---

## How to use your 25 ohm pots

If you want to use your existing 25 ohms pots because of their physical appearance, then a **small** resistor in series could reduce the current to a reasonable amount and still give a good reading range. For example, 330 ohms on the "high" side (and nothing between the low side and ground).

```
Vout = 5 * (330 / (355 + 330))
Vout = 5 * 0.193
Vout = 0.963

```

Or:

```
Vout = 5 * (355 / (355 + 330))
Vout = 5 * 0.581
Vout = 2.591

```

That is now going to give you a reading between 0.96V and 2.59V which, whilst not the full range of 0V to 5V should give you reasonable differentiation as you turn the pot. And the current through it would be:

```
I = V / R
I = 5 / 355
I = 0.014A (14 mA)

```

Thus the power would be:

```
W = I * V
W = 0.014 * 5
W = 0.070 (70 mW)

```

---

## References

# Answer
> 1 votes
Most potentiometers take the form of a 3-terminal device, where the two outside terminals are a fixed resistor and the middle terminal adjusts the tap from one extreme to the other.

simulate this circuit – Schematic created using CircuitLab

In this configuration, you end up creating a simple voltage divider. You should pick the potentiometer's voltage such that the fixed portion does not draw more current than necessary, regardless of the tap position. (The arduino's analog input itself does not draw any significant current really.)

If you use a 1k pot, then the current always flowing from 5V to ground is 5mA, which should not tax the Arduino's voltage regulator too much. If you used a 100 ohm pot, then the current would be 50mA -- not likely to damage things, but certainly more than is necessary just to operate a voltage divider.

If you use a 1M-ohm pot, then you are working with 5 micro-Amps, and at that low current, noise from the power supply starts to interfere with your analog readings.

As for your actual setup, it really depends on how you had it wired, etc.

# Answer
> 1 votes
There is no lower limit on the value of a potentiometer that you can use with the Arduino, however the lower the resistance the more current it will pull from the power supply and, if it's too low a resistance and isn't rated for a high enough power, could burn out and catch on fire.

There is, however, an upper limit on the resistance of a potentiometer that you can use.

As a general rule of thumb the *output impedance* of what you connect to an ADC should be no more than around a tenth of the *input impedance* of the ADC. On the Arduino the ADC has around a 1MΩ input impedance, so you shouldn't connect anything with more than around 100kΩ output impedance.

For a potentiometer (well, for any voltage divider) the output impedance is the value of the two halves of the resistance in parallel. For a 10K potentiometer with the wiper set right in the middle that's 5K for each half, so the formula is:

```
     R1 * R2   5000 * 5000
Ro = ------- = ----------- = 2500Ω
     R1 + R2   5000 + 5000

```

As you can imagine that's the maximum output impedance at that point. For example, if you adjust it so it's 9000Ω and 1000Ω it works out as:

```
     R1 * R2   1000 * 9000
Ro = ------- = ----------- = 900Ω
     R1 + R2   9000 + 9000

```

So from that you can interpolate that the maximum value potentiometer you can reliably use would have an output impedance of 100kΩ, which is (100000/2500) 40 times more than the 10kΩ one, so 400kΩ is really the maximum you can use.

The main reason for this limit is that the ADC's front-end is a capacitor, and that capacitor has to charge up to the voltage of the input. That charge time is limited by the current available to flow into the pin, and with too high an output impedance the current available is too low and the capacitor can't charge to the right voltage in the limited *acquisition time* of the ADC.

The datasheet itself speaks of the output impedance limit:

> The ADC is optimized for analog signals with an output impedance of approximately 10 kΩ or less. If such a source is used, the sampling time will be negligible.

So they don't recommend anything more than 10kΩ, which equates to a maximum of 40kΩ for the potentiometer's resistance.

# Answer
> 0 votes
The Analog Digital Converter (ADC aka analog input) has only a small capacitance, which has to be loaded to do a measurement. This is normally no problem, even with high resistance potentiometers. Also - if you are using the potentiometer correctly - it is very unlikely, that you have blown it (with 5V supply voltage there is only a current flow of 0.5mA through a 10k potentiometer). The current that flows in the ADC is also very small.

The point in using a potentiometer for providing analog input is, that the total resitance is always the same, regardless of the position. See this schematic:

simulate this circuit – Schematic created using CircuitLab

Both voltage dividers have the same total resistance (10kOhm). If you set the position of the potentiometer to the middle, they have exactly the same output: 2.5V. Moving the slider of the potentiometer is the same as taking some of the resistance from one of the resistors on the right and adding it to the other. So a potentiometer is a variable voltage divider. Normally you want the current, that flows through this voltage divider to be small, because it would be only wasted to heat the resistor strip. If you are using a potentiometer with 25 Ohm total resistance while having a 5V power supply, the current trough it would be 200mA, which is pretty much. And if your power supply cannot give you that much, your application will get really instable.

So I see 2 possible problems:

1. You used the potentiometer the wrong way, or
2. You made a soldering mistake

EDIT:

From your comment I read, that you are not familiar enough with the rules, how a voltage divider really works. So I will try to explain a bit more.

A potentiometer looks like this on the inside. It consists of one strip of a resistive material. Each side of the strip is connected to one of the outer pins. The full length of the strip has a constant resistance, say 10kOhm for now. The knob of the potentiometer is connected to a contact, that slides over this resistive strip, making electrical contact with it. When you measure the resistance between one of the outer pins and this middle contact, you get a resistance that is dependent on the position of the contact.

Let's say, we want to measure the resistance between the left contact and the middle contact (the slider). If the slider is very close to the left pin, the resistance we measure is very small, since there is only very few resistive material between the contacts. As we move farer away from the left side of the strip, the measured resistance gets bigger.

At the same time (when we are moving away from the left side of the strip) we are moving towards the right side of the strip, essentially decreasing the resistance between the middle contact and the right side of the strip.

Now we have to do some maths: Ohm's Law states that voltage is resistance multiplied by current

```
U = R * I

```

We connect the outer pins of the potentiometer to our 5V power supply and to ground. So `U = 5V`. And we know the total resistance between these pins: `10 kOhm`. To get the current, that flows through our potentiometer, we reform the above formula to

```
I = U / R

```

Using the above values we calculate the current through the potentiometer to be `0.5mA`. The current through the first part of the resistor strip (say from left to the middle contact) is the same as in the second part (from middle contact to right), as the current has nowhere else to go.

Now we position the middle contact exactly in the middle of the resistive strip. This means that you have half of the total resistance on each side: `5 kOhm`. In electrical circuits the voltage is always measured in reference to ground. So here only the ground side matters for the rest of the calculation. We again need Ohm's Law:

```
U = R * I = 5kOhm * 0.5mA = 2.5V

```

As we want to read this with an Arduino (which uses a 10 bit ADC --\> values in the range of 0 to 1023) we get about 512. (This may vary a bit because of fluctuations and distortion)

When we position the middle contact at the ground end of the resistive strip, we have a ground-side resistance of about `0 Ohm`. So we get `0V` at the middle pin and a ADC value of about 0.

When we position the middle contact at the 5V end of the resistive strip, we have a ground-side resistance of about `10 kOhm`. Using Ohm's Law we get `5V` at the middle pin, which translates to an ADC value of about `1023`.

Changing the position also changes the ratio of the resistance on ground-side and 5V-side of the strip. But when you (as said in your comment) just add big resistors to both sides of the 25 Ohm potentiometer, you will only we able to control this really small part of the total resistance. So this will not work.

Note: Not every potentiometer has a linear changing resistive strip. Some have a logarithmic or exponential changing strip.

---
Tags: arduino-uno, analogread, arduino-pro-mini, potentiometer
---


title: Generating Sinusoid Signal of 40khz

text:
# Question
Title: Generating Sinusoid Signal of 40khz
I would like to generate a sinusoidal signal of 40kHz using Arduino Uno. Maximum I could generate was 1kHz, using bit banging, fast PWM. Do you have ideas of how to boost it to 40kHz?

I used "Advanced Arduino Sound Synthesis" for inspiration. https://makezine.com/projects/make-35/advanced-arduino-sound-synthesis/

# Answer
> 0 votes
Let's first do some maths.

* You want 40,000 cycles per second.
* Each cycle needs splitting up into samples. For example, let's use 128 samples.
* Assume you want an 8-bit amplitude resolution.

Each second of signal would need 40,000 cycles * 128 samples. That's 5120000 samples per second.

If using PWM to generate the audio that's 256 clock cycles (28) per sample. That means 5120000 * 256 = 1,310,720,000.

That means a "carrier frequency" of over 1.3GHz. There's no way an Arduino can do that.

If instead you used a simple DAC (e.g., an R-2R ladder) connected to the 8 pins of port D (that's pins 0-7 on the Uno) you don't need the 256 clock cycles per sample. That means that you have to output a new sample to PORTD 5,120,000 times per second. That's outputting at over 5MHz.

With some well crafted assembly code that *might* be possible. The Arduino certainly won't be able to do anything else at all at the same time.

You would be much better off using a chip that has audio capabilities and DMA. Maybe a Teensy 3.x would be a better choice for your project.

---
Tags: arduino-uno, pwm, frequency, signal-processing
---


title: I2C EEPROM "hangs" on endTransmission()

text:
# Question
Title: I2C EEPROM "hangs" on endTransmission()
I am working on the 24LC256 EEPROM, wired as such, except 3.3v to the EEPROM, with 'scope clamped on SDA and SCL. I'm using an address scanner script with a few tweaks, 57600 baud, 10kOhm pullups, 100000 I2C clock, and some serial prints for snooping:

```
for(address = 1; address < 127; address++ ) {
    Serial.printf("\n%02x", address);
    Wire.beginTransmission(address);
    Serial.printf(",");
    error = Wire.endTransmission();
    Serial.printf(".");
    Serial.flush();
    if (error == 0) {
      Serial.printf("I2C device found at address 0x%02x", address);
      Serial.println("  !");
      nDevices++;
    }
    ...

```

When the loop hits the address corresponding to the jumpers (pins 1, 2, 3 correspond to address 0b01010abc, aka 0x5?, where ? = binary encoding of those pins), it just sorta hangs:

```
4c,.
4d,.
4e,.
4f,.
50,

```

(here I have 1, 2, 3 all low, so the chip responds to addr 0x50). Since it's hitting `,` but not `.`, I know it's hanging at `Wire.endTransmission()`. It always hangs at endTransmission at the address encoded by the jumpers. SCL is low and SDA is high.

Scope trace looks fine counting through the addresses.

Trace of address not found.

Trace of hanging at address.

gif of cycling through last few addresses.

I'm on an Adafruit Feather nrf52 BLE, if that matters.

# Answer
Because of the way that the I2C library works, the only place it **can** hang is on the endTransmission. The other calls just buffer stuff up in memory.

There is probably some electrical issue. For example, the pull-up resistors might be better as 4.7k.

There is another library which handles transmission a bit differently which might resolve the hanging.

However if it is hanging there are probably other issues (cable lengths, pull-up resistors, noise) that are the underlying issue.

The standard library waits in a tight loop for certain interrupts to arrive, and if they don't arrive it hangs indefinitely.

---

> except 3.3v to the EEPROM

You may well need a level-shifter. It's all very well only sending out 3.3V to the EEPROM, but the rest of the circuit is dealing in 5V not 3.3V. You can get suitable level shifters quite cheaply.

Why are you using 3.3V anyway? That chip can handle 5V. I have a post about that exact chip which works fine there.
> 0 votes

---
Tags: i2c
---


# Question
Title: How do I correctly choose components for my current project?
Previously I asked a question that was a bit to broad so I'm narrowing the focus to a single component board of my design.

I have a set of 3 luckylight R/G bar graphs (datasheet here: https://cdn-shop.adafruit.com/datasheets/KWL-R1230XDUGB.pdf) A 5.1 V 2A power source (recycled ac/dc converter voltage tested datasheet here: http://pdf1.alldatasheet.com/datasheet-pdf/view/322359/BOTHHAND/M1-10S05.html) a series of 5 SN74HC595 (for controlling the LED multiplexing) and an Arduino Nano.

The purpose of the bar graphs is to show the player how much of his available system energy he/she is using.

The first three bars of the graph are set to Red, the next 5 are yellow, and the final 4 are green.

As various components are switched on, or other activities drain the power of the engine core, a program level command will switch the multiplexing array to have them shut off.

The problem I'm having is getting enough power to each of the LEDs of the bar graph without overloading the IC pins on the Arduino or shift registers and making the colors appear correctly.

I know I could use Darlington arrays, or a bunch of transistors to keep the power going to the LEDs on a line independent of the ICs, but i'm not sure the right way to go about this. I have a few ULN2803 Darlingtons and a lot of 2n2222a transistors.

(Also my current Arduino code only has, at max, 8 LEDs from each register on at the same time, with a forward voltage of 2.4 volts and 20mA per LED. There are three cycles to my code because the bar graphs have three shared cathode pins that run three 2x4 matrices.)

Additionally I don't know precisely how to calculate the resistor values I would need for this arrangement to maintain the same voltage being applied to the 24 simultaneously running LEDs and get their brightness to be equivalent. Currently i'm noticing LEDs that are farther down the 595 logic chain are receiving less power and appearing weaker. (yes i have been running them off the power coming from the Arduino thus far)

Hopefully this is a narrow enough question.

# Answer
> 0 votes
According to this datasheet the 595 can drive up to 6 mA per output pin with a maximum of 20 mA for the input to the chip (so, 2.5 mA if you are driving all outputs).

Since your LEDs are quoting a forward current of 25 mA it seems that you will fall somewhat short of providing the 25 mA per LED.

There are higher power shift registers, eg. the TPIC6B595.

You might want to consider a multiplexing LED driver such as the MAX7219. I have a post about using that chip.

Your LEDs sound similar to the things that the MAX7219 is designed to drive. It also has inbuilt current-limiting with the current selected by a single resistor.

It isn't clear from your question whether you have the common anode or common cathode device, but you need a common cathode for the MAX7219.

---

The MAX7219 is not that expensive if you buy it from eBay. For example search for "MAX7219 kit". I found hits for 4 x MAX7219 for $US 9.75 including boards, capacitors and LEDs. Just discard the LEDs (8 x 8 dot matrix) and run the wires to your bargraph.

---

> As they are designed to run 7 segment displays how would I connect it to transfer from my current 16 bit binary shift setup ...

They can run in a couple of modes (see the Decode Mode register) and one is to send arbitrary bits. Since you can program in any combination of bits (in my link above there is an array which does a CP437 font) you can therefore make up any combination of bars on and off. I would get one as an experiment (buy one of those kits from eBay) and try the idea out. It will be a lot less mucking around than 595 chips, transistors, current-limiting resistors, and so on.

There are various kits around, some are pre-soldered (which you won't want), some come with SMD chips and some with through-hole chips. Choose SMD or through-hole depending on your confidence with soldering SMD parts.

---

> I know on my shift registers pins 1-8 go to the LED anodes and Pins 9-11 go to transistors that run the cathodes. Can you help me understand the pin connections to get the MAX to run this?

Looking at your bar graph specs:

You have 3 rather than 8 cathodes (pins 14, 9 and 8 are duplicates of 1, 6 and 7). So, you would run the cathode wiring (1, 6, 7) to the first 3 "digit" pins (2, 11 and 6) on the MAX7219. The other 8 wires (marked anodes) would go to the 8 anodes (2, 3, 4, 5, 10, 11, 12, 13).

As you have only used 3 cathode pins you could wire up a second bargraph using another 3 cathode pins (and run the anodes in parallel). That way a single MAX7219 can drive two bargraphs, giving you a total of 24 bars, each of which can show red, green, or yellow at one time.

---

## Example wiring and code

I ordered a couple of the LED modules and worked out a schematic for them:

One MAX7219 can drive two of the modules.

Example of wiring:

Example code:

```
#include <SPI.h>

 // define max7219 registers
const byte MAX7219_REG_NOOP        = 0x0;
const byte MAX7219_REG_DIGIT0      = 0x1;
const byte MAX7219_REG_DIGIT1      = 0x2;
const byte MAX7219_REG_DIGIT2      = 0x3;
const byte MAX7219_REG_DIGIT3      = 0x4;
const byte MAX7219_REG_DIGIT4      = 0x5;
const byte MAX7219_REG_DIGIT5      = 0x6;
const byte MAX7219_REG_DIGIT6      = 0x7;
const byte MAX7219_REG_DIGIT7      = 0x8;
const byte MAX7219_REG_DECODEMODE  = 0x9;
const byte MAX7219_REG_INTENSITY   = 0xA;
const byte MAX7219_REG_SCANLIMIT   = 0xB;
const byte MAX7219_REG_SHUTDOWN    = 0xC;
const byte MAX7219_REG_DISPLAYTEST = 0xF;

// which groups of bars we are addressing
const byte BARS_1_4   = MAX7219_REG_DIGIT0;
const byte BARS_5_8   = MAX7219_REG_DIGIT1;
const byte BARS_9_12  = MAX7219_REG_DIGIT2;
const byte BARS_13_16 = MAX7219_REG_DIGIT3;
const byte BARS_17_20 = MAX7219_REG_DIGIT4;
const byte BARS_21_24 = MAX7219_REG_DIGIT5;

// within a group, which one (from the left)
const byte BAR1_RED = 0x80;
const byte BAR2_RED = 0x20;
const byte BAR3_RED = 0x08;
const byte BAR4_RED = 0x02;

const byte BAR1_GREEN = 0x40;
const byte BAR2_GREEN = 0x10;
const byte BAR3_GREEN = 0x04;
const byte BAR4_GREEN = 0x01;

// yellow is done by adding red and green
const byte BAR1_YELLOW = BAR1_RED + BAR1_GREEN;
const byte BAR2_YELLOW = BAR2_RED + BAR2_GREEN;
const byte BAR3_YELLOW = BAR3_RED + BAR3_GREEN;
const byte BAR4_YELLOW = BAR4_RED + BAR4_GREEN;

void sendByte (const byte reg, const byte data)
  {
  digitalWrite (SS, LOW);
  SPI.transfer (reg);
  SPI.transfer (data);
  digitalWrite (SS, HIGH);
  }  // end of sendByte

void setup () {

  SPI.begin ();

  sendByte (MAX7219_REG_SCANLIMIT, 5);   // show 6 digits
  sendByte (MAX7219_REG_DECODEMODE, 0);  // using an led matrix (not digits)
  sendByte (MAX7219_REG_DISPLAYTEST, 0); // no display test

  // clear display
  for (byte col = 0; col < 8; col++)
    sendByte (col + 1, 0);

  sendByte (MAX7219_REG_INTENSITY, 7);  // character intensity: range: 0 to 15
  sendByte (MAX7219_REG_SHUTDOWN, 1);   // not in shutdown mode (ie. start it up)
}   // end of setup

void loop ()
 {
  // send various test combinations
  sendByte(BARS_1_4, BAR1_RED | BAR2_GREEN | BAR3_RED | BAR4_GREEN);
  sendByte(BARS_5_8, BAR2_RED);
  sendByte(BARS_9_12, BAR2_YELLOW);
  sendByte(BARS_13_16, BAR1_RED | BAR2_GREEN | BAR3_RED | BAR4_GREEN);
  sendByte(BARS_17_20, BAR2_YELLOW);
  sendByte(BARS_21_24, BAR1_RED | BAR2_RED);
 }  // end of loop

```

This is documented in my page about the MAX7219.

---
Tags: power
---


# Question
Title: string.indexOf() always returns a non-zero value
I am developing a hardware project which contains a facility to change the stored password by any user, if he/she knows the current password.The new password is stored in arduino eeprom. In the main screen, if the user enters the current password, door is unlocked from inside. . The issue faced here is that the point where current password is entered by user, it works fine, but **I want to check that '#' is not entered by user in the new password which is not performed properly.**

Because in the main screen, when user presses '#' key, change password function is called up, where user is asked to enter current password.

Here is the screenshot of the circuit prepared from fritzing.

The code snippet for entering new password is as under.

```
lcd.clear();
lcd.print("New Passkey:");
lcd.setCursor(0, 1);
while (j < 4)
{
  char key = keypad4x4.getKey();

  if (key)
  {
    new_password[j++] = key;
    lcd.print(key);
    tone(buzzer, 1000, 50);

    if (j == 4)
    {
      lcd.print("4 reached");
      delay(1000);
      new_password[5] = '\0';
      String str = String(new_password);
      if (str.indexOf('#'))    /** this condition comes out to be true always i.e. always returns a non-zero value**/
      {
        tone(buzzer, 200, 700);
        lcd.clear();
        lcd.print("Invalid Entry");  /** It is printed everytime on lcd**/
        delay(2000);
        key = 0;
        changePass();
        break;
      }
      else  /** this block is not entered, so new password is not saved in EEPROM **/
      {
        for (int i = 0; i < 4; i++)
        {
          EEPROM.write(i, new_password[i]);
        }
        lcd.print(" Done......");
        delay(1000);
        break;
      }
    }
  }
}

```

and

`new_password[5]` is used to store new password entered by user.

Now, I am using a string variable to store this new password.

I am using `string.indexof()` function to identify whether this new password contains a '#' character anywhere in it.But it seems that when I put this in an if block in code, it becomes true everytime.I have added comments at respective positions to highlight the problem faced by me. I have tested this code in Proteus simulator, and actual project too.

So, my issue is this one, **even if correct password is entered by user,without '#', then also, string.indexOf('#') condition becomes true(returns a non-zero value everytime) and thus even valid password is not saved in EEPROM**. I guess I was able to explain my query accurately, please go through the code, and tell me where I am wrong, because I have gone through it many times and could not find the exact issue. Thanks in advance

# Answer
> 1 votes
The problem here is that `indexOf` returns the position of the character in the string, or *-1 if it's not found*.

In C `0` is `false` and *everything else is true*. That includes `-1`.

However, your usage if String here to just check for one character is incredibly wasteful and should be avoided. Instead, use `strchr`:

```
if (strchr(new_password, '#') != NULL) {
    ... contains # ...
}

```

---
Tags: arduino-uno, string, eeprom
---


title: Only one of 4 LEDs are lighting up

text:
# Question
Title: Only one of 4 LEDs are lighting up
Before you ask - I've checked that the LEDs worked before putting them in my circuit. They all work.

I've connected 4 LEDs, shown in the arrangement below, up to my Adruino Lilypad. Pin 9 was used as the + 5V, the "- pin" was used as ground. In the schematic below, the "1" represents pin 9.

simulate this circuit – Schematic created using CircuitLab

When I start my sketch, I set pin 9 to high to check that all the LEDs are working. (this is a PWM pin so I write, `analogWrite(9, 255);`). At this point, only D5 lights up. If I connect up the two wires connecting R9-D6 and R10-D7, then both D5 and D8 light up... but never D7 or D6?

Doing some basic circuit calcs, the total resistance of the circuit is 100 Ohms (1 / (1 / (100 + 100)) + (1 / (100 + 100))). I'm powering from the usb connection to the computer so power source should be 5 V. Total current draw should therefore be 50 mA? Is that too much? If so, why does only D5 - or D5 and D8 when adjusting the circuit - light up?

# Answer
> 2 votes
Those LEDs are 3.3V forward voltage. With two in series you need at least 6.6V to light them up.

---
Tags: led, current
---


title: Arduino RFID tag scanning problems

text:
# Question
Title: Arduino RFID tag scanning problems
For a school project, I'm using an Arduino Uno and a Parallax RFID together with some other components, I used a script I got from Instructables for reading my serial input from the RFID (link: `http://www.instructables.com/id/Wiring-and-programming-the-Parallax-RFID-Serial-Ca/`) To use this serial data, you need to include an if loop in your loop function to check if the scanned tag equals the previous one. If it doesn't, the tag gets used further in the program. This doesn't allow scanning the same tag twice in a row. But I need that for my project. I have tried to work around it, but I can't seem to get it working, I always create a loop of unlimited scans or some other inregularities. Here's my code:

```
/* Libraries that need to be manually installed:
Blynk libraries: https://github.com/blynkkk/blynk-library/releases/download/v0.5.1/Blynk_Release_v0.5.1.zip
LiquidCrystal_I2C library: https://cdn.instructables.com/ORIG/FVH/K8OQ/J8UH0B9U/FVHK8OQJ8UH0B9U.zip
 */
#define BLYNK_PRINT Serial
#include <SoftwareSerial.h>
#include <BlynkSimpleShieldEsp8266.h>
#include <ESP8266_Lib.h>
#include <Wire.h>
#include <LiquidCrystal_I2C.h>
#include <Servo.h>
//#include <ThingSpeak.h>

//Setting up the Blynk wifi connection
#define ESP8266_BAUD 9600
char auth[] = "auth";

//Setting up the virtual pins
WidgetTerminal terminal(V1);
BLYNK_WRITE(V1){}
int freeSpots = 5;
BLYNK_READ(V2)
{
  Blynk.virtualWrite(V2, freeSpots);
}

//Setting up the RFID
#define RFIDEnablePin 8
#define RFIDSerialRate 2400
String RFIDTAG=""; //Holds the RFID Code read from a tag
String DisplayTAG = ""; //Holds the last displayed RFID Tag

//Setting up the LCD
LiquidCrystal_I2C lcd(0x27, 2, 1, 0, 4, 5, 6, 7, 3, POSITIVE);

//Setting up the serial connection
SoftwareSerial EspSerial(2, 3);
ESP8266 wifi(&EspSerial);

//Setting up the servo
Servo slagboom;

//Tag database
char tags[7][5] = {"6196", "6753", "5655", "69EC", "9FFC"};
char owners[7][5] = {"per1", "per2", "per3", "per4", "per5"};
int statuses[7] ={0};

//unsigned long channelNumber = 461353;
//const char * APIKey = "IHFFREPE9XUNSN94";

void setup() {
  //Serial communication
  Serial.begin(RFIDSerialRate);
  EspSerial.begin(ESP8266_BAUD);
  //RFID pin setup
  pinMode(RFIDEnablePin,OUTPUT);
  digitalWrite(RFIDEnablePin, LOW);
  //Blynk startup
  Blynk.begin(auth, wifi, "ssid", "pass");
  //LCD startup
  lcd.begin(16,2);//16 kolommen, 2 rijen
  lcd.backlight();
  //Servo startup
  slagboom.attach(10);
  slagboom.write(35);

  //ThingSpeak.begin(client);

  //Blynk terminal printing test
  delay(1000);
  slagboom.detach();
  terminal.println(F("Terminal printing succesfull"));
  terminal.flush();

}

void loop() {
  if (Serial.available() > 0)
  {
    ReadSerial(RFIDTAG);
  }
  if (DisplayTAG != RFIDTAG)
  {
    DisplayTAG=RFIDTAG;
    tagCompare(RFIDTAG);
  }
}

//Function for comparing the tag to the database
void tagCompare(String tagToCompare)
{
  char lastTag[5];
  tagToCompare.toCharArray(lastTag, 5);
  int i = 0;
  while (i < 5)
    {
      if (strcmp(tags[i], lastTag) == 0)
        {
          terminal.print(owners[i]);
          if (statuses[i] == 0)
          {
            lcd.clear();
            lcd.setCursor(0,0);
            lcd.print("Welkom, ");
            lcd.setCursor(0,1);
            lcd.print(owners[i]);
            statuses[i] = 1;
            freeSpots--;
            digitalWrite(RFIDEnablePin, HIGH);
            slagboom.attach(10);
            slagboom.write(145);
            delay(1000);
            digitalWrite(RFIDEnablePin, LOW);
            slagboom.write(35);
            delay(500);
            slagboom.detach();
            terminal.println(F(" heeft de parking betreden."));
            terminal.flush();
          }
          else
          {
            lcd.clear();
            lcd.setCursor(0,0);
            lcd.print("Tot ziens ");
            lcd.setCursor(0,1);
            lcd.print(owners[i]);
            statuses[i] = 0;
            freeSpots++;
            digitalWrite(RFIDEnablePin, HIGH);
            slagboom.attach(10);
            slagboom.write(145);
            delay(1000);
            digitalWrite(RFIDEnablePin, LOW);
            slagboom.write(35);
            delay(500);
            slagboom.detach();
            terminal.println(F(" heeft de parking verlaten."));
            terminal.flush();
          }
          //ThingSpeak.writeField(channelNumber, 1, i, APIKey);
          Blynk.run();
        }
      i++;
      }
  i = 0;
}

//Function for reading the tag
void ReadSerial(String &ReadTagString)
{
  int bytesread = 0;
  int val = 0;
  char code[10];
  String TagCode="";

  if(Serial.available() > 0)
  {
    if((val = Serial.read()) == 10)
    {
      bytesread = 0;
      while(bytesread<10) // Reads the tag code
      {
        if( Serial.available() > 0)
        {
          val = Serial.read();
          if((val == 10)||(val == 13)) // If header or stop bytes before the 10 digit reading
          {
            break; // Stop reading
          }
          code[bytesread] = val; // Add the digit
          bytesread++; // Ready to read next digit
        }
      }
      if(bytesread == 10)  // If 10 digit read is complete
      {
        for(int x=6;x<10;x++) //Copy the Chars to a String
        {
          TagCode += code[x];
        }
        ReadTagString = TagCode; //Returns the tag ID
        while(Serial.available() > 0) //Burn off any characters still in the buffer
        {
        Serial.read();
        }

      }
      bytesread = 0;
      TagCode="";
    }
  }
}

```

Any help would be very much appreciated. Thanks in advance.

Edit: here's the changes I made to the loop():

```
void loop() {
  if (Serial.available() > 0)
  {
    ReadSerial(RFIDTAG);
  }
  unsigned long millisScanned;
  if (DisplayTAG != RFIDTAG)
  {
    DisplayTAG=RFIDTAG;
    tagCompare(RFIDTAG);
    millisScanned = millis();
  }
  unsigned long millisReference = millisScanned + 10000;
  if ((DisplayTAG == RFIDTAG) && (millis() >= millisReference))
  {
    tagCompare(RFIDTAG);
    millisScanned = millis();
  }
}

```

# Answer
> 1 votes
If you wish to allow even for duplicate scans, but only want to check it if the RFID reader returns a new scan string, then you don't even need `millis()`

```
void loop() {
  static bool pendingTag = false;
  if (Serial.available() > 0)
  {
    ReadSerial(RFIDTAG);
    pendingTag = true;   // Indicate that this is a new scan to check
  }
  if (pendingTag)
  {
    tagCompare(RFIDTAG);
    pendingTag = false;  // The tag is checked, no need to check again
    DisplayTAG=RFIDTAG;  // Not even sure if you use this anywhere else.
  }
}

```

---
Tags: arduino-uno, rfid
---


title: Traffic light light system with sensors

text:
# Question
Title: Traffic light light system with sensors
I'm trying to make a traffic light system with a ultrasonic range sensor as well as a light dependant resistor. I'm trying to make it so that the default setting is 2 seconds red light 1 second yellow 2 seconds green then 1 second yellow, this will then repeat until something else happens - I've got this working fine.

Then I want 2 different states.

One where if something comes with 10cm of the sensor then the buzzer will beep and the yellow light must blink on and off 10x with intervals of 0.1ms. When the object moves away it must then return to the default setting.

Secondly I want it when the LDR detects that the light has dropped below a level the red light will turn on and stay on until a object approaches the sensor. When an object is near the sensor it must then turn the red light off and turn the Green light on.

Here is all the code i have so far and i cant figure out why its not working. Any help would be appreciated Thanks

```
    #define ECHOPIN 3
    #define TRIGPIN 2
    float distance;
    long distancecm;

    int RED = 13;
    int YELLOW = 12;
    int GREEN = 11;

    int piezoPin = 8;

    int sensorpin = A0;
    int sensorvalue = 0;

    void setup() {
      pinMode(RED, OUTPUT);
      pinMode(YELLOW, OUTPUT);
      pinMode(GREEN, OUTPUT);
      Serial.begin(9600);
      pinMode(ECHOPIN, INPUT);
      pinMode(TRIGPIN, OUTPUT);
      }

    void distancesensor()
      {
      digitalWrite(TRIGPIN, LOW);
      delayMicroseconds(2);
      digitalWrite(TRIGPIN,HIGH);
      delayMicroseconds(10);
      digitalWrite(TRIGPIN,LOW);
      distance = pulseIn(ECHOPIN, HIGH);
      distancecm = distance/29.1/2;
      if (distancecm <=10);
        for (int j=1; j<=5; j=j+1)
        {
         tone(piezoPin, 1, 500);
         digitalWrite(YELLOW, HIGH);
         delay(100);
         break;
         }
    }

    void lightsensor()
      {
      sensorvalue = analogRead(sensorpin);
      if (sensorvalue > 500)
        digitalWrite(RED,HIGH);
        digitalWrite(TRIGPIN, LOW);
        delayMicroseconds(2);
        digitalWrite(TRIGPIN,HIGH);
        delayMicroseconds(10);
        digitalWrite(TRIGPIN,LOW);
        distance = pulseIn(ECHOPIN, HIGH);
        distance = distance/58;
        while (distance >10)
          digitalWrite(RED,LOW);
          digitalWrite(GREEN,HIGH);
          digitalWrite(TRIGPIN, LOW);
          delayMicroseconds(2);
          digitalWrite(TRIGPIN,HIGH);
          delayMicroseconds(10);
          digitalWrite(TRIGPIN,LOW);
          distance = pulseIn(ECHOPIN, HIGH);
          distance = distance/58;

       }

    void loop() {
      distancesensor;
      lightsensor;
      digitalWrite(RED, HIGH);          //RED ON
      delay(2000);                      //WAIT 2 SECONDS
      digitalWrite(RED, LOW);           //RED OFF
      delay(200);
      distancesensor;
      lightsensor;
      digitalWrite(YELLOW, HIGH);       //YELLOW ON
      delay(1000);                      //WAIT 1 SECOND
      digitalWrite(YELLOW, LOW);        //YELLOW OFF
      delay(200);
      distancesensor;
      lightsensor;
      digitalWrite(GREEN, HIGH);        //GREEN ON
      delay(2000);                      //WAIT 2 SECONDS
      digitalWrite(GREEN, LOW);         //GREEN OFF
      delay(200);
      distancesensor;
      lightsensor;
      digitalWrite(YELLOW, HIGH);       //YELLOW ON
      delay(1000);                      //WAIT 1 SECOND
      digitalWrite(YELLOW, LOW);        //YELLOW OFF
      delay(200);
      distancesensor;
      lightsensor;
      //REPEAT
      }

```

# Answer
The photo of your circuit doesn't really show, how all the components are wired. For this you should either draw a schematic (which you can do with the schematic tool directly in the question editor) or provide a good visible wiring diagram like from Fritzing (though a proper schematic would be better).

For now I cannot see any wrong wiring, though you definitely should recheck it and add a proper diagram to your question.

For your code I will shortly sketch the functionality of non-blocking code and a state machine:

1. **Non-blocking code:** Task, that require a long amount of time (this means long for a microcontoller; seconds are long in this context), you should not use code, which blocks the whole program execution, until the task is completed. Instead you should only shortly check, if there is an action to be taken. If not, quickly proceed with other code. This enables you to do, which seems to be multitasking. For timed sequences you can use the `millis()` function. It returns the number of milliseconds since the program has started and overflows after 50 days. The following code saves the timestamp, when the LED was toggled the last time and checks, if enough milliseconds have passed since the last time. This way you can do something else in the meantime (like checking the state of your sensors). Also refer to the `BlinkWithoutDelay` example of the Arduino IDE.

```
unsigned long timestamp = 0;
unsigned long interval = 500;
...
void loop(){
  if(millis() - timestamp > interval){
    digitalWrite(led_pin, !digitalRead(led_pin));
    timestamp = millis();
  }
}

```
2. **State machine:** A state machine is code, that holds it's current state in a variable, thats mostly numeric. This variable is read at every loop cycle and used to determine, which piece of code is to be executed. In your case you would have states for "red light on", "yellow light on", "green light on", "distance lower than 10cm" and "LDR reports low light condition". Each on this gets it's own number. For convenience you should use an enum. Now on every loop cycle we use a switch case to go to the right code depending on the state. For your case you would set the state code with non-blocking behavior as described above. Then you only need transitions between the states, by setting the state variable.

```
enum STATE {STATE1, STATE2, STATE3};
STATE state = STATE1;
...
void loop(){
  switch(state){
    case STATE1:
      digitalWrite(led1_pin, HIGH);
      if(millis() - timestamp > interval){
        digitalWrite(led1_pin, LOW);
        state = STATE2;
      }
      break;
    case STATE2:
      // doing whatever this state needs to do and then do transition with setting state variable
      break;
    case STATE3:
      // doing whatever this state needs to do and then do transition with setting state variable
  }
}

```

For designing the states and transitions it sometimes makes sense to sketch them on paper. A bubble with a names is a state and then you connect these states with arrows.

Since you want to check the sensors in every state, you should do this outside of the `switch` statement. The measurement functions then do nothing else but the measurement and setting the `state` variable accordingly (so no `digitalWrite()` or `delay()` in there).
> 0 votes

---
Tags: arduino-uno
---


title: How to reset ESP8266 wifi module

text:
# Question
Title: How to reset ESP8266 wifi module
I have programmed `ESP8266` to make it accessible over the network using below program.

**First Program**

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

//SSID and Password of your wifi router
const char* ssid = "Moto";
const char* password = "reset1234";

ESP8266WebServer server(80);

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

  WiFi.begin(ssid, password);     //Connect to your WiFi router
  Serial.println("");

  // Wait for connection
  while (WiFi.status() != WL_CONNECTED) {
    delay(500);
    Serial.print(".");
  }

  //If connection successful show IP address in serial monitor
  Serial.println("");
  Serial.print("Connected to ");
  Serial.println(ssid);
  Serial.print("IP address: ");
  Serial.println(WiFi.localIP());  //IP address assigned to your ESP

  server.begin();                  //Start server
  Serial.println("HTTP server started");
}

void loop() {
  server.handleClient();          //Handle client requests
}

```

It is working fine, What is the way to reset it to run below program? I wanted to send AT commands on serial monitor using below program which has been uploaded successfully but not responding AT commands on Serial Monitor, as ESP8266 is running above program and showing output of above program on running below program on Serial Monitor.

I want to reset ESP8266 so it responds to below program. What is the way ?

```
Connected to Moto
IP address: 192.168.43.115
HTTP server started

```

**SecondProgram**

```
#include "SoftwareSerial.h"

SoftwareSerial esp8266(2, 3); // RX, TX

void setup()
{
  Serial.begin(9600); // serial port used for debugging
  esp8266.begin(9600);  // your ESP's baud rate might be different
}

void loop()
{
  if(esp8266.available())  // check if the ESP is sending a message
  {
    while(esp8266.available())
    {
      char c = esp8266.read();  // read the next character.

      Serial.write(c);  // writes data to the serial monitor
    }
  }

  if(Serial.available())
  {
    delay(10);  // wait to let all the input command in the serial buffer
    Serial.write("Hello");
    // read the input command in a string
    String cmd = "";
    while(Serial.available())
    {
      cmd += (char)Serial.read();
    }
    // send to the esp8266
    esp8266.println(cmd);
  }
}

```

# Answer
> 3 votes
You need to reinstall the AI Thinker AT firmware.

Here's how you do it: How to flash ESP8266 firmware update ESP-01 AI thinker

Last time I did it I used the esptool.py program, and used the ai-thinker-0.9.5.2.bin firmware (there's two versions on there, the default 115200 baud, and a 9600 baud variant).

On Linux I then used the command:

```
foo@bar:~$ ./esptool.py --port /dev/ttyUSB0 --baud 57600 write_flash 0 ai-thinker-0.9.5.2.bin
Connecting....
Detecting chip type... ESP8266
Uploading stub...
Running stub...
Stub running...
Configuring flash size...
Auto-detected Flash size: 512KB
Flash params set to 0x0000
Compressed 520192 bytes to 165297...
Wrote 520192 bytes (165297 compressed) at 0x00000000 in 29.0 seconds (effective 143.3 kbit/s)...
Hash of data verified.

Leaving...
Hard resetting...

```

This was, of course, with GPIO0 held LOW for programming mode (I actually use an adaptor with a programming switch that controls GPIO0), and for other operating systems you will need to change the port name to suit (`COM3:`, `/dev/cu.usbmodem4873`, etc).

# Answer
> -1 votes
```
//reset settings - in case of trouble just put in your code
//wifiManager.resetSettings();

```

That\`s all you need

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


title: Upcoming Project

text:
# Question
Title: Upcoming Project
Hey guys I have a project that will require 20 I/O pins with serial communication from a computer to control each of the pins. I would like something as small as possible would a arduino micro or uno work for this project or will i need to go bigger like a mega. I have looked at all the pinouts but am confused to know of which pins I can use as digital I/O or not. Thanks

# Answer
If you require 20 I/O pins then use Arduino Mega. If it’s too big then use Nano, Micro or Pro Mini (you need a serial thingy to program the Mini) with I/O expanders like PCF8574P with I2C communication or MCP23S17 with SPI communication.
> 2 votes

# Answer
There are a couple of options

1. Easiest = Use an Arduino with a greater number of pins (e.g. MEGA2560)
2. Easy = Use an add-on board (e.g. Teensy)
3. Harder = Use shift registers (see Is there a way to have more than 14 Output pins on arduino?)

Further discussion on these options here.
> 2 votes

---
Tags: serial, pins, digital
---


title: More than 4 MCP23S17 on 1 SPI bus

text:
# Question
Title: More than 4 MCP23S17 on 1 SPI bus
I would like to use 7 MCP23S17 as output expanders on one SPI bus. Every IC has its own address from 0 to 6. The first MCP23S17 can be written with no problem. The second chip did not work properly. The CS pin of the MCP23S17 is set like at the all other 4 ICs.

Does anybody have experience with more then 4 MCP23S17 on SPI? Could anyone help?

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

MCP A(0, 10);
MCP B(1, 8);
int d = 250;

void setup() {
  A.begin();
  B.begin();
  for (int k = 1; k <= 16; k++) {
    A.pinMode(k, OUTPUT);
    B.pinMode(k, OUTPUT);
  }
}

void loop() {
  //////////// ON THE LIGHT ONE BY ONE  FROM BEGGING
  for (int f = 1; f <= 16; f++) {
    A.digitalWrite(f, HIGH);
    delay(d );
  }
  for (int f = 1; f <= 16; f++) {
    B.digitalWrite(f, HIGH);
    delay(d );
  }
  ////////////  OFF THE LIGHT ONE BY ONE  FROM BEGINNIG
  for (int f = 1; f <= 16; f++) {
    A.digitalWrite(f, LOW);
    delay(d);
  }
  for (int f = 1; f <= 16; f++) {
    B.digitalWrite(f, LOW);
    delay(d);
  }
}

```

# Answer
> 2 votes
```
 MCP A(0, 9);
 MCP B(1, 8);
 MCP C(2, 7);
 MCP D(3, 6);
 MCP E(4, 5);
 MCP F(5, 3);

```
* `CS` on pin 10 is often used for Ethernet
* `CS` on pin 4 is often used for SD

# Answer
> 1 votes
Assuming that the adressing is correct and all the modules work fine individually, there are some things you can do:

* try to disable the slave select of the modules that aren’t require to communicate at a certain time, there are examples for that
* add a bit of code where you define chip select as an input for all but one and see if you can communicate with that one. Do that for all of them
* remove MISO pin from all but one and see if you can communicate with that one. Do that for all of them
* use a tri-state buffer through which you connect the MISO pin and use chip select for enabling the buffer. This buffer puts the MISO pin into a state of high impedance when a certain module is not used for communication and prevents fata from being lost

---
Tags: arduino-nano, spi
---


# Question
Title: How to keep warm arduino uno board with 12v dc supply
I have an arduino uno board with ESP8266 module and i have done all connection using breadboard.

Now when i run arduino uno with USB cable for long time then its not getting hot ! but when i supply power with 12v dc adapter in black barrele then its getting too much hot (i cant touch with my fingure).

Now when i remove the ESP8266 module power and test it again with 12v dc power supply then its not getting hot !

So what is the problem with ESP8266 module ? Is my wiring creates heat ?

# Answer
See Can I use arduino's 3.3 V output directly to esp8266?

From that page:

> The specs for the Uno say that it does not provide as much current on the 3.3V line as the specs for the ESP8266 requires. You will need to provide another regulator that can supply enough current.

Also, putting 12V into the barrel jack is making work for the on-board voltage regulator (located near the barrel jack) because it has to convert 12V to 5V (making heat in the process). You would be better off putting a lower voltage into the barrel jack, ideally around 7V (but not lower).

Alternatively, just power through the USB port as you have been, and plug the USB cable into a USB charger.

---

To summarize, both the 5V and 3.3V voltage regulators are probably working very hard, thus getting hot.
> 4 votes

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


# Question
Title: Unable to get Arduino Ethernet Shield IP address connected to Raspberry
My Arduino Uno with Ethernet Shield is connected to a Raspberry (rasp1) and the Ethernet Shield is connected to another Raspberry (rasp2) by Ethernet cable; rasp2 has a private IP address (192.168.10.0). I want to find out the Arduino IP address.

I used the example sketch DHCPAddressPrinter but when running it the Serial Monitor remains empty (as Mac Address I used the address located underneath the shield).

Code Used:

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

// Enter a MAC address for your controller below.
// Newer Ethernet shields have a MAC address printed on a sticker on the shield
byte mac[] = {
    0x90, 0xA2, 0xDA, 0x11, 0x32, 0x49
};

// Initialize the Ethernet client library
// with the IP address and port of the server
// that you want to connect to (port 80 is default for HTTP):
EthernetClient client;

void setup() {
    // Open serial communications and wait for port to open:
    Serial.begin(9600);
    // this check is only needed on the Leonardo:
    while (!Serial) {
        ; // wait for serial port to connect. Needed for Leonardo only
    }

    // start the Ethernet connection:
    if (Ethernet.begin(mac) == 0) {
        Serial.println("Failed to configure Ethernet using DHCP");
        // no point in carrying on, so do nothing forevermore:
        for (;;)
        ;
    }
    // print your local IP address:
    Serial.print("My IP address: ");
    for (byte thisByte = 0; thisByte < 4; thisByte++) {
        // print the value of each byte of the IP address:
        Serial.print(Ethernet.localIP()[thisByte], DEC);
        Serial.print(".");
    }
    Serial.println();
}

void loop() {

```

# Answer
`192.168.10.0` is not a valid IP address (unless it's on a /32 subnet which makes no sense on ethernet).

You need to allocate a proper IP address within a proper subnet, such as `192.168.10.1/24` (i.e., IP `192.168.10.1` and netmask `255.255.255.0`), and either manually provide a similar IP address to the Arduino (such as `192.168.10.2/24` \[IP `192.168.10.2` netmask `255.255.255.0`\]), or install and configure a DHCP server on the Raspberry to hand out IP addresses within that subnet range (e.g., `192.168.10.100/24` to `192.168.10.200/24`) for the Arduino to then be able to use DHCP mode.

Most of that is outside the scope of an Arduino SE site, though.
> 1 votes

---
Tags: raspberrypi
---


title: Non-blocking analogRead

text:
# Question
Title: Non-blocking analogRead
In my recent project, I'm working with the motor. I have to drive the motor for the specific time like for 2 minutes, 3 minutes, 4 minutes and 5 minutes. I already created functions for that. And motor drive based on readings taken from the sensor.

My code is below:

```
#define PIN_OUTPUT 6

const int kPinIN1 = 4;
const int kPinIN2 = 5;

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

  pinMode(kPinIN1, OUTPUT);
  pinMode(kPinIN2, OUTPUT);
}

void loop()
{
  Serial.println(analogRead(A0));

  if(analogRead(A0) > 100 && analogRead(A0) < 200)
  {
    motorDriveFor2Min();
  }
  else if(analogRead(A0) > 200 && analogRead(A0) < 300)
  {
    motorDriveFor3Min();
  }
  else if(analogRead(A0) > 300 && analogRead(A0) < 400)
  {
    motorDriveFor4Min();
  }
  else if(analogRead(A0) > 400 && analogRead(A0) < 500)
  {
    motorDriveFor5Min();
  }
}

void motorDriveFor2Min()
{
  digitalWrite(kPinIN1, HIGH);
  digitalWrite(kPinIN2, LOW);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(7000);

  digitalWrite(kPinIN1, LOW);
  digitalWrite(kPinIN2, HIGH);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(7000);

  digitalWrite(kPinIN1, HIGH);
  digitalWrite(kPinIN2, LOW);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(7000);

  digitalWrite(kPinIN1, LOW);
  digitalWrite(kPinIN2, HIGH);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(7000);

  digitalWrite(kPinIN1, HIGH);
  digitalWrite(kPinIN2, LOW);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(7000);

  digitalWrite(kPinIN1, LOW);
  digitalWrite(kPinIN2, HIGH);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(7000);

  digitalWrite(kPinIN1, HIGH);
  digitalWrite(kPinIN2, LOW);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(7000);

  digitalWrite(kPinIN1, LOW);
  digitalWrite(kPinIN2, HIGH);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(7000);

  digitalWrite(kPinIN1, HIGH);
  digitalWrite(kPinIN2, LOW);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(64000);
}

void motorDriveFor3Min()
{
  motorDriveFor2Min();

  digitalWrite(kPinIN1, HIGH);
  digitalWrite(kPinIN2, LOW);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(7000);

  digitalWrite(kPinIN1, LOW);
  digitalWrite(kPinIN2, HIGH);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(7000);

  digitalWrite(kPinIN1, HIGH);
  digitalWrite(kPinIN2, LOW);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(7000);

  digitalWrite(kPinIN1, LOW);
  digitalWrite(kPinIN2, HIGH);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(7000);

  digitalWrite(kPinIN1, HIGH);
  digitalWrite(kPinIN2, LOW);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(32000);
}

void motorDriveFor4Min()
{
  motorDriveFor3Min();

  digitalWrite(kPinIN1, HIGH);
  digitalWrite(kPinIN2, LOW);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(7000);

  digitalWrite(kPinIN1, LOW);
  digitalWrite(kPinIN2, HIGH);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(7000);

  digitalWrite(kPinIN1, HIGH);
  digitalWrite(kPinIN2, LOW);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(46000);
}

void motorDriveFor5Min()
{
  digitalWrite(kPinIN1, HIGH);
  digitalWrite(kPinIN2, LOW);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(120000);

  digitalWrite(kPinIN1, HIGH);
  digitalWrite(kPinIN2, LOW);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(7000);

  digitalWrite(kPinIN1, LOW);
  digitalWrite(kPinIN2, HIGH);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(7000);

  digitalWrite(kPinIN1, HIGH);
  digitalWrite(kPinIN2, LOW);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(7000);

  digitalWrite(kPinIN1, LOW);
  digitalWrite(kPinIN2, HIGH);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(7000);

  digitalWrite(kPinIN1, HIGH);
  digitalWrite(kPinIN2, LOW);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(7000);

  digitalWrite(kPinIN1, LOW);
  digitalWrite(kPinIN2, HIGH);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(7000);

  digitalWrite(kPinIN1, HIGH);
  digitalWrite(kPinIN2, LOW);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(7000);

  digitalWrite(kPinIN1, LOW);
  digitalWrite(kPinIN2, HIGH);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(7000);

  digitalWrite(kPinIN1, LOW);
  digitalWrite(kPinIN2, HIGH);

  analogWrite(PIN_OUTPUT, 255);

  verboseDelay(120000);
}

void verboseDelay(unsigned long ms)
{
  unsigned long now = millis();
  unsigned long start = now;

  do
  {
    now = millis();
  }
  while (now - start < ms);
}

```

Here, I have four functions named `motorDriveFor2Min()`, `motorDriveFor3Min()`, `motorDriveFor4Min()` and `motorDriveFor5Min()` for my specific time means for 2 minutes, 3 minutes, 4 minutes and 5 minutes respectively.

So, suppose If I want to drive motor for 4 min then I have to call function `motorDriveFor4Min()` and for that, I have to set my reading between 300 & 400. But I can't able to do that because when my reading reaches at 100 then it starts executing another function means `motorDriveFor2Min()` and then continuously run that functionality. During that time I try to change the reading but nothing happens. After restating Arduino it run according to the reading.

So, I thought maybe delay() function block everything. So I replace inbuilt delay function with custom delay function. But that can't solve my problem. Then I google it out and I found out that analogRead may cause this problem. Any suggestion for this.

# Answer
It's not analogRead. It's not (just) delay. It's the whole method of your program.

The way it's written you can do *nothing* else while driving a motor for X minutes.

You need to rethink your whole program so that it's not "run for X minutes" each time, but instead "Run the motor until the time is up" and constantly re-evaluate what the time should be.

That means:

* No "run for X" functions.
* No `delay()` functions (of *any* form - yours is as bad as the normal one).
* A state machine to determine what should be happening when.
* Constantly referencing both `millis()` and `analogRead()` to determine what state the state machine should be in or progress to and when.
> 3 votes

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


title: Can't assign String to Array of String

text:
# Question
Title: Can't assign String to Array of String
I have to input 5 words and organize. In order to organize words, I have to get them into Array of String to compare. I succeed to get `char[buffer]` into `String in_str` but somehow `in_str` doesn't get into `str[5]`. is `String str[i]=in_str;` Wrong?? How can I put `in_str` to Array of `String str`??

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

void loop() {
  int state = 1, len = 0 ,i=0, k=1;
  char buffer[128];
  String str[5];
  while (true) {
    if (state == 1) {
      Serial.print("Enter the ");
      Serial.print(k);
      Serial.print("th Word --> ");
      state = 2;
    }
    while (Serial.available()) {
      char data = Serial.read();
      if (data == '\n') {
        buffer[len] = '\0';
        String in_str = buffer;
        String str[i]=in_str;
        Serial.println(in_str);

        i=i+1;
        k=k+1;
        len = 0;
        if(i>4){state = 3; }
        else {state = 1;}
        break;
      }
      buffer[len++] = data;
    }
  if(state==3){
    Serial.println("After Sorting");
   for (int i = 0; i < 4; i++) {
    for (int j = i + 1; j < 5; j++) {
      int compare = str[i].compareTo(str[j]);
      if (compare > 0) {         String temp = str[i];
        str[i] = str[j];
        str[j] = temp;
      }
    }
  }

   for (int i = 0; i < 5; i++) {
    Serial.println(String(i) + " : " + str[i]);
  }

    break;
  }

  }
}

```

# Answer
> 1 votes
When you write `String str[i]=in_str;` that is wrong. You only write the type when you are declaring the variable, once.

When assigning, you need only write the variable name, not the type: `str[i]=in_str;`

---
Tags: string, array
---