text:
Stopwatch stop/start button and reset
i am trying to make a stop watch with a stop/start button and a reset button
i have made this
#include "RTClib.h"
//Setup the Real Time Clock, DS3231
RTC_DS3231 rtc;

const byte SQWinput = 2;  // Must be External Interrupt

volatile uint32_t  MillisecondsAtStartOfSecond = 0;

 unsigned long secondss=0 ;
 unsigned long minutess=0 ;

 unsigned long  hourss =0;
 unsigned long ms;

boolean passed_second=true;
boolean start=true;

const byte ledPin = 13;

const byte startButton = 7;

const byte resetButton = 3;
// Instantiate another Bounce object

const char daysOfTheWeek[7][12] = {"Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"};

// The SQW pin, when set to 1 Hz mode, has a falling edge at the beginning of every second.
void SQWFallingISR()
{
  MillisecondsAtStartOfSecond = millis();
}

void setup ()
{
  Serial.begin(9600); // Set Serial Monitor to 115200
  delay(200);

  pinMode(7, INPUT);
  digitalWrite(7, HIGH);
  pinMode(3, INPUT);
  digitalWrite(3, HIGH);

  if (! rtc.begin())
  {
    Serial.println("Couldn't find RTC");
    Serial.flush();
    abort();
  }

  if (rtc.lostPower())
  {
    Serial.println("RTC lost power, let's set the time!");
    // When time needs to be set on a new device, or after a power loss, the
    // following line sets the RTC to the date & time this sketch was compiled
    rtc.adjust(DateTime(F(__DATE__), F(__TIME__)));
    // This line sets the RTC with an explicit date & time, for example to set
    // January 21, 2014 at 3am you would call:
    // rtc.adjust(DateTime(2022, 4, 03, 21, 14, 0));
  }

  // Configure SQW pin on the DS3231 to output a 1Hz squarewave
  rtc.writeSqwPinMode(DS3231_SquareWave1Hz);

  // Get MillisecondsAtStartOfSecond on the falling edge of SQW.
  attachInterrupt(digitalPinToInterrupt(SQWinput), SQWFallingISR, FALLING);
}

void loop ()
{
  DateTime now = rtc.now();

    ms = millis();

  noInterrupts();
  // How long since the second started?

  ms -= MillisecondsAtStartOfSecond;
  interrupts();

  if(digitalRead(7) != HIGH)   //START BUTTON
{    displayTime (now, ms);
     Serial.println("stopwatch  ");

  Serial.print(hourss);
  Serial.print(':');
  Serial.print(minutess);
  Serial.print(':');
  Serial.print(secondss);
  Serial.print(':');
  Serial.println(ms);
}

 if(digitalRead(3) != HIGH)   //RESET BUTTON
{
     Serial.println("stopwatch  ");

  Serial.print(0);
  Serial.print(':');
  Serial.print(0);
  Serial.print(':');
  Serial.print(0);
  Serial.print(':');
  Serial.println(0);
  ms=0;
}
 // displayTime (now, ms);
  /*Serial.println("stopwatch  ");

  Serial.print(hourss);
  Serial.print(':');
  Serial.print(minutess);
  Serial.print(':');
  Serial.print(secondss);
  Serial.print(':');
  Serial.println(ms);
  Serial.println("*********************************");
  Serial.println("Clock & Date  ");*/

  }

void displayTime(DateTime &now, unsigned long ms)
{
  ms = ms % 1000;  // Ignore full seconds

  Serial.print(now.year(), DEC);
  Serial.print('/');
  Serial.print(now.month(), DEC);
  Serial.print('/');
  Serial.print(now.day(), DEC);
  Serial.print(" (");
  Serial.print(daysOfTheWeek[now.dayOfTheWeek()]);
  Serial.print(") ");
  Serial.print(now.hour(), DEC);
  Serial.print(':');
  if (now.minute() < 10)
    Serial.print('0');
  Serial.print(now.minute(), DEC);
  Serial.print(':');
  if (now.second() < 10)
    Serial.print('0');
  Serial.print(now.second(), DEC);
 // Serial.println();
  Serial.print(':');
  if (ms < 100)
    Serial.print('0');
  if (ms < 10)
    Serial.print('0');
  Serial.print(ms, DEC);
  Serial.println();
  Serial.println("*********************************");

  if(ms>998) {
      secondss++;

  }
    if(secondss>59) {
     secondss=0;
      minutess++;

    }
    if(minutess>59) {
     minutess=0;
      hourss++;}

    }

but it is not working properly
the time is not incrementing after ms reaches 999
what is causing this?

What do you mean by “it is not working properly”? What behavior do you see? How is it different from the behavior you expect?

the time is not incrementing after ms reaches 999

declare now in setup() ... DateTime now; .... then use now = rtc.now(); in loop()

This code is quite confusing, as you are using both millis() and an
RTC as time sources.
Your problem may come from here:
ms -= MillisecondsAtStartOfSecond;

If the internal clock of your Arduino is a bit off, it may happen that
an RTC second is only 999 milliseconds from millis(). If that happens,
then ms will never hit 999, and will instead go straight from 998
to 0.
Or maybe it's here:
ms = ms % 1000;  // Ignore full seconds
// ...
if (ms > 998) {
    secondss++;
}

If you sketch is busy (maybe it is communicating with the RTC), it may
not run this code precisely at millisecond 999. And 999 is the only
value of ms that can possibly increment secondss.
For a stopwatch, you don't really need the RTC data. You can implement
it entirely on the basis of millis(), and that would simplify things:
bool stop_watch_running;
uint32_t stop_watch_last_update;
uint16_t stop_watch_ms;
uint8_t stop_watch_s;
uint8_t stop_watch_min;
uint8_t stop_watch_h;

void stop_watch_reset() {
    stop_watch_running = false;
    stop_watch_ms = 0;
    stop_watch_s = 0;
    stop_watch_min = 0;
    stop_watch_h = 0;
}

void stop_watch_start() {
    stop_watch_last_update = millis();
    stop_watch_running = true;
}

// Call this periodically.
void stop_watch_update() {
    if (!stop_watch_running)
        return;
    uint32_t now = millis();
    stop_watch_ms += now - stop_watch_last_update;
    stop_watch_last_update = now;
    while (stop_watch_ms >= 1000) {
        stop_watch_ms -= 1000;
        stop_watch_s++;
        if (stop_watch_s >= 60) {
            stop_watch_s = 0;
            stop_watch_min++;
            if (stop_watch_min >= 60) {
                stop_watch_min = 0;
                stop_watch_h++;
            }
        }
    }
}

void stop_watch_stop() {
    stop_watch_update();
    stop_watch_running = false;
}

If you know a bit about C++ classes, you may want to turn this into a
class, and replace the stop_watch_ prefix with StopWatch::.

Hello Edgar
Thank u v much for your code
RTC is used to get sq wave output


text:
OLED screen goes blank on delay() - U8G2 library + Arduino Nano
Description
I'm currently trying to get this SSD1306 0.91" OLED screen with an Arduino Nano with the U8G2 library (as per seller's guide), and in any code I run, as soon as a delay() is executed, the screen goes blank and doesn't show any further text or image.
What is the possible cause?
Wiring

Code
To first make sure the OLED module works, I'm using one of the HelloWorld examples from the U8G2 library, from which (with comments removed) I'm executing the next code:
#include <Arduino.h>
#include <U8g2lib.h>

#ifdef U8X8_HAVE_HW_SPI
#include <SPI.h>
#endif
#ifdef U8X8_HAVE_HW_I2C
#include <Wire.h>
#endif

U8G2_SSD1306_128X32_UNIVISION_F_SW_I2C u8g2(U8G2_R0, /* clock=*/ SCL, /* data=*/ SDA, /* reset=*/ U8X8_PIN_NONE);

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

void loop(void) {
  u8g2.clearBuffer();                   // clear the internal memory
  u8g2.setFont(u8g2_font_ncenB08_tr);   // choose a suitable font
  u8g2.drawStr(0,10,"Hello World!");    // write something to the internal memory
  u8g2.sendBuffer();                    // transfer internal memory to the display
  delay(1000);
}

Expected Result
The OLED Screen should always show "Hello World!" text, as per this youtube video with the same setup.
Actual Result
At startup, it shows the "Hello World" text for a fraction of a second and it disappears.
I've found out that as soon as the delay() is executed, screen goes blank forever and doesn't reload any text. I don't want this approach if possible since:

I plan on using a battery to power the Arduino and the screen, and a permanent screen refresh would decrease autonomy
When doing so, the screen is a little bit flickery.

Troubleshooting executed

I used a different Arduino Nano, and result was the same.
I'm using a 5V 2A power supply for the entire circuit.
I tried different U8G2 example sketches, with the same result (only working if no delay()).
I tried using another OLED module of the same specs, and result is the same.
I've tried to use Adafruit SSD1306 library, and screen doesn't show anything.

What I can tell you is that if I substitute an UNO for your Nano (which should make no difference) and an x64 display for your x32 display (which may make a difference, but I doubt it), your code works verbatim. It does not blank the display. I can modify it to display a counter and it counts as predicted. Include version numbers of everything involved (ide, libraries, core) and links to your actual display and arduino board.

Well. I found my display that's appears to be identical to what you have (assuming what you really have is what you linked) and it continues to work. There is a minor difference in how it displays, but it still essentially works as expected. So, add details.

Thanks a lot. In the last week I had little time, but I'll do a test later today and come back with further findings and update this comment/post.

Just did some additional testing and here's some more info:

IDE's: tried with Arduino IDE 2.0.1 and VSCode 1.73.0 with Arduino extension v0.4.12

Just tested with an original Uno and same result.
If I put a delay(50), the screen keeps the HelloWorld! word although blinking is more visible.
Moving everything except delay() or delay(50) to setup results in the same behavior (it shows HelloWorld for a fraction of a second and screen goes blank).

I finally found the root cause. I was using a breadboard for this setup, and as soon as I took the components out and used different cables, everything started working as expected. Lesson learnt: do not always rely on the breadboards being 100% functional; when everything else fails, remove the breadboard from the equation.

source: Stack Exchange

license: Creative Commons - Attribution Share-Alike - https://creativecommons.org/licenses/by-sa/4.0/

sort: votes


text:
manage some output based on some parameter and rtc
i'm trying to create a program that given a configuration (i've used multiple struct nested) i need in loop() to check for each output if they need to be on or off and set the output accordingly
let me explain the configuration (i'm not sure that this is the best way to make and store this config, suggestions are appreciated)
struct Period
{
    String name;
    String type;
    String value;
};

struct State
{
    String name;
    Period periods[2];
};

struct Output
{
    String name;
    int pin;
    int forcePin;
    State states[2];
};

Output outputs[4];

now i populate the first object (this is something that need to be editable by the user and i was thinking to store it in the EEPROM, for now in the setup() i do this
    outputs[0].name = "OUTPUT 1";
    outputs[0].pin = 27;
    outputs[0].forcePin = 25;
    outputs[0].states[1].name = "STATE 1";
    outputs[0].states[1].periods[0].name = "day";
    outputs[0].states[1].periods[0].type = "BOOL";
    outputs[0].states[1].periods[0].value = "ON";
    outputs[0].states[1].periods[1].name = "night";
    outputs[0].states[1].periods[1].type = "BOOL";
    outputs[0].states[1].periods[1].value = "OFF";
    outputs[0].states[0].name = "STATE 2";
    outputs[0].states[0].periods[0].name = "day";
    outputs[0].states[0].periods[0].type = "BOOL";
    outputs[0].states[0].periods[0].value = "ON";
    outputs[0].states[0].periods[1].name = "night";
    outputs[0].states[0].periods[1].type = "BOOL";
    outputs[0].states[0].periods[1].value = "OFF";

then in the loop i have few function that determinate the state and period and i call this function that should manage all the outputs
globalState in loop read from an input and set the variable
globalPeriod check the time and set if night or day
void manageOutputs()
{
    for (Output out : outputs)
    {
        Serial.println(out.name);
        Serial.println(out.pin);
        Serial.println(out.forcePin);
        if (digitalRead(out.forcePin) == LOW)
        {
            Serial.println("forced on set output");
            digitalWrite(out.pin, HIGH)
            continue;
        }

        Serial.println(out.states[globalState].name);
        Serial.println(out.states[globalState].periods[globalPeriod].name);
        Serial.println(out.states[globalState].periods[globalPeriod].type);
        Serial.println(out.states[globalState].periods[globalPeriod].value);
        if (out.states[globalState].periods[globalPeriod].type.equals("BOOL")) {
            if (out.states[globalState].periods[globalPeriod].value.equals("ON")) {
                digitalWrite(out.pin,HIGH);
            } else {
                digitalWrite(out.pin,LOW);
            }
        }
    }
}

i have multiple type of output in mind for example TIMER (so in the value field i would have some parameter to call another function that will alternate the output on and off for the time given) will have something like "15:10" so it will stay 15 minutes on and 10 minutes off, or a condition (for example if VAR1 > 50) so the field value would have "VAR1:>:50" so it will turn on only if the condition is met. So i will have a switch case where now i check if BOOL.
now that i hope that i have explained the situation, i would like to know if it's a good way to have 3 nested struct or if there is a better solution considering the necessity to have it stored in EEPROM, and if this is a good way to have this kind of condition like this or if there is a better way.
Considering also that in the future i would like to make a webpage or an api to update this kind of configuration from a pc (maybe using a esp-8266 for that, that is also connected to the arduino, or do everything with an esp32, but i would like first to have the basic loop working and then i will make the "UI")
thanks a lot

The 1st issue is this line: digitalWrite(out.pin, HIGH) with no semicolon. Next issue is globalState does not exist. Please read: https://stackoverflow.com/help/minimal-reproducible-example

There are many uses of the String class in these code snippets. Using
strings is quite natural in some higher-level languages. On an Arduino,
however, I would strongly advise you against this for two reasons:

String objects use dynamic memory, which is not friendly to the small
amount of RAM available on a typical Arduino.

Saving a String to EEPROM is not trivial: you do not want to save the
String object (it contains a pointer that would not make sense in
EEPROM context), and you instead have to save the character array it
refers to. This could involve handling complex memory allocation
withing the EEPROM.

Instead of a string meant to handle one of a predefined set of values
("BOOL", "TIMER", ...), use an enum. This is similar to an int,
where each possible value has been given a name (TYPE_BOOL is 0,
TYPE_TIMER is 1, ...). Instead of a string holding numbers, store the
numbers themselves. In essence, you want to create a data storage format
that is friendly to the binary nature of the CPU. If you really have to
store strings, e.g. for names (are those name fields really useful?
they do not look so in the provided example), limit their length and
store them as fixed-size character arrays.
The period::value field is interesting in that it can store different
kinds of information depending on the type field. For such a situation
the appropriate data structure is a discriminated union. A union
is like a struct except that all fields share the same memory space
and only one can be valid at a time. In a discriminated union, the
union is accompanied by  a ytpe field that tells us which is the
valid field.
Applying those principles to your problem could give this kind of data
structure:
// All the possible Period types.
enum Type {
    TYPE_BOOL,
    TYPE_TIMER,
    // etc.
};

// This is a discriminated union.
struct Period
{
    Type type;
    union {  // one union member per possible type.
        bool bool_value;  // valid when type == TYPE_BOOL
        struct {
            int on_time;
            int off_time;
        } timer_value;  // valid when type == TYPE_TIMER
        // etc.
    };
};

struct State
{
    Period periods[2];
};

struct Output
{
    int pin;
    int forcePin;
    State states[2];
};

These data structures can be trivially saved in EEPROM, as they are
self-contained: they hold no pointers to data stored in dynamic memory.
Then, in manageOutputs(), you will read a period's bool_value only
when type is TYPE_BOOL, it's timer_value only when type is
TYPE_TIMER, etc:
void manageOutputs()
{
    for (Output out : outputs)
    {
        if (digitalRead(out.forcePin) == LOW) {
            digitalWrite(out.pin, HIGH);
            continue;
        }
        Period &period = out.states[globalState].periods[globalPeriod];
        switch (period.type) {
            case TYPE_BOOL:
                if (period.bool_value) {
                    digitalWrite(out.pin, HIGH);
                } else {
                    digitalWrite(out.pin, LOW);
                }
                break;
            case TYPE_TIMER:
                digitalWrite(out.pin, HIGH);
                delay(period.timer_value.on_time);
                digitalWrite(out.pin, LOW);
                delay(period.timer_value.off_time);
        }
    }
}

Thanks a lot, the .name are useful to set a name on the output to be easy configurable and to be easier to understand what the output do (i don't think is necessary on the sub struct, but maybe on the main output, i will do some test with char array .. to see if it easy to work with that)

all_licenses: Creative Commons - Attribution Share-Alike - https://creativecommons.org/licenses/by-sa/4.0/


text:
Combining two scripts
I'm trying to combine two scripts I've found. One to get my remote control model to work via a controller and the other to enable 6 ultrasound modules I have. When I omit the code highlighted in "THIS SECTION" (for the ultrasound modules) the controller and model works fine but when I put it in (to enable to ultrasound modules), the controller becomes unresponsive and the wheels spin uncontrollably.
I'm assuming it's something to do with having what should be two seperate loop sections combined into one?
Any help is much appreciated,
Thanks

//This section defines all the pin data and  to be used within the program loop.

//The following four lines set the pin numbers for the PS2 controller.
#define PS2_DAT        11 //Data pin.
#define PS2_CMD        10 //Command pin.
#define PS2_SEL        9  //Attention pin.
#define PS2_CLK        8  //Clock pin.

//The following six lines set the pin numbers for the motor module.
#define IN1     33 //Positive polarity for the right sided wheels.
#define IN2     35 //Negative polarity for the right sided wheels.
#define IN3     37 //Positive polarity for the left sided wheels.
#define IN4     39 //Negative polarity for the left sided wheels.
#define ENA     31 //Jumper pin start.
#define ENB     41 //Jumper pin end.

//The analogue values read from the PS2 contoller.
int LX = 0;
int LY = 0;
int RX = 0;
int RY = 0;

//The following twelve lines set pin numbers for the ultrasonic sensors.
int trigPin1=7; //Front transmitter (Object ahead detection).
int echoPin1=6; //Front receiver.
int trigPin2=5; //Right transmitter (Lane keeping).
int echoPin2=4; //Right receiver.
int trigPin3=3; //Rear right transmitter (Right blindspot detection).
int echoPin3=2; //Rear right receiver.
int trigPin4=14; //Rear centre transmitter (Parking sensor).
int echoPin4=15; //Rear centre receiver.
int trigPin5=16; //Rear left transmitter (Left blindspot detection).
int echoPin5=17; //Rear left receiver.
int trigPin6=19; //Left transmitter (Lane keeping).
int echoPin6=18; //Left receiver.

// This section sets the modes of PS2 controller.
//#define pressures   true
#define pressures   false
#define rumble      true
//#define rumble      false

PS2X ps2x; //Creates PS2 controller class.
int error = 0;
byte type = 0;
byte vibrate = 0;

void setup() {

Serial.begin (9600); //Opens the sensor serial ports and sets data rate to 9600bps
  pinMode(trigPin1, OUTPUT);
  pinMode(echoPin1, INPUT);
  pinMode(trigPin2, OUTPUT);
  pinMode(echoPin2, INPUT);
  pinMode(trigPin3, OUTPUT);
  pinMode(echoPin3, INPUT);
  pinMode(trigPin4, OUTPUT);
  pinMode(echoPin4, INPUT);
  pinMode(trigPin5, OUTPUT);
  pinMode(echoPin5, INPUT);
  pinMode(trigPin6, OUTPUT);
  pinMode(echoPin6, INPUT);

  pinMode(IN1,  OUTPUT);
  pinMode(IN2,  OUTPUT);
  pinMode(IN3, OUTPUT);
  pinMode(IN4, OUTPUT);
  pinMode(ENA, OUTPUT);
  pinMode(ENB, OUTPUT);

  digitalWrite(ENA, LOW);
  digitalWrite(ENB, LOW);

  delay(300);  //Added delay to give the wireless PS2 module time to start up before configuring it.

  //Checks for errors determined by pin data: GamePad(clock, command, attention, data, pressures, rumble)
  error = ps2x.config_gamepad(PS2_CLK, PS2_CMD, PS2_SEL, PS2_DAT, pressures, rumble);

  if (error == 0) {
    Serial.print("Found Controller, configured successful ");
  }
  else if (error == 1)
    Serial.print("No controller found, check wiring");

  else if (error == 2)
    Serial.print("Controller found but not accepting commands");

  else if (error == 3)
    Serial.print("Controller refusing to enter Pressures mode, may not support it.");
  }

void loop() {
---------------------------------------THIS SECTION------------------------------
long duration1, distance1;
  digitalWrite(trigPin1, HIGH);**
  delayMicroseconds(10); // Added this line
  duration1 = pulseIn(echoPin1, HIGH);
  distance1 = (duration1/2) / 29.1;

   if (distance1 >= 500 || distance1 <= 0){
    Serial.println("Out of range");
  }
  else {
    Serial.print ( "Sensor1  ");
    Serial.print ( distance1);
    Serial.println("cm");
  }

  long duration2, distance2;
  digitalWrite(trigPin2, HIGH);
  delayMicroseconds(10); // Added this line
  duration2 = pulseIn(echoPin2, HIGH);
  distance2 = (duration2/2) / 29.1;

   if (distance2 >= 500 || distance2 <= 0){
    Serial.println("Out of range");
  }
  else {
    Serial.print("Sensor2  ");
    Serial.print(distance2);
    Serial.println("cm");
  }
  long duration3, distance3;
  digitalWrite(trigPin3, HIGH);
  delayMicroseconds(10); // Added this line
  duration3 = pulseIn(echoPin3, HIGH);
  distance3 = (duration3/2) / 29.1;

   if (distance3 >= 500 || distance3 <= 0){
    Serial.println("Out of range");
  }
  else {
    Serial.print("Sensor3  ");
    Serial.print(distance3);
    Serial.println("cm");
  }
  long duration4, distance4;
  digitalWrite(trigPin4, HIGH);
  delayMicroseconds(10); // Added this line
  duration4 = pulseIn(echoPin4, HIGH);
  distance4 = (duration4/2) / 29.1;

   if (distance4 >= 500 || distance4 <= 0){
    Serial.println("Out of range");
  }
  else {
    Serial.print("Sensor4  ");
    Serial.print(distance4);
    Serial.println("cm");
  }
  long duration5, distance5;
  digitalWrite(trigPin5, HIGH);
  delayMicroseconds(10);
  duration5 = pulseIn(echoPin5, HIGH);
  distance5 = (duration5/2) / 29.1;

   if (distance5 >= 500 || distance5 <= 0){
    Serial.println("Out of range");
  }
  else {
    Serial.print("Sensor5  ");
    Serial.print(distance5);
    Serial.println("cm");
  }
  long duration6, distance6;
  digitalWrite(trigPin6, HIGH);
  delayMicroseconds(10);
  duration6 = pulseIn(echoPin6, HIGH);
  distance6 = (duration6/2) / 29.1;

   if (distance6 >= 500 || distance6 <= 0){
    Serial.println("Out of range");
  }
  else {
    Serial.print("Sensor6  ");
    Serial.print(distance6);
    Serial.println("cm");
  }
---------------------------------------------END----------------------------------------

  ps2x.read_gamepad(false, vibrate); //read controller and set large motor to spin at 'vibrate' speed

  delay(50);
  if (ps2x.Button(PSB_L1))
  {
    LY = ps2x.Analog(PSS_LY); //receive values from p22 joystick
    LX = ps2x.Analog(PSS_LX);
  }
  if (ps2x.Button(PSB_R1))
  {
    RY = ps2x.Analog(PSS_RY);
    RX = ps2x.Analog(PSS_RX);
  }
  if (LY > 200 || RY > 200) //check if the joystick pushed up side
  {
    REV();
  }
  if (LY < 100 || RY < 100)
  {
    forward();
  }
  if (LX < 100 || RX < 100)
  {
    left();
  }
  if (LX > 200 || RX > 200)
  {
    right();
  }
  if(LX == 128 && LY == 128 && RX == 128 && RY == 128)
  {
    waithere();
  }
LY = LX = 128;         //return to default vlaues
RY = RX = 128;         //return to default values
}

void forward()
{
  digitalWrite(ENA, HIGH);
  digitalWrite(ENB, HIGH);
  digitalWrite(IN1, HIGH);
  digitalWrite(IN2, LOW);
  digitalWrite(IN3, HIGH);
  digitalWrite(IN4, LOW);
}
void REV()
{
  digitalWrite(ENA, HIGH);
  digitalWrite(ENB, HIGH);
  digitalWrite(IN1, LOW);
  digitalWrite(IN2, HIGH);
  digitalWrite(IN3, LOW);
  digitalWrite(IN4, HIGH);
}
void left()
{
  digitalWrite(ENA, LOW);
  digitalWrite(ENB, HIGH);
  digitalWrite(IN1, LOW);
  digitalWrite(IN2, LOW);
  digitalWrite(IN3, HIGH);
  digitalWrite(IN4, LOW);
}
void right()
{
  digitalWrite(ENA, HIGH);
  digitalWrite(ENB, LOW);
  digitalWrite(IN3, LOW);
  digitalWrite(IN4, LOW);
  digitalWrite(IN1, HIGH);
  digitalWrite(IN2, LOW);
}
void waithere()
{
  digitalWrite(ENA, LOW);
  digitalWrite(ENB, LOW);
  digitalWrite(IN3, LOW);
  digitalWrite(IN4, LOW);
  digitalWrite(IN1, LOW);
  digitalWrite(IN2, LOW);
}

pulseIn() has a standard timeout of 1s. Try to reduce it and see, if it works better

you can simpify your code if you use arrays to hold variables ... trigPin[], echoPin[], duration[], distance[] ... then you can use a for loop to iterate through the six sensors, instead of repeating code


text:
NRF24I01 with antenna Communication Delay
I am doing my senior design project which is due in a week, I am currently using the NRF24I01 with antennas for both the transmitter and the receiver. I am building a robot that is suppose to climb a wall, the transmitter and receiver are to allow me to controller where it goes using a joystick. I will attach both codes. My current issue is when I push on the joystick one motor will run full speed while the other starts slow then catches up to full speed. After I let go of the joystick, the motors will still spin full speed for a minute trying to catch up for the delay in the beginning.
This is really frustrating because I am not well-versed with Arduino and I cannot figure out how to fix it, please help.
Also I am using the radio.head library.
Reciever code:
#include <RHReliableDatagram.h>
#include <RH_NRF24.h>

#include <SPI.h>

#define CLIENT_ADDRESS 1
#define SERVER_ADDRESS 2

// Motor A connections analog 0 is digital 14 on arduino
int enA = 9;
int in1 = 2;
int in2 = 4;

// Motor B connections
int enB = 5;
int in3 = 7;
int in4 = 6;

// Create an instance of the radio driver
RH_NRF24 RadioDriver;

// Sets the radio driver to NRF24 and the server address to 2
RHReliableDatagram RadioManager(RadioDriver, SERVER_ADDRESS);

// Define a message to return if values recieved
uint8_t ReturnMessage[] = "JoyStick Data Received";

// Define the Message Buffer
uint8_t buf[RH_NRF24_MAX_MESSAGE_LEN];

void setup()
{
    // Set all the motor control pins to outputs
    pinMode(enA, OUTPUT);
    pinMode(enB, OUTPUT);
    pinMode(in1, OUTPUT);
    pinMode(in2, OUTPUT);
    pinMode(in3, OUTPUT);
    pinMode(in4, OUTPUT);

    // Initilize RadioManager with defaults - 2.402 Ghz (channel 2), 2Mbps, 0dbm
    if (!RadioManager.init())
        Serial.println("init failed");
}

void loop()
{
    if (RadioManager.available())
    {
        // Wait for a message addressed to us from the client
        uint8_t len = sizeof(buf);
        uint8_t from;

        if (RadioManager.recvfromAck(buf, &len, &from))
        {
//          Serial Print the values of joystick
//          Serial.print("got request from : 0x");
//          Serial.print(from, HEX);
//          Serial.print(": MotorA = ");
//          Serial.print(buf[0]);
//          Serial.print("MotorB = ");
//          Serial.print(but[1]);
//          Serial.print(" Dir = ");
//          Serial.println(buf[2]);

            // Set Motor Direction
            if (buf[2] == 1)
            {
                // Motors are backwards
                digitalWrite(in1, LOW);
                digitalWrite(in2, HIGH);
                digitalWrite(in3, LOW);
                digitalWrite(in4, HIGH);
            }
            else
            {
                // Motors are forwards
                digitalWrite(in1, HIGH);
                digitalWrite(in2, LOW);
                digitalWrite(in3, HIGH);
                digitalWrite(in4, LOW);
            }

            // Drive Motors
            analogWrite(enA, buf[1]);
            analogWrite(enB, buf[0]);

            // Send a reply back to the orginitor client, check for error
            if (!RadioManager.sendtoWait(ReturnMessage, sizeof(ReturnMessage), from))
                Serial.println("sendtoWait failed");
        }
    }
}

Transceiver code:
#include <RHReliableDatagram.h>
#include <RH_NRF24.h>

#include <SPI.h>
#define joyVert  A0
#define joyHorz  A1

int joyposVert = 512;
int joyposHorz = 512;

#define CLIENT_ADDRESS 1
#define SERVER_ADDRESS 2

RH_NRF24 RadioDriver;

RHReliableDatagram RadioManager (RadioDriver, CLIENT_ADDRESS);

uint8_t motorcontrol[3];

uint8_t buf[RH_NRF24_MAX_MESSAGE_LEN];

void setup()
{
    // put your setup code here, to run once:
    Serial.begin(9600);
    if (RadioManager.init())
        Serial.println("init failed");
    motorcontrol[2] = 0;
}

void loop()
{
    // put your main code here, to run repeatedly:
    Serial.println("Reading motorcontrol values");
    joyposVert = analogRead(joyVert);
    joyposHorz = analogRead(joyHorz);

    //FORWARD & BACKWARD
    if (joyposVert < 460)
    {
        motorcontrol[2] = 1;
        motorcontrol[0] = map(joyposVert, 460, 0, 0, 255);
        motorcontrol[1] = map(joyposVert, 460, 0, 0, 255);

    }
    else if (joyposVert > 564)
    {
        motorcontrol[2] = 0;
        motorcontrol[0] = map(joyposVert, 564, 1023, 0, 255);
        motorcontrol[1] = map(joyposVert, 564, 1023, 0, 255);
    }
    else
    {
        motorcontrol[0] = 0;
        motorcontrol[1] = 0;
        motorcontrol[2] = 0;
    }

    // STEERING
    if (joyposHorz < 460)
    {
        // Move Left
        joyposHorz = map(joyposHorz, 460, 0, 0, 255);

        motorcontrol[0] = motorcontrol[0] - joyposHorz;
        motorcontrol[1] = motorcontrol[1] + joyposHorz;

        // Dont exceed range of 0-255 for motor speeds
        if (motorcontrol[0] <   0) motorcontrol[0] = 0;
        if (motorcontrol[1] > 255) motorcontrol[1] = 255;

    }
    else if (joyposHorz > 564)
    {
        // Move Right
        joyposHorz = map(joyposHorz, 564, 1023, 0, 255);

        motorcontrol[0] = motorcontrol[0] + joyposHorz;
        motorcontrol[1] = motorcontrol[1] - joyposHorz;

        // Dont exceed range of 0-255 for motor speeds
        if (motorcontrol[0] > 255) motorcontrol[0] = 255;
        if (motorcontrol[1] <   0) motorcontrol[1] = 0;

    }
    // Adjust to prevent "buzzing" at very low speed
    if (motorcontrol[0] < 8)motorcontrol[0] = 0;
    if (motorcontrol[1] < 8)motorcontrol[1] = 0;

    // Display the Motor Control Values in the serial monitor.
//  Serial.print("Motor A: ");
//  Serial.print(motorcontrol[0]);
//  Serial.print(" - Motor B: ");
//  Serial.print(motorcontrol[1]);
//  Serial.print(" - Direction: ");
//  Serial.println(motorcontrol[2]);

    // Send a message containing Motor Control data to manager_server
    if (RadioManager.sendtoWait(motorcontrol, sizeof(motorcontrol), SERVER_ADDRESS))
    {
        // Now wait for a reply from the server
        uint8_t len = sizeof(buf);
        uint8_t from;

        if (RadioManager.recvfromAckTimeout(buf, &len, 2000, &from))
        {
            Serial.print("got reply from :0x");
            Serial.print(from, HEX);
            Serial.print(": ");
            Serial.println((char*)buf);
        }
        else
        {
            Serial.println("No reply, is nrf24_reliable_datagram_server running?");
        }
    }
    else
        Serial.println("senttoWait failed");

//  delay(10);  //Wait a bit before next transmission
}

First thing to do is to open your code in the Arduino IDE and press Control-T to format the code and line up the blocks.  I don't know how you can try to see the logic in this with code wandering all over the page.  When real coders write with the nice neat blocks, we don't do that just to make it pretty.  It makes it easier to read as well.  The IDE does it for you so there's really no excuse.  Oftentimes that exercise alone will make the problem stand out like a sore thumb.

Please find out, when exactly the message gets send by the transceiver and when the full message is received by the receiver (finding out, which part of the code causes the delay). You can light an LED right before sending the message, turning it off afterwards. and on the receiver you can turn on an led, when the message got fully received. That way you can determine, if the timing problem really lies in the radio code, or if it is something else.

@Delta_G It is lined up in my code but when I put it in here I just manually spaced it so I know it is not great to look at. But in my actual code it is.

@chrisl When I look at the serial monitor most of the time the messages are sent and received immediately.  For some reason sometimes it will report to me that the message failed to send.

@jsotola The motors work fine when they are connected to a direct power source. The transmitter and receiver have some delay which affects the motors, which is why it will spend for a while without me using the joystick. Using deductive reasoning and some help from a professor I understand my issues are with the communication between the two NRF24I01 I just do not understand what it is.

@jsotola Yes but the main issue is the delay when I move the controller. It does not matter if I move the motor side to side or forward or backwards the same issue will occur... or another common issue if i hold the controller in one spot (forward, backwards left, or right) the motors may not start I keep holding the stick for many a minute or 30 seconds then the motors will start. After I let go of the joystick the motors will still spin for a little longer than the time I help the joy stick in that position.

@jsotola I kind of understand what you are saying. If it help I am using a motor driver to control the motors. For the issue you are saying is there a resource you know of that can help. Right now I am using the transmitter code that connects the joystick to move the individual motors so I have a full 360 scope of movement.  This project has deemed to be very difficult and my knowledge of code is not that strong so I am having to teach myself so my understand of the components responsibilities are lacking.

solve the problem in steps .... the transmission delays do not really matter right now .... transmit only the joystick position of only one axis .... on the receiver, move both the motors at the same time and in the same direction .... choose the forward or backward depending on the joystick value received  ..... your code is pretty close to that already

I am only using one joystick to control both the motors would this make a difference to your suggestion?

a joystick usually has X and Y .... send only one .... that way you have only simple data to deal with

I ditched the RH_NRF lib due to x problems when used in applications like yours, I now use an optimized high speed nRF24L01 library Give it a try https://github.com/nRF24/RF24

I would suggest changing your code so that you only send any data when the position of the joystick actually changes, rather than blasting data constantly flooding the link.

@Majenko this does not work (sending only when changes) if you use it as RC equipment. In my boat /flying models this acts as fail safe/heartbeat -no signal from the remote stop engines or initiate failure procedure. (Just as an info for the special case usage in remote controled models)

Periodic sending is fine. Flooding a digital link could cause problems. A regular heartbeat packet one every 100ms or something shouldn't flood the link and give you your failsafe.


text:
Pushbutton and switch case follow up question
PROBLEM STATEMENT:

A circuit is measuring various parameters (Temperature, Humidity,
etc.) through sensors connected to it continuously.
When a Push Button is Pressed and Hold for 2 seconds in between the Arduino should enter into Setup mode.(I have used IF loop and
millis() function to achieve this )
In Setup mode there are 6 screens which will appear one after one.
Once Arduino enters into Setup mode Switch case 0 (screen1) should appear (I have used serial monitor for the same).
Now if I press the same push button and released within a moment the next Switch case 1 (screen2) should appear.
Step 5 will be repeated till Switch case 5 (screen6).
After Switch case 5 the loop rolls over to Switch case 0 (SCREEN1) then Switch case 1, Switch case 2, so on.
If in between above Switch Case loop Push Button is Presses and Hold for 2 seconds the Switch case loop must get terminated and the
Arduino should go back to MAIN LOOP() where it is measuring the
sensor parameter.
Again if the push button is Pressed and Hold for 2 seconds in between sensing process the Arduino should enter into Setup mode.

CONSIDERATIONS:

Push Button is connected to Pin2 of Arduino (ACTIVE LOW)
The input at Pin2 is considered as interrupt so that Arduino provides service to any moment of the time.
Arduino serial monitor is used to demo the Screen1-Screen6 as output.
0.1uf Capacitor is used across the Push Button for debounce considerations. And 10K, 0.25W resistor is connected from VCC to Pin
no.2
The code for sensing parameters (Temperature, Humidity, etc.) is yet to be written.

ACHIEVEMENT:
Upto Point No. 7 of PROBLEM STATEMENT the code is working fine.
BUG:
If I press Push Button for 2 seconds in SWITCH CASE loop, Arduino is going out of the SWITCH CASE and going into MAIN LOOP() but again coming back to SWITCH CASE() loop.
It should ask again to press Push Button for 2 Seconds to enter into Setup Mode.
const int btn = 2;
const int ledPin =  13;
int selector = 0;
boolean  volatile wait = false;
const unsigned long event=2000;
unsigned long previous1=0;
unsigned long current1=0;
unsigned long sum1=0;
unsigned long previous2=0;
unsigned long current2=0;
unsigned long sum2=0;
bool buttonPress = false;
void setup()
{
Serial.begin(9600);
pinMode(ledPin, OUTPUT);
pinMode(btn, INPUT);
attachInterrupt(digitalPinToInterrupt(btn),decoder,CHANGE);
}

void loop()
{
  if (digitalRead(btn) ==LOW && !buttonPress)
  {
    previous1 = millis();
    buttonPress = true;
  }
  else if (digitalRead(btn) == HIGH && buttonPress)
  {
    current1 = millis();
    sum1=current1-previous1;
    Serial.println(sum1);
    Serial.println("SUM1");
    if (sum1>=event)

       {  BREAK1:
          doSwitchCase();
          selector++;
          goto BREAK1;
          if (selector >6)
              {
                  selector = 0;
                  delay(500);
              }
        }
        buttonPress = false;
  }
  wait = true;
  interrupts();

}

void decoder()
{
 noInterrupts();
 wait = false;
}

void doSwitchCase()
{
  switch(selector)
  {
  case 0:
    Serial.println("SCREEN1");
    while (digitalRead(btn)!=LOW) ;
    previous2 =millis();
    while (digitalRead(btn)!=HIGH) ;
    current2=millis();
    sum2=current2-previous2;
        if(sum2>=event)
        {
         Serial.println(sum2);
         loop();
        }
    break;

  case 1:
    Serial.println("SCREEN2");
    while (digitalRead(btn)!=LOW) ;
    previous2 =millis();
    while (digitalRead(btn)!=HIGH) ;
    current2=millis();
    sum2=current2-previous2;
        if(sum2>=event)
        {
         Serial.println(sum2);
         loop();
        }
    break;

  case 2:
   Serial.println("SCREEN3");
    while (digitalRead(btn)!=LOW) ;
    previous2 =millis();
    while (digitalRead(btn)!=HIGH) ;
    current2=millis();
    sum2=current2-previous2;
        if(sum2>=event)
        {
         Serial.println(sum2);
         loop();
        }
   break;

  case 3:
   Serial.println("SCREEN4");
    while (digitalRead(btn)!=LOW) ;
    previous2 =millis();
    while (digitalRead(btn)!=HIGH) ;
    current2=millis();
    sum2=current2-previous2;
        if(sum2>=event)
        {
         Serial.println(sum2);
         loop();
        }
   break;

  case 4:
   Serial.println("SCREEN5");
    while (digitalRead(btn)!=LOW) ;
    previous2 =millis();
    while (digitalRead(btn)!=HIGH) ;
    current2=millis();
    sum2=current2-previous2;
        if(sum2>=event)
        {
         Serial.println(sum2);
         loop();
        }
   break;

  case 5:
  Serial.println("SCREEN6");
    while (digitalRead(btn)!=LOW) ;
    previous2 =millis();
    while (digitalRead(btn)!=HIGH) ;
    current2=millis();
    sum2=current2-previous2;
        if(sum2>=event)
        {
         Serial.println(sum2);
         loop();
        }
  break;
  }
}

One note before NEVER use goto in C++ its bad style and makes in an object oriented language to 99.9% no sense. To enter the switch case after a2 second press you have just to enter one statement t omy original proposal.I did not read your code as it gets unreadable the more functionality you want to add. Think about refactoring it or you will run out of luck to get help (as nobody tortues himself with caotic code of others:
const int btn = 2;
const int ledPin =  13;
int selector = 0;
const unsigned long buttonPressLong = 2000;  // 2 seconds
const unsigned long buttonPressShort = 250;  // 0.25 secondis feasable
const unsigned long buttonPressDebounce = 50;  // debouncing for too short presse Thanks Edgar Bonet
unsigned long buttonPressStart = 0;

bool buttonPress = false;
bool inMenu = false;

void setup() {
  Serial.begin(9600);
  pinMode(ledPin, OUTPUT);
  pinMode(btn, INPUT);
  }

void loop() {
  if (digitalRead(btn) == LOW && !buttonPress ) {
    buttonPressStart = millis();
    buttonPress = true;
  }
  // The routine is only triggered if a previous pressing took place, otherwise it's ignored
  else if (digitalRead(btn) == HIGH && buttonPress) {
    if (millis() - buttonPressStart > buttonPressLong && millis() - buttonPressStart > buttonPressDebounce && inMenu) {
      Serial.print("Long press: ");
      Serial.println(millis() - buttonPressStart);
      buttonPress = false;
      inMenu = false;
    }
    if (millis() - buttonPressStart < buttonPressLong && millis() - buttonPressStart > buttonPressDebounce && !inMenu) {    // HERE IS A CHANGE
      Serial.print("First long press ");    // HERE IS A CHANGE
      inMenu = true;
    }
    if (millis() - buttonPressStart < buttonPressShort && millis() - buttonPressStart > buttonPressDebounce && inMenu) {
      Serial.print("Short press: ");
      Serial.println(millis() - buttonPressStart);
      doSwitchStatement();
      selector++;
      if (selector > 6) {
        selector = 0;
        delay(500);
      }
      buttonPress = false;
    }
  }
  // Here you could do other stuff as it is non blocking
}
doSwitchStatement(){...}// Stays the same as yours

I just changed 1 statement (and 1 debug msg) to achieve what you want see // HERE IS A CHANGE


text:
invalid conversion from 'char' to 'const char*' [-fpermissive] on a string
I am compiling some code I didn't write, and it bombs out with the error message
invalid conversion from 'char' to 'const char*' [-fpermissive]

on the line
if (loginPassword == '\0') loginPassword = "";

I don't see why that line is any different than the previous strings, and the answers I can find all have to do with variables that start as char.
What is wrong with this code, and how do I fix it?
    void saveUnit(String tempUnit, String supportMode, String loginPassword, String minTemp, String maxTemp, String tempStep) {
      const size_t capacity = JSON_OBJECT_SIZE(6) + 200;
      DynamicJsonDocument doc(capacity);

      // if temp unit is empty, we use default celcius
      if (tempUnit == '\0') tempUnit = "cel";
      doc["unit_tempUnit"]   = tempUnit;

      // if minTemp is empty, we use default 16
      if (minTemp == '\0') minTemp = 16;
      doc["min_temp"]   = minTemp;

      // if maxTemp is empty, we use default 31
      if (maxTemp == '\0') maxTemp = 31;
      doc["max_temp"]   = maxTemp;

      // if tempStep is empty, we use default 1
      if (tempStep == '\0') tempStep = 1;
      doc["temp_step"] = tempStep;

      // if support mode is empty, we use default all mode
      if (supportMode == '\0') supportMode = "all";
      doc["support_mode"]   = supportMode;

      // if login password is empty, we use empty
      if (loginPassword == '\0') loginPassword = "";
      doc["login_password"]   = loginPassword;

      File configFile = SPIFFS.open(unit_conf, "w");
      if (!configFile) {
        // Serial.println(F("Failed to open config file for writing"));
      }

      serializeJson(doc, Serial);
      serializeJson(doc, configFile);

      configFile.close();
    }

I'm guessing this was copied out of a context where loginPassword was a pointer rather than String, where it probably should have really been compared with nullptr or 0 depending on the era of C++.

@timemage
https://github.com/gysmo38/mitsubishi2MQTT/blob/master/src/mitsubishi2mqtt/mitsubishi2mqtt.ino

Okay.  If that's the original context, I have no idea why it ever compiled.  You don't get this same error for supportMode and the others that follow this same pattern?

Correct, this is the first line that breaks. I can't figure why, when it should break before this.

It seems likely all that follow the pattern if (X == '\0') X = some_default; should have been written if (X == "")  ...  or maybe more efficiently if (X.length() == 0)  ..., but this is sort of nonsense for the loginPassword field. If it's already blank... it's blank.

Alright, well, if I run arduino-cli compile against an esp32:esp32:esp32 FQBN, with minimal scaffolding around your code, e.g. including ArduinoJson.h, SPIFFS.h, empty loop and setup, it compiles without error.  The esp32 core that happens to be on my machine is 1.0.4, probably old, but that's what I have.  ArduinoJson was version 6.18.0.

Same version of ArduinoJson, compiling against esp8266

Let us continue this discussion in chat.

Regardless of the findings below, you don't really want to compare a string object with a null-character this way (more on that below).  Really something like:  if (someArduinoStringObj.isEmpty()) { is a better idea, no matter what core you're on.
So for anyone that has landed here with this problem with code that had worked and no longer works, the answer is basically don't do that; probably shouldn't have been doing that in the first place.
If you're curious on what I found, there's material on that below.

So, I don't have a complete handle on this, but I do have something to report.   When we started going through this I didn't think there would be anything going on in the Arduino board support packages that would have any effect on this, but it turns out that's not the case.
We worked out that under ESP8266 Arduino core 3.0.0 the lines of the following form fail to compile and under version 2.7.4 the compile without error.  Here under 3.0.0 it was not picky about specifically loginPassword.
if (someArduinoStringObj == '\0') someArduinoStringObj = "some literal";

This can be abstracted to the somewhat nonsensical:
someArduinoStringObj == '\0';

Since that's the part makes the difference.  I really thought there was something more clever going on in the WString.h/WString.cpp code, an extra constructor or implicit conversion operator call prior to the code for the == operator.  There is an explicit constructor for String that takes a single char, but it's just that, it's explicit; it doesn't take part in evaluating the == expression above.  And there's no automatic conversion from String to const char *. It turns out that isn't anything clever going on in String class when it comes to this problem.  In fact you can boil this down to something similar so that the String class itself isn't actually involved at all, into:
void func(const char *) {}

void setup() {
  func('\0');
}

// ...

This will likewise pass compilation under 2.7.4 and fail with a similar error message under 3.0.0.  So, with String it is just trying to call the operator==(const char *), even though it's being given a char type.  Before getting into that, I tested a theory, which was to find out what happens if given == '\1'; or == 'X') etc, any non-zero value, because 0 has had an interesting relationship with pointers in C++ and C.  It makes more sense once you realize there's special going on in String.h.  We're basically talking about func('\0') vs func('\1') or func('X')  Well, under 2.7.4 these values fail where '\0' does not, but under 3.0.0 both fail.  So I got looking into the platform.txt file on both core versions, thinking maybe I'll spot a difference in compiler options.  E.g. it would make "sense" if 2.7.4 had -fpermissive where 3.0.0. didn't, but that's not the case.  The major difference is that 3.0.0 has -std=g++17 and 2.7.4 has -std=g++11.  Just for the hell of it I stole the command-line out of the verbose output compiling for the .ino.cpp file and replaced -std=g++17 with -std=g++11 and applied it to a cut-down file; didn't make any difference.  So, as far I tell there's some difference in default options specified between the two compiler versions in use in the two esp8266 package versions.
Constant expressions that evaluate to zero of int type (at least), will convert to null pointer constants.  I haven't been in the habit of using character-typed ('\0') zero valued constant expressions for null pointers, and I haven't dug through the various editions of the C++ standard to see what each one has to say about them; color me unsurprised either way.  But in any case, that's is basically what's happening here: The string object is being compared to a null pointer constant, at least when it compiles.  And if that makes you go WTF, well, me too.  If you follow this out, you ultimately you end up here:
unsigned char String::equals(const char *cstr) const {
    if (len() == 0)
        return (cstr == NULL || *cstr == 0);
    if (cstr == NULL)
        return buffer()[0] == 0;
    return strcmp(buffer(), cstr) == 0;
}

So, roughly speaking someArduinoString == '\0', where it will compile, is equivalent to someArduinoString == nullptr which is sort of the same effect as someArduinoString == "".  So, what you're seeing is not exactly an implicit form of someArduinoString == String('\0').
I can't picture wanting to say someArduinoString == '\0' over someArduinoString.isEmpty(), but in terms of why it doesn't work on 3.0.0, I'm still unsure.  I can tell you that it will if you plant -fpermissive into platform.txt, but that doesn't really explain it.  Sometime when I'm really bored I'll see what the language standard actually says and what versions of g++ did what under what options.
Even I worked that out my answer would still be: don't do that.


text:
How to make 12V flashing LEDs using an Arduino Uno?
I have 3 LEDs powered by an Arduino; each LED has its own flash rate.
Now I want it to be powered by an external 12V power source and still have the flashing function of the Arduino?

You will need a transistor or a MOSFET to do that (one per LED). Just google that and you'll find many examples how to do it. On Arduino.SE, there have also been many questions about this topic.

Thank you very much! I tested it and it works perfectly! :D

Use a N-channel MOSFET, wire load to drain pin, source to (common) ground, and place a 1 kilo-ohm resistor in series with your arduino pins. Bear in mind that MOSFETs respond to voltage, not milliamps, on the gate - get one that responds well to 5V logic.

You do not need a series resistor with a MOSFET (although it does no harm). If using a bipolar transistor it is essential.

@Milliways We discussed that before. Different strokes I suppose.

Or you could use a relay. Many small ones available for a couple of dollars.

Using a relay for such circuit would be just annoying because of "clicking" on relay.

Hmmm, I didn't read that that was a criteria, not to mention that there are small, quit, solid state relays.

As has been mentioned, you could use an N Channel MOSFET, but preferably look for a Logic Level MOSFET.  These are capable of being turned on by lower voltage levels such as on the pins of an Arduino.
Having said that, i have used two non logic level MOSFEt's in Arduino projects successfully.  They are the IRF3205 and IRF 520 - both are readily availalable and will work OK with the Arduino output pins for your low-current-driving-an-LED requirement.

license: Creative Commons - Attribution Share-Alike - https://creativecommons.org/licenses/by-sa/3.0/


text:
Using Arduino libraries for adding more functionalities to a bootloader
I have a short question to ask before putting time for research.
I have an Arduino Leonardo with the LUFA mass storage bootloader flashed. Now what I need to do is to add more functionalities to the bootloader. Because in the final product, the Leonardo board will be connected to a fitness machine (permanently connected) and the machine has Windows OS. Then the Leonardo should be able to read an RFID card (I need to add an RFID reader to the board, each user has his own RFID card) and then mount a remote server directory to the local USB Host based on the selected user.
I will have to use a wifi shield too. My question is this: is it theoretically possible to add all these functionalities to the LUFA mass storage bootloader? Because it's not possible to use the Arduino IDE for this purpose, since I'm not uploading any sketch on top of the bootloader, rather than editing the existing mass storage bootloader with the required functionalities and re-flash the chip. Am I correct? (This is what I understood after some research. And I'm a noob :D).
Could you please elaborate what would be the first step for solving this issue?

I couldn't understand WHY you can't create a sketch running after the bootloader that runs the code. Anyway just write a program (like a sketch in arduino, or use directly the avr tools) and then upload it. I suggest you to upload it in the usual way, but if you don't want the bootloader anymore just use an external programmer: you will overwrite it.

just an addendum: a bootloader is just a simple program wich executes at boot and loads the main program after some operations (e.g. check if a newer program should be downloaded and flash it). If you want to use as the normal program, it's not a bootloader anymore (since it is not used to load), but simply a program

mount remote server directory to local USB Host -- Do you have any concept about how those two things operate, and the disparity between them? And how what you propose can never work?

I'm not getting why you want to put all your code in the bootloader. That just doesn't make sense.

@frarugi87 I think my question was not that clearly explained. LUFA mass storage bootloader was used to replace the existing Leonardo bootloader. Now when I plug it to the PC, it doesnt recognised as uc but as a mass storage. So I can't use Arduino to program the application memory

Ok, now I got it. Sorry, since I never played with leonardo I was not used to how the programming or bootloader replacement was done. Anyway, but I may be wrong, since I just did a 5-minutes research, you just have to grab the LUFA source code, install the AVR tools to compile, try to compile the example and see if it works. If it does, you have everything set up correctly. Then modify the LUFA source code to do what you have to, thus creating the program (aka firmware) you need and... You are done. And it won't be a bootloader anymore, but just a firmware ;)

@frarugi87 Thanks for the reply. I kinda got this part. And the mass storage example works fine. But my problem is including arduino libraries to LUFA examples. Because each of these examples have one main makefile and several other makefiles. For a beginner like me it's quite hard to figure out where to add these relevant libraries. For ex: I want to use a SD card shield, and I have to add the libraries in a make file and call the setup function in LUFA  massstorage.c main class :o

Ok, I'm kind of slow these days, so sorry for taking so much to understand ;) Well, arduino compilation is somewhat "simpler" than regular one, so a lot of details are hidden. Now you are moving towards a more "standard" way of coding. For the SD card example, go into the arduino source files folder (don't remember where they are) and grab the files SdCard.h and SdCard.cpp. You'll also need Fat16Config.h and SdInfo.h probably, but compilation errors will tell you what are the missing files. Create a copy of MassStorage (will be your program) and inside of it create the folder MyLibs ...

... and put the sd card library files inside. Now open the makefile and search the variable SRC. These are all the source files you are compiling, so add the source files you have added (in this case, only SdCard.cpp, since the other are header files). And then you (should) have included the SdCard library to this program. Use it like you would in an arduino sketch (so include the header and then use the class). Just one remark: I think you'll need to rename BootloaderMassStorage.c to BootloaderMassStorage.cpp, since you need classes inside (and then there will be problems with plain C, so ...

... maybe you'll need to rename all the files to cpp - and of course change the c extension to cpp also in the makefile). Once done, recompile and flash. There will be a lot of errors, but usually I deal with them one by one, since I'm not much expert and so I usually make a lot of mistakes

@frarugi87 Thanks for the detailed explanation. I will try what you said and will post you about the progress :)

@Isuru sorry, but I read the answers and a question arose: why do you need this? Isn't it simpler to have Windows mount the folder? Through the leonardo you detect the ID, pass it to the PC and then it automatically mounts the correct folder. Do you want more security? Use encryption: store the keys on the leonardo, then show only the enabled one. This way it will be simpler for the PC, and you will get bonus features like network on the PC (and so even remote access or database upload)

Let us continue this discussion in chat.

@Majenko: I think, that the task IS possible, but it is really hard (and Leonardo may need more memory for that eventually and some shields too and so ...) but if I understand the problem, than the Leonardo should pretends to be mass storage device for that application, and pretend it have some folders and files on it, depending which RFID is used to activate it.
The application probabelly is NOT going to format the MSD because it would lose all the user data on it.
So Leonardo can do following:

pretend it is already formatted and have some known filesystem on it (vfat is easy enought and probabelly usable as many USB flash sticks came with it)
when the machine detects inserted USB, it ask for type - so it get MSD
then it will read partition table - Leonardo can emulate it easily, having "just one partition of given size and type" the partition can even be stored as a file on that fileserver to save Leonardo's memory.
next goes reading FAT table and root directory

knowing  the user from RFID it is possible to select the right directory on file server,
then enumerate lengths of all files inside (and directories)
make table with the names and "offset"
send back the FAT as if those files were ordered on the "disk" so each entry points to the following sector, until the last marks EOF
root directory begins after FAT and contains names of the files, their lenghts, dates and starting sectors (and some very basic right like read-only, system and such)
then follows files and directories

each time the machine asks for a "sector", it is possible to compute, in which file the sector is placed, read the portion of a file (potentially fill it with zeroes to "sector lenght" and return it as requested "sector"
if the sector is in directory instead, return the part of directory (that means filenames and such)
if the sector is outside it all (should not happen), return just zeroes.

On the other direction:

if you get something outside structure, put it to temp. file along with address of such stray "sector"
if you get something in a file, just replace the file content on given offset
if you get something in directory, you need to compare it with previous version and "rename file", "create file" or "delete file" acordingly.
it would probabely need two directories on the server for each user - one for actual files, other for "lost sectors" and "deleted files" which could be "reconected", "undeleted" or "attached later" to the files/directories. The second directory can be emptied after "removing USB MSD" when user with given RFID logouts.

It is lot of work, but basically it could be done. It also needs a lot of accounting on the Leonardo and lot of communication with the fileserver, but it is possible to do.
It suppose, that the files on fileserver would not be modified by somebody else while "mounted" and that the Windows machine would not "format" the USB to some kind of filesystem, the Leonardo does not understand (how to translate to the real files on server).
But for the supposed use I think those two conditions could be reasonable. The MSD probabelly just holds the "user profile" so the machine can put in records of hir/her activiti, some stats and so on, probabely it would be just a few growing files maybe even just in root directory.
Anyway I would not like to write such system, as it is terrifying lot of work and a lot of things could go wrong, if there is a bug (or bad connection).
Also the size of required memory for Leonardo is large - probabelly larger, than the Leonardo actually have, but it could be offloaded to the filesystem too (in "hidden directory" not shown to the machine) - which would be slow and hard to manage - or expanded by HW RAM, which would be a lot faster, but needs nontrivial settings.
(Remebers me, how I wrote resident program for DOS, which had just 130 bytes, which swaped in two 16KB widows of EMS where the rest of program (actually interpret of some pseudocode) was placed (it was like 4 or 6 such 16KB pages, but was able to swap itself acordingly) while the remaining two EMS pages was reserverd for data (like 300-400KB total of pseudocode and data) which was also swapped as needed to access everything. From DOS point of view it was just the 130B resident API, from the view of program, which was using it, it was 400KB engine running FORTH-like program and containing database. The result was like 3x faster processing of 2.000+ employes wages.)
Here are the memory restrictions even more tight, but I thing, that it is possible to do such thing, only it is extremely hard to make it work reliably.

Thanks for your detailed answer. I got the general idea about what you explained. Regarding the files that will be written to Leonardo: There will be around 23 small files(no folders) with format "ini", "apt" and "dat". And the Leonardo mass storage has FAT12 file system. And I will extend the storage with a SD card. Yet I have less knowledge in file systems. So I will be spending the next few days on researching about the topics you mentioned. Life is hard xD

From your brief description of what you want to do I think you want to:

Mount a Windows share on your Leonardo
Make said share available through USB MSD

Well, sorry to break it to you, but that is not possible. No, it's not because the Leonardo isn't up to the task, but you are trying to mix two completely different concepts.
A Windows share (CIFS) is a file-centric system. That is, you access files within the share and request bytes at offsets within the files. The client has no concept of the underlying filesystem, it just works on files.
A USB MSD device, in contrast, has no concept of files, directories, etc. Instead all it knows about is blocks. Raw fixed size blocks of data. The computer that it is attached to is what knows what a filesystem is. It requests blocks of data from the MSD and interprets them as a filesystem, allowing you to access the files within it.
You can see the problem you would now face? MSD responding to requests for raw blocks of data from a computer which then wants to get the contents of files from a server - how do they fit together? Simply: they don't.
So you are going to have to re-think your basic idea.
One possible idea would be to use some client-server block based system, such as iSCSI, which gives you block devices on a network (a single file which is an image of a virtual disk), though only the device which is attached to that block device through the network can see the content of it.

all_licenses: Creative Commons - Attribution Share-Alike - https://creativecommons.org/licenses/by-sa/3.0/


text:
Store data in flash/EEPROM and process it in parallel
I want to store incoming data in flash or EEPROM and then apply FFT or some other method to detect frequency and intensity.
I am taking sound through microphone amplifying it with an LM741 and giving this amplified signal as input to an Arduino and then processing it at the same time.
But the problem is that the time taken in running the code is interfering with the sampling rate. I want to store say 50 inputs in flash and then process these 50 numbers, while at the same time the next set of 50 numbers is being stored, so that I can have data stored at a constant sampling rate.
Also how can I store data continuously? Because if I do this in loop() won't it again have time lag due to rest of the code?
I am new to Arduino, so please give details or some link to help me understand.
Thanks.

Writing to EEPROM is probably too slow. Just store it in memory. You can set the ADC to run in free running mode, where it will continually measure the voltage. You can then attach a function to the interrup so it run whenever a conversion is ready. You can store the values in a ring buffer. So the interrupt will fill the buffer with new data, while the loop will process the data and remove it from the buffer.

But will I be able to measure the time between any two reading? I want to get the frequency and so I need the time between any two data which I intend to keep fixed. So to be clear, I should store data by setting clock frequency and using free mode in setup and attach a function (to process data) to interrupt when the ring buffer is full, and do nothing of this in Loop?

Time between readings is constant in free running mode. I think you can even use a timer to trigger ADC conversions if you need a specific sampling frequency (instead of changing the ADC clock prescaler). You don't need an interrupt for when the buffer is full. Just have the loop check with a if statement if there is enough data in the buffer to start prosessing it. Ideally you'd process the data as it is coming in instead of waiting for a lot of data, and the process I'll this data in one chunk. But this depends on your situation.

Thanks a lot. I am going to read more about it and try to implement it.

A common method of overlapping data input with data processing uses double (or multiple) buffering.  For example, one of two buffers is processed in the foreground (that is, in the loop() routine) while another buffer is filled in background (via interrupt handlers).  Each time a buffer fills, the usage of the two buffers swaps: that which was being processed now refills, while the recently-filled buffer gets processed.  To make this work, buffer processing must take less time than buffer filling.
For recording conversion times, because free-running ADC conversions each take the same amount of time, you can just save fill-start and fill-end times with each buffer, and interpolate to find out reading times.
If you plan to process audio data at near-normal speeds, it's likely most Arduinos won't be fast enough to keep up.  However, using an Arduino Due probably is feasible.  The Due is based on an ARM Cortex M3 processor with 72 MHz operating frequency, 32-bit arithmetic, large RAM (for an Arduino), etc.
An alternative method of processing audio data is to use a frequency analysis chip.   Here is a low-end example:  The MSGEQ7 Graphic Equalizer Display Filter is about $5 in an 8-pin DIP package from sparkfun.com.  Apparently, it continuously measures peak spectral intensity in each of seven frequency bands, and can read the peaks out perhaps a thousand times per second.  Audio goes in on the "Audio in" pin.  A Reset pin resets an output-multiplexor counter to zero.  Each time after you clock a strobe line, a band's reading is presented as an analog voltage on a "DC out" output line; the band's peak reading is decayed about 10%; and the multiplexor advances one band upward in frequency, rolling over from highest to lowest every seven strobes.

What I want to do is store incoming data from in flash or eeprom

No, for your application you absolutely do not want to do that. You want to use RAM instead.
The Arduino has three kinds of memory:

Bytes in RAM (also called SRAM) can be written an unlimited times and written very quickly. RAM is designed for short-term storage of information while a sketch is running. The contents vanish when the Arduino is turned off, but this isn't a problem for you unless you need to process previously read information later on after the Arduino is turned back on. An Arduino Uno has 2048 bytes of RAM and all your C/C++ variables must fit in that.
An EEPROM byte can be written around 100,000 times; writing it is much, much slower than writing a RAM location. This makes it very bad for doing intensive processing, as opposed to, e.g., just storing configuration variables that are rarely read. EEPROM is designed for storage of information across power cycles of the microcontroller; unlike RAM, previously written data are still there to be read when the Arduino is powered on. An Arduino Uno has 1024 bytes of EEPROM; this is only used when your code or library code explicitly requests data be written to or read from it.
Each block of flash memory can be written around 10,000 times; writing it is much slower than RAM, though it can be read very quickly. Flash storage is designed for storing programs, not data; it's the memory from which instructions are read, though you can with care store "constant" data in it too. It's only changed when you upload a sketch via USB.* An Arduino Uno has 32768 bytes of Flash memory and your program and any constants you store in Flash must fit in it.

* Not technically true, but if you know how to use Flash for runtime data storage, this answer isn't providing you any useful information. :-)


text:
PCF8563 does not remember time when restarting Arduino Uno?
I'm trying to use the following RTC module (PCF8563) with Arduino Uno.
I am using this library to set/get time and date from PCF8563. However, whenever I shut down the Arduino, the time/date is lost! Even though, as you can see in the picture, the module is equipped with a 3V battery to keep running when Arduino is unplugged.
Any help would be highly appreciated!

Did you try to put the jumper in the “BAT” position?

[SOLVED]
The solution is simply to put a jumper between BAT and VCC positions in the module itself. Many thanks to Edgar Bonet


text:
Digital read on voltages between 1 and 31 volts?
Hello Arduino comunity!
I am working on a circuit that uses an Arduino Mini to read values from certain points of a boost/buck converter circuit to determine things like input state, output state, overheat and so on. The circuit is working all right, and the only part left to do is to connect the digital pins of the Arduino to the different points in the boost/buck regulator.
The problem is however that I need to read from a range of voltages between 1 and 31 volts with the Arduino, which isn't possible, because not only will it damage the controller if the voltage exceeds 5V, but values below 3V will be regarded as false.
I thought of putting some potential dividers, which would obviously not do the trick, and I also thought of using a WS78L05 voltage regulator per input pin (because each pin might have a different voltage from the rest) but that isn't dealing with voltages <=5V and 31V exceeds its rating as well.
Lastly I thought of using transistors, which seemed like a good idea, but I would require 2 transistors per input wired as follows:

simulate this circuit – Schematic created using CircuitLab
But it is impractical to do for 4 inputs and there is limited space available on the PCB too :(
Is there any IC that encapsulates the circuit above, or is there any other way to achieve what I want to do?
Thanks very much :)

First you need to look at each individual input and what exactly it is sensing, and what those voltages mean. Then you can work out what you need for that input. Don't try and make a "one solution fits all" system,  unless all your input sense the same thing.

@Majenko Not trying to find a 'fit all' situation. The thing is that the output can either be on, or off therefore 1 or 0. If the output voltage is 10V or if it is 31V makes no difference, the output is open (1) whereas if the voltage in the output is 0V it means that the DPDT switch before it is off therefore the output is closed. Thats what im trying to sense. Same aplies for the input and the overheat switch (it is a 65C thermal switch. if it is off then there is overheat, if it lets n volts through then its alright)

So a voltage divider sized to cope with the highest voltage you want to sense, fed into an analog input. You then read the value and compare it to a threshold for on or off.

@Majenko Well the potential divider i thought of consists of a 51k and a 10k resistor (we dont need much current) at 31V it produces 5.082V which is alright, however at 1V it produces 0.16V which would be hard to sense and would very easily provide false-trigers... Not to mention that it would probably drop even further with a pulldown resistor :(

0.16V would read 32 on the ADC. That's plenty, surely? If you want more, then size your divider a little higher (say 7V) and clip it with a 5V zenner diode?

What are your thresholds for on/off?

Using a simple voltage divider (51K / 10K as you have worked out already) fed directly into an ADC input will give you a reading of 32 on the ADC at 1V input. That should be enough to give a reliable threshold detection.
If you want to have higher sensitivity at lower voltages you can increase the output of your voltage divider to more than 5V and then clip it with a zenner diode. For instance if you reduce the 51K to 33K you get 7.2V out of the voltage divider. A 5V zenner diode can then clip it to 5V. Your 1V input (which would be 0.233V on the output of the divider) would now read 47 on the ADC. Anything over 21V would then read 1023.

simulate this circuit – Schematic created using CircuitLab
Theoretically you could get away with not having the voltage divider at all and just using the zenner and one resistor to clip the incoming voltage to 5.1V. That would give you the greatest sensitivity, but also the greatest current flow through the zenner.

simulate this circuit
Size R1 to limit the current at your maximum voltage to within the rating of the zenner.

Thanks for the response, it does make sense but i dont  think that i can manage all those in the tight space i have :S 4 input pints that need voltage regulation (they are one next to the other) and the space in which i need to fit all that is small (it has to be to fit in the enclosure as well) Also which of the two designs above is going to be the one with the least drop when 1V is in the input? Also isnt there any IC you are aware of that holds the two transistors in the arrangement i showed above? Lastly, it just poped in my mind to use optocouplers. Would that be possible and effective?

Why do you use a zener, instead of clamping the voltage to the 5V rail with a regular diode?

@Gerben Because it gives less noise on the power rail that way. With a regular diode it takes time to switch from reverse to forward bias and you get spikes of noise on the power rail while it is doing that. With a zenner it breaks over at its rated voltage and limits the voltage without needing to switch from reverse to forward bias.

@fillpant The second design will give you 1V out when you put 1V in. It will give you 3V out when you put 3V in. It will give you 5.1V out when you put 6V in. It will give you 5.1V out when you put 31V in. It doesn't scale the voltage, it clips the voltage. Anything above 5.1V is thrown away as heat in the resistor.

@fillpant Opto couplers are possible, yes, but I would have thought a resistor and zenner diode would be the smallest possible footprint. Especially in SMD formats.

Alright i see! I dont have the ability to solder SMD's but i agree they would fit perfectly.
Im probably going to go with the zener and resistor solution.
How many mW will the zener have to handle in the worse-case (31V)?
Lastly i found this: http://www.nteinc.com/specs/2000to2099/pdf/nte2033.pdf will something like that do the trick? an 8 pin chip fits perfectly, so if i find the respective IC but with positive input and positive output i bet it would work just fine wouldn't it?
Thanks :)

Use two quad lm339 voltage comparator chips to make an analog to digital convertor-you will need 2 to read 31 volts accurately. Its a standard ADC circuit, with this common lm339 is,  so a search will find circuit-it may need a simple modification to combine the two circuit.

The junction of a 51KΩ, 10KΩ voltage divider will feed an Arduino ADC input 5.08 V at 31 V input, and 0.16 V at 1 V input.  With a 5 V reference, I think the first of those will give 1023 counts, and the latter, 33 counts.  This is from 1023*(1/5)*10/(10+51) ≃ 33.54.  That may be enough counts for reliable detection, depending on how noisy the environment is.
For more sensitivity at lower voltages, if the first reading is less than 225 counts, one can switch to the 1.1 V internal ADC reference and take another reading.  (1023*1.1/5 ≃ 225.06.)  With a 1.1 V reference, a 1 V input to the divider produces 152 counts, and a 6.7 V input produces about 1023 counts.  (1023*(1/1.1)*10/(10+51) ≃ 152.46 and 1.1/(10/61) ≃ 6.7.)
To change the ADC  reference voltage, say analogReference(DEFAULT) for Vcc reference, or analogReference(INTERNAL) for 1.1 V reference.


text:
Help: convert Arduino code to avr-gcc code
I need to convert Arduino code to avr-gcc code. This is code:
#include <Servo.h>

Servo myservo;

void setup() {
  myservo.attach(11);
}

void loop() {
  myservo.write(67);
}

I use Arduino Mega.

I'm voting to close this question as off-topic because this is not a "gimme tha codez" site.

Possible duplicate of Will a .ino Arduino Sketch compile directly on GCC-AVR?

You didn't actually ask a question, you might have asked: "how can I re-implement the servo library in avr-gcc", but that will require quite some effort and a little knowledge from your side.

Try this:
#include <Servo.h>

extern "C" void init(void);

Servo myservo;

int main()
{
    init();
    myservo.attach(11);
    for (;;) {
        myservo.write(67);
    }
}

Note that this still needs the Arduino core library, as the Servo
library depends on it, which means all this is an exercise in futility.
If you are using the Arduino core, the simplest thing is to use it the
Arduino way. If you do not want to use Arduino core, then you will have
to partially re-implement the Servo library.

@user29971: oops, forgot an include, fixed. Do not forget to add all the relevant -I, -L and -l options to the compile command.

compiler code in avr-gcc comand line in linux no include Arduino.h include avr/io.h. thanks Edgar Bonet

i use standard library and registers.

@user29971: If you do not want to #include <Arduino.h>, you can just declare init() yourself, see amended answer.


text:
Demultiplexing Arduino with C++ code
I have been working on a small project recently. I have a circuit like in the image below:

Hardware Setup Demultiplexer IR Test

As you can see I have 8 IR LEDs, which are driven by an MC14051B Multiplexer/Demultiplexer. My goal is to select each IR led individually and send data over the selected IR LED. None of the other LEDs can send signals. Only one LED at a time can be sending IR codes.

Hardware Setup Single IR Test

Below is the code I used to send the signal using the IR Library over one LED (no demultiplexer was used in this test).
// New function to send 'items' codes which are held in the array 'data'
void sendMulti (const uint8_t& items, const uint32_t* data) {
  for (int i = 0; i < 2; i++) {
    for (uint8_t itemIndex = 0; itemIndex < items; ++itemIndex) {
      irsend.sendNEC(data[itemIndex], 32);
      delay(1000);
    }
  }
  delay(5000); //5 second delay between each signal burst
}

void loop () {
  static const uint8_t MaxItems = 3;
  uint32_t  data[MaxItems] = {0x1067E21D,0x106722DD,0x106722DD,0x106722DD,0x106722DD,0x106722DD,0x106722DD,0x10676897,0x10676897,0x10676897,0x10676897,0x10676897,0x10676897,0x10678877,0x10676897,0x1067A857,0x1067A857,0x10678877,0x1067A857};
  sendMulti(MaxItems, data);
}

The Single IR Test was a success. However now I want to use the demultiplexer. Any advice or pointers will make me very happy.

Explain the usage of pin A0.

The most important document you have to read is called a datasheet. Here you can find the MC14051's.
I assume you already know how a mux/demux work, so... Well, you have eight LEDs, one on X0, another on X1, ... up to X7. The one connected to the pin X, which is your A0 (the pin used on irsend, I assume) is indexed by the three inputs A, B and C.
On page 5 you see the truth table. According to that table, you have to write a 0 on inhibit, and the value on ABC. So, to select led on X0, you have to write 0 on pins 7, 8, 9 and 10. If you want to select led X1, 8 should go high. For led X7, 8, 9 and 10 should be 1, while 7 is low. And this is for all the combinations...