text:
else if is ignored if not Serial.println anything before
I encountered to me inexplicable behavior on an arduino uno.
I'm serial reading a string from the serial monitor/python serial. This string is the conditional on several if/else if statements.
The crazy thing is, some strings just get ignored, but if I print out the read string after reading it, the ignored statements then get executed and the script works the way it's supposed to.
This is the code:
// power outlet 1
# define OUT_1_1 2 // relay #4
# define OUT_1_2 3 // relay #3

// power outlet 2
# define OUT_2_1 4 // relay #2
# define OUT_2_2 5 // relay #1

void setup() {
  pinMode(LED_BUILTIN, OUTPUT);

  // power outlet 1
  pinMode(OUT_1_1, OUTPUT);
  pinMode(OUT_1_2, OUTPUT);

  // power outlet 2
  pinMode(OUT_2_1, OUTPUT);
  pinMode(OUT_2_2, OUTPUT);

  // init outputs to HIGH
  digitalWrite(OUT_1_1, HIGH);
  digitalWrite(OUT_1_2, HIGH);
  digitalWrite(OUT_2_1, HIGH);
  digitalWrite(OUT_2_2, HIGH);

  Serial.begin(9600);
}

void loop() {
  String str = "";

  // checking for bytes in the buffer
  if (Serial.available() > 0) {
    str = Serial.readStringUntil("\n");
  }
  // Serial.println(str); // if this line is uncommented serial input "2_ON\n" and "2_OFF\n" is recognized and outled 2 is successfully switched

  // identity
  if (str == "IDN\n") {
    Serial.println("Serial Power Outlet");
  }

  // controlling power outlet 1
  else if (str == "1_ON\n") {
    digitalWrite(OUT_1_1, LOW);
    digitalWrite(OUT_1_2, LOW);
  }
  else if (str == "1_OFF\n") {
    digitalWrite(OUT_1_1, HIGH);
    digitalWrite(OUT_1_2, HIGH);
  }

  // controlling power outlet 2
  else if (str == "2_ON\n") {
    digitalWrite(OUT_2_1, LOW);
    digitalWrite(OUT_2_2, LOW);
  }
  else if (str == "2_OFF\n") {
    digitalWrite(OUT_2_1, HIGH);
    digitalWrite(OUT_2_2, HIGH);
  }
  delay(1000);
}

If I serial input 2_ON\n or 2_OFF\n the according else if blocks are just ignored (all other inputs work correctly).
But after I've uncommented // Serial.println(str); these blocks are executed the way they are supposed to and all works just fine.
Where is my mistake, what am I getting wrong here?
These blocks also get executed if I Serial.println any random output.
Why do I have to Serial.println something first so my script works according to plan? What am I missing?
EDIT: added all of the code.

Post the whole code. I bet you have a memory overrun somewhere.

Tank you for reading, I've just added all of the code. Even though that was just the setup() and 4 defines.

I've just found out that the character '2' literally is dropped, when I print out 'str' at the end of loop(). This only happens to '2', not any other character.
So I will go with 'A_ON/OFF' and 'B_ON/OFF' as control strings and continue with my project. Still, this is no clean solution and I'd still like to know why this behavior is observed.

Even though you read until \n, that just controls the ending of your buffered string.  It does not control it's start.  There may be some garbage before the command that you have not cut out.  In other words, I suggest you check if the string endsWith as opposed to == the command string.
As for what noise could be causing garbage or why activity on the tx side of the serial cleaned it up, i do not know.  Heck something might just be weird enough in the wiring that '2' is just the set of bits needed to aggravate it.

That's interesting, thanks for the input! I'll try tomorrow and check if endsWith() works.

Reality has no duty to conform to our theories, but often we do have jobs that require us to make our theories conform to reality.  I'd like to think there's more going on here than a ghost in the machine that hates 2 but likes B.


text:
Anyone have example code for ESP32 as media controller for Android/iPhone Media Apps
There's actually another post with this very same topic but no answers on that post. Back in January of 2020, the last commenter said he had sample code and then he went dark without posting the actually code. The thread is here:
Want to create bluetooth audio control (volume up/down, play, pause, etc.) for smartphone
My problem is the exactly the same as the original post. Amazon and Aliexpress have literally hundreds of these "media buttons" that you can buy and pair via bluetooth with your Android or iOS. You can then playback media on iOS/Android and the "media buttons" can control the playback. Pretty common controls are volume up/down, next, previous, play and pause.
I've written a lot of Arduino code for Nano, Uno and even MKR. I've written a bunch of ESP8266 and ESP32 code as well. Usually when I try and learn something, a few google searches will find an example that I can figure out. For this, I've been able to find nothing.
Every tutorial or sample code is about how to send commands to the ESP32 via Bluetooth or pair an ESP32 with a bluetooth joystick, etc. None of those examples help me understand what's needed for an ESP32 to pair with my Android and act as media buttons, sending volume up, down and play/pause commands via bluetooth.
Can anyone help with example code for doing this with an ESP32? (by the way, this forum would not let me comment on the original post or I would have. it said I didn't have enough karma points or something)

Have you googled for something like "ESP32 bluetooth HID"? I did and at the first glance the results seem really promising, for example this Arduino library for the ESP32. It also comes with an example on how to use it. If you have seen such results, how exactly are they not helping you?

Well after I posted this question, I kept googling. Literally hours of googling at this point. Then I stumbled across this example:
https://github.com/T-vK/ESP32-BLE-Keyboard
I wrote that sketch to my ESP32, paired my iPhone and it immediately starting controlling music playback on my phone. After looking at the code, it's so simple that I'm embarrassed I couldn't figure this out on my own. In case the link goes dead, I'll paste the code here:

#include

BleKeyboard bleKeyboard;

void setup() {
  Serial.begin(115200);
  Serial.println("Starting BLE work!");
  bleKeyboard.begin();
}

void loop() {
  if(bleKeyboard.isConnected()) {
    Serial.println("Sending 'Hello world'...");
    bleKeyboard.print("Hello world");

    delay(1000);

    Serial.println("Sending Enter key...");
    bleKeyboard.write(KEY_RETURN);

    delay(1000);

    Serial.println("Sending Play/Pause media key...");
    bleKeyboard.write(KEY_MEDIA_PLAY_PAUSE);

    delay(1000);

    Serial.println("Sending Ctrl+Alt+Delete...");
    bleKeyboard.press(KEY_LEFT_CTRL);
    bleKeyboard.press(KEY_LEFT_ALT);
    bleKeyboard.press(KEY_DELETE);
    delay(100);
    bleKeyboard.releaseAll();

  }
  Serial.println("Waiting 5 seconds...");
  delay(5000);
}

source: Stack Exchange

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

sort: votes


text:
Calling a localhost php script from arduino
Is it possible to connect arduino uno to call a php script using ONLY an arduino uno board, and an esp8266-01 wifi module.? That is, I lack wifi shield such as node MCU.
I just need the setup to call a php script on my localhost server.
I'm using arduino IDE 1.8.13.
Gracias

You may want to see my blog where I use an ESP-01 as a wifi-shield of an Arduino. You can either communicate with ESP-01 via AT Command or have both Arduino and ESP-01 running its own Arduino code with a pre-defined communication states management between the two.

This seems like just what I want. Let me run  thru the tutorial and see. Thank you

You can program the ESP-01 module using the arduino IDE. There are instructions in the README here: https://github.com/esp8266/Arduino
You can program the ESP-01 to connect to WiFi and communicate with your arduino sketch using the serial port. Don't forget the ESP-01 runs at 3.3V while the arduino runs at 5V. You'll need to shift the voltages somehow, otherwise you'll burn the arduino uno.
Here's an example of code you can run on the ESP-01 to connect to WiFi and start a TCP connection: https://github.com/esp8266/Arduino/blob/master/libraries/ESP8266WiFi/examples/WiFiClient/WiFiClient.ino
All that's missing is making an HTTP request instead of a "raw" TCP connection. You can probably find that in the examples. Then, add code for serial communication back to your arduino uno.
Good luck!

Much appreciated. I'm working on this. I'll get you feedback. Thanks again

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


text:
Jumping to bootloader from application code in atmega328p
I'm trying to program an Arduino Uno (atmega328p) using only the serial Tx/Rx lines (no DTR, so no automatic reset). This is so I can upload code via WiFi/TCP using an ESP-01.
To achieve this, I need to Arduino sketch/application to reset itself (and run the bootloader) whenever it sees avrdude trying to upload code (e.g. when 0 0  appears in the serial port).
I've tried a few approaches to jumping to the bootloader from application code but had no success so far.

Using the watchdog timer

void reset_to_bootloader() {
    // see 11.2.2 MCUCR – MCU Control Register
    // Enable change of interrupt vectors
    MCUCR = (1<<IVCE);
    // Move interrupts to Boot Flash section
    MCUCR = (1<<IVSEL);

    // enable watchdog timer
    wdt_enable(WDTO_30MS);

    // block waiting for the watchdog to timeout and jump to the bootloader
    while(1);
}

Unfortunately, the datasheet[1] mentions the IVSEL bit is not available in atmega328p, so even though this compiles, it simple resets the MCU and the bootloader does not run.

Jumping to the bootloader address directly

There is a table in the datasheet (Table 26-7. Boot Size Configuration, ATmega328P) that specifies the bootloader start address for the 4 supported bootloader section sizes, which are configured by the BOOTSZ fuse.
I have read the fuses and confirmed the bootloader section is 512-bytes (256 words) long.
Therefore, according to the datasheet, the Boot Loader Flash Section is 0x3F00 - 0x3FFF. So, the start of the bootloader should be at word-address 0x3F00.
I have even dumped the whole 32768-byte flash off the MCU and confirmed the bootloader is at byte-address 0x7e00, which matches the expected word-address 0x3F00 (0x7e00 / 2 = 0x3F00).
I have tried a couple methods of jumping to address 0x3F00. Here's a few. None of them seem to work. They just reset the MCU and the bootloader doesn't seem to run.
void jump_to_bootloader() {
    size_t bootloader_addr = 0x3F00;

    void (*bootloader_ptr)() = (void (*)())(bootloader_addr);

    SREG = 0;
    wdt_disable();
    bootloader_ptr();
}

void jump_to_bootloader2() {
    asm volatile ("ijmp" ::"z" (0x3F00));
}

Jumping and updating the value of MCUSR

I then realised the bootloader[4] checks the reset source and only runs on an external reset:
ch = MCUSR;
if (! (ch &  _BV(EXTRF))) // if its a not an external reset...
    pp_start();  // skip bootloader

So I tried faking it before jumping, but it didn't work either:
    MCUSR = _BV(EXTRF);
    asm volatile ("ijmp" ::"z" (0x3F00));
}

Any help is appreciated. Thanks in advance!

edit:

Jumping to after the bootloader checks the reset source

Following @Edgar Bonet's suggestion, avoiding the if (!(ch & _BV(EXTRF))) appStart(); check in the bootloader by jumping to the instruction that follows it:
void jump_to_bootloader2() {
    // the bootloader assumes these are true:
    cli();
    SP = RAMEND;
    SREG = 0;
    MCUSR = 0;
    asm volatile ("eor  __zero_reg__, __zero_reg__");
    asm volatile ("eor  r1, r1");
    // jump to after the bootloader checks the reset source
    asm volatile ("ijmp" ::"z" (0x7e0au / 2));
    while(1);
}

I could see it entered the bootloader (LEDs flashed a couple times), but avrdude was not able to upload code.
The bootloader sets up a watchdog timer (WDT), so I'm suspecting avrdude waits for to long after sending the initial 0 0 0  and since the bootloader does not see anything on the serial port the WDT resets it.

References:

[1] AVR Instruction Set Manual: http://ww1.microchip.com/downloads/en/devicedoc/atmel-0856-avr-instruction-set-manual.pdf
[2] atmega328p datasheet: http://ww1.microchip.com/downloads/en/DeviceDoc/Atmel-7810-Automotive-Microcontrollers-ATmega328P_Datasheet.pdf
[3] random forum thread I have also read: https://www.avrfreaks.net/forum/jump-bootloader-app-help-needed
[4] bootloader code: https://github.com/sparkfun/Arduino_Boards/blob/805def002e815509032fde37a674d2916af8aecc/sparkfun/avr/bootloaders/atmega/ATmegaBOOT_168.c#L299-L307

I don't see any way of doing this if the UNO is running optiboot. The only options I see is to slightly change, compile, and flash a new bootloader on the UNO. Or connect one of the Arduino pins, or one of the ESP pins to the UNOs reset pin.

The source of Optiboot on Uno is here.
I would prefer a simple watchdog reset with
  wdt_enable(WDTO_15MS);
  while (true);

But I am not sure now if it runs sketch upload detection in bootloader.
For direct jump to Optiboot on Uno (one flash page) this should work
typedef void (*bootloader_jump_t)();
const bootloader_jump_t bootloader_jump = (bootloader_jump_t)((FLASHEND-511)>>1);

and then you can call bootloader_jump();
EDIT:
while the Optiboot 4 on Uno from factory doesn't check for new upload after watchdog reset or direct jump, Optiboot 8 has checks to handle this right

It appear the new UNOs use the optiboot bootloader. Optiboot check if the reset button is pressed (or reset it pulled low via the DTR signal), and if not, will runs your sketch immediately (removing the 3 second delay). So I don't think these pieces of code will work.

@Gerben, Uno always used Optiboot. version 4 as bundled with the core package

Thank you for the reply.
((FLASHEND-512)>>1) gives 16127, which is 0x3EFF. The bootloader starts in the next flash word (0x3F00), so I don't think jumping to 0x3EFF will work. And, as I said, I already tried jumping to 0x3F00. :/

@Nuno, sorry. jumping to 0x3F00 with Optiboot 8 will work. https://github.com/Optiboot/optiboot/blob/6f98751c6d184ec4a9c7f1fe0f0dcf12f9db2cc9/optiboot/bootloaders/optiboot/optiboot.c#L628

@Juraj I see, if I change the bootloader to Optiboot 8 it may work. Thanks! I'll give it a try when I have some free time. I'm not sure if the bootloade can replace itself, so it'll take a little more effort as the arduino pins for SPI flashing are currently inaccessible.

@Juraj I changed the bootloader to Optiboot 8 with a timeout of 4s (2s didn't work) and then used the WDT to reset to bootloader and it works ;) Many thanks!

Maybe you could jump to right after the line
if (!(ch & _BV(EXTRF))) appStart();

Here is an excerpt of the disassembly:
  if (!(ch & _BV(EXTRF))) appStart();
    7e06:   81 ff           sbrs    r24, 1
    7e08:   f0 d0           rcall   .+480       ; 0x7fea <appStart>

#if LED_START_FLASHES > 0
  // Set up Timer 1 for timeout counter
  TCCR1B = _BV(CS12) | _BV(CS10); // div 1024
    7e0a:   85 e0           ldi r24, 0x05   ; 5
    7e0c:   80 93 81 00     sts 0x0081, r24

The conditional call to appStart() is made by the instructions sbrs
and rcall. The instruction right after that is the ldi at byte
address 0x7e0c (word address 0x3f05). I would try jumping right there.
You won't miss much:

eor r1, r1 is not needed when jumping from C++, as the value of r1
is already enforced by the compiler as per the ABI.
in r24, 0x34 reads MCUSR into a register that is clobbered right
away
out 0x34, r1 clears MCUSR; if this turns out to be useful, you
could do it right before jumping to the bootloader.

You may want to check that the bootloader you have matches the
disassembly I linked to.

Thanks! Indeed, my dumped flash matches at least the 4 lines of the excerpt you quoted. I tried jumping to 0x7e0au / 2, which is right after the check for the EXTRF bit. I tried this and I could see the bootloader blinking the LEDs but avrdude was not able to sync. :/
I've updated the original question with this (see 4. Jumping to after the bootloader checks the reset source).


text:
Issues with Arduino UNO printing repeated "double" on serial monitor
A weird is happening which i can't figure out why. First I had issue communicating with SIM800L.
So i tried checking the USART Hardware to see what UNO sends to SIM800 using small piece attached below.
The sketch is to compares what i send from serial monitor with strings "Hello", "heLLo" and "Hello" expecting to get Found .... or No match found.
each line string i send, the serial monitor prints twice WHY?,
The first says not found and the second say Received == ........ WHY?
**See the output of serial terminal
when i typed "Hello" with quotes.
12:03:46.536 -> Buffer Received= "  No match found
12:03:46.569 ->
12:03:46.569 -> Buffer Received= Hello"
12:03:46.603 ->     Found Hello
when i typed "HELLO" with quotes.
12:03:55.855 -> Buffer Received= "  No match found
12:03:55.888 ->
12:03:55.888 -> Buffer Received= HELLO"
12:03:55.921 ->     Found HELLO**

****when i typed "heLLo" with quotes.
12:04:04.016 -> Buffer Received= "  No match found
12:04:04.049 ->
12:04:04.049 -> Buffer Received= heLLo"
12:04:04.082 ->     Found heLLo
12:04:04.115 ->****

When i typed without quotes, all i get No match found
char buffer[100];
uint8_t index=0;

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

void loop()
{
  if(Serial.available()>0)
  {
    index=0;
    while(Serial.available())
    {
      buffer[index++]=Serial.read();
    }

    buffer[index]='\0';
    Serial.println(' ');
    Serial.print("Buffer Received");
    Serial.print(buffer);
    Serial.print('\t');
    if(strstr(buffer, "Hello")!=NULL) Serial.println("Found Hello");
    else if(strstr(buffer, "HELLO")!=NULL) Serial.println("Found HELLO");
    else if(strstr(buffer, "heLLo")!=NULL) Serial.println("Found heLLo");
    else Serial.println("No match found");
    Serial.flush();
  }
}

Note: Suspecting my PC hardware and serial driver,
so I tried it in my Ubuntu 20.04 and window 10 installed with Arduino IDE 1.8.13
suspecting it may be crystal, i tried two different boards and used even Atmega328P core.
I also suspected my keyboard "ENTER" key, so i tried the serial monitor "send" button.
with no difference.
I seems to run short is ideas so i am posting to the community. Let me have your advice and experience too.
Thanks.

You have a fundamental misunderstanding of how serial communication works. You can't just read "while available" because that will not be true. You need to "read if available and up until the terminating character".

9600 Bd means 1ms per character. If there's no terminating character to rely on, simply waiting a few ms via delay(10); after the first Serial.available()> 0 is an ugly but doable alternative in this case.

Hello DataFiddler, You great, your suggestion works. it was just a case of delay which ignored. I actually added delay(10) in-between character reads. and no more print duplication. BUT WHY is that necessary? in eclipse i don't think i have that experience. IT WORTH NOTING WHEN USING ARDUINO IDE!

Doesn’t matter what IDE you use to write the code the code is the same.  The problem is that the serial data doesn’t come all at once.  You get one character and read it and then before the next character arrives available is again 0 and you go off to compare your one character you read.  While you’re doing that the rest of the string arrives.  When you get back around you’ve now got the whole string.  With the delay you’re giving the string time to complete arrive one letter at a time on the port.

It’s not necessary to have the delay if you write proper code to handle serial data.  Have it look for an end marker before it does the comparison.  Or have it wait until available returns the full length of the string before you start reading it.

Dear Delta_G OK, i am noting all suggestions. Cheers!

@Delta_G: "Doesn’t matter what IDE you use to write the code" - But it may matter if you use its in-built terminal emulator.

As Majenko and DataFiddler already stated in the comments, you are reading the Serial interface in the wrong way, because you seem to misunderstand a specific point involving the interface.
The Serial (UART) interface knows only of individual bytes, which are send asynchronously over the lines. It does not have any context of a full packet or message. When you type in some data into the Serial Monitor and then press "Send", the data will be send, but not as one big bunch of data. The individual bytes are delayed.
The first delay comes with the nature of the interface itself, as you send with a limited baudrate. With a baudrate of 9600 the Arduino is way faster, than the bytes can arrive. So when you first get a result higher than zero from Serial.available(), the rest of the message is not yet received. Thus with your current code you would only process only the first part of the message.
The second delay comes with the fact, that you and the Serial program on your PC cannot control, when exactly each byte is send. Thats done by the driver. So it might happen, that there is a small gap between 2 bytes somewhere in your message. You cannot mitigate this without writing your own driver and you cannot predict this.
So, what to do now? You should read data, when it is available, and put it into a buffer. And only, when a full message was received, you should process the data. Now you need to know, where the end of a message is. Mostly a delimiting character (like the newline character \n) at the end of the message is used. So you read, if available, and only process the message, when you have read the delimiting character. Something like this:
unsigned int buffer_pos = 0;
char buffer[50]="";

void loop(){
    if(Serial.available()){
        char c = Serial.read();
        if(c == '\n'){
            buffer[buffer_pos] = '\0'; // End the message as C string with a null character
            // process the message here
            buffer_pos = 0;
        } else {
            buffer[buffer_pos] = c;
            buffer_pos++;
        }
    }
}

buffer holds the message. buffer_pos is the current position in the buffer. We terminate the message with the null character, to get a valid C string in the buffer. After processing the message, we set the position back to zero, to receive the next message. When you send data from your PC, you need to make sure, that the message is ended with the newline character.
Now you are independent on when exactly the data is send.

DataFiddler stated in the comments, that without a delimiting character you can simply delay for enough time, so that the data has enough time to arrive. He also stated, that it is ugly. It is a bad coding style. A long delay will impact the responsiveness of your program, while a short delay may give you problems with longer messages. So I suggest, that you directly use the correct way to read the Serial interface. Then you don't have such pitfalls.

Dear chris! you guys are great! THANKS ALOTS. got it resolved first from DataFiddler suggest and next Majenko suggestion. Your explanations is explicit. I enjoy all your contribution. JUST that i was abit careless in handling that. Funny as it will sound. I battle with this for about 22hrs. Just as i stated earlier, i will be more caution next to avoid this kind avoidable stress.

@Avong, please upvote good answers and mark as correct the answer which is best, as this is the best way to thank people for taking the time to write good answers. The upvote button is the little up arrow at the top left of the answer.


text:
String array length in function
I know this question has been asked a thousand times, but I can't find a solution for my case.
I what to get the length of a string array in a given function. This is for an arduino board.
#define LEN(x) sizeof(x)/sizeof(x[0])
const char* mainMenu[] = {"FirstWord", "SecondWord", " "};

void myFunction(const char** m) {
  int a = LEN(m);

  /* Do something */
};

void setup(){
   myFunction(mainMenu);
};

The LEN(m) works fine in the setup() function. But in myFunction() it either gives me 1 (i guess the length of the pointer) or 9 (length of the 0th element of the array)

The problem is that LEN is evaluated locally for each usage replacing it with the content. In myFunction the parameter being passed to it is a pointer, not the array.
You need to evaluate the size once and once only in the context where the array hasn't collapsed into a pointer. That is usually done immediately where the array is defined:
const char* mainMenu[] = {"FirstWord", "SecondWord", " "};
#define MAINMENU_LEN (sizeof(mainMenu) / sizeof(mainMenu[0]))

Because mainMenu is a global it's always available, and when you require the length you get the length of the global array.
If you want to keep things local you will have to pass the number of elements in the array as a parameter to the function that uses that information.
myFunction(mainMenu, MAINMENU_LEN);

Another common alternative is to have some "end of array" marker and you loop through your array until you find that marker (that's how strings work - with \0 for the end of array marker):
const char* mainMenu[] = {"FirstWord", "SecondWord", " ", 0};

Then:
for (int i = 0; m[i] != 0; i++) {
    ...
}

hum, ok interesting. But how would I calculate the length of any given array passed to myFunction? In the example I only had mainMenu, but if I have multiple menus, I want to get its length programmitically

You can't. You have to calculate it somewhere where the array is still an array (the point where it's defined) and pass that value as a parameter.

really? so there is no function similar to go or python with len(x) or length(x) ?

No. There is no function like that. Simply because that is not how C works.

@will.mendil I have added some commonly used methods to my answer for you.

Just saw that, the for loop should work. I'm really used to python and fell in love with go a few months ao. But for what I'm doing, tinygo won't work since it's missing some functions. I'm struggling with C as the way it works it very different. Anyway, thanks for the help


text:
error at compiling : 'class TwoWire' has no member named 'setClock'
I am a newbie C programmer and I just started with Arduino web editor (Win10-Firefox)to code for a Raspberry Pi (3B) board. RPi is on line via ethernet connection.
I tried to compile an example from Garmin Lidar_lite v3HP for I2C, as available in the library collections for Arduino.
When compiling the example I get after a while this error message:
Using library Wire in folder: /home/builder/.arduino15/packages/arduino/hardware/mraa/1.0.8/libraries/Wire (legacy)
Using library lidar_lite_3_0_3 at version 3.0.3 in folder: /home/builder/opt/libraries/latest/lidar_lite_3_0_3
/tmp/967842743/v3HP_I2C/v3HP_I2C.ino: In function 'void setup()':
/tmp/967842743/v3HP_I2C/v3HP_I2C.ino:51:18: error: 'class TwoWire' has no member named 'setClock'
Wire.setClock(400000UL); // Set I2C frequency to 400kHz (for Arduino Due)
^
exit status 1
Checking the arduino forum I find some similar question, but of many years ago and likely not applicable any longer.
I appreciate your expert inputs on how to resolve in simple terms.
Thanks a lot! Greetz, Ivan

You're trying to compile code to run on a Pi? What core did you install into the IDE to do that?

Yes, that is the intent. Arduino web editor offers possibility to select not only arduino boards, but also linux based ARM systems such as RPi  board and also other SBC are supported by the web editor. I have seen Youtube tutorial that was demonstrating web editor en RPi.- see https://www.youtube.com/watch?v=yVS9zIcWa7w . That triggerd my interest.

Then probably the library in that (unknown?) core doesn't support that functionality. Maybe that functionality doesn't make any sense on a Linux computer where I guess the clock speed may be set in the DT overlay.

Thanks for the reply. I tried again with the arduino on PC with RasPiDuino librarie and had no further problem. The resulting executable does work on a RPi3 wirh Buster OS. Apparently the arduino webeditor lacks some libraries to succesfully compile for raspberry  . I continue this road. Item can be closed.

You should write that as an answer then wait the prescribe period (if there is one) and accept your own answer. That way people looking for an answer to the same problem can easily find it.

Thanks for the reply. I tried again with the arduino on PC with RasPiDuino librarie and had no further problem. The resulting executable does work on a RPi3 with Buster OS. Apparently the arduino webeditor lacks some libraries to succesfully compile for raspberry . I continue this road. Item can be closed.

If you now wish to delete your question, just use the 'delete' button on the question.


text:
TCP client readStringUntil only when data exists
I have the attached script that reads data from a socket server (it is PHP at the server end).
My problem (I think) is that the readStringUntil() needs a test above it, so that it "reads up to \r" only if there is any data being received, otherwise it seems to keep trying to read forever, because when I DO send data, it is received with 1-2 seconds delay.
If I constantly send (properly \r delimited) data without any pause, then it seems to be received instantly (10-20ms or so).
I tried: if (client.available()) { String received_message = client.readStringUntil('\r'); } but it doesn't seem to be the right function, doesn't do anything.
This is ESP32 board, compiler mentioned it found two wifi libraries, one in arduino folder and one in ESP32, it used the second one. This might be relevant to what functions are available.
#include <WiFi.h>

const char* ssid = "MyWiFi";
const char* password =  "1234";

const uint16_t port = 8080;
const char * host = "myserver.example.com";

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

  WiFi.begin(ssid, password);
  while (WiFi.status() != WL_CONNECTED) {
    delay(500);
    Serial.println("...");
  }

  Serial.print("wifi connected with IP: ");
  Serial.println(WiFi.localIP());
}

void loop() {

  WiFiClient client;

  if (!client.connect(host, port)) {
    Serial.println("connection to host failed");
    delay(500);
    return;
  }

  Serial.println("connected to server");

  // I assume this is where I need a test like "if any received data exists" >>>

  String received_message = client.readStringUntil('\r');
  Serial.println(received_message);

  // intentional delay doesn't seem to do much
  // when it constantly tries to read for data that is not always there
  delay(100);

  // do I need to disconnect here ?!
  // client.stop();
}

EDIT: my PHP loop looks like this:
do{
    $accept = socket_accept($socket) or die("Could not accept incomming connection");

    // $message_to_send = 'hi there '.microtime(true)."\r";
    // OR
    // get message from memcached variables

    if($message_to_send!=''){

        echo "\nsending: ".$message_to_send;

        socket_send($accept, $message_to_send, strlen($message_to_send), MSG_OOB);
    }

} while (true);

esp WiFi libraries close the connection when the last WiFiClient object which referenced it is destroyed. so here at the end of the loop().

does the server send data immediately after you connect to it? you send no request

You mean that is when it closes it automatically or when I need to call the close ? Thanks.

Server sends data immediately if I tell it to, it is inside an infinite loop where I make it check for new data and send it if found. The delay appears when it looped with no data to send and then it started sending something.

If the loop constantly sends properly delimited data on each cycle (e.g 'hi there '.microtime(true)."\r"), then there is no delay.

your client connects and disconnects in every loop(). make WiFiClient global, connect it back only when it disconnects. and then will if (client.available()) work

You mean the client.connect in top of the loop causes the delay ? I don't think is that because if I comment-out the client.readStringUntil() then it loops much faster.

Do I move WiFiClient right above the loop(){} to make it global ? And I don't know how to connect it back when it disconnects :/

client.readStringUntil() waits a second for the data. if the server sends the data immediately after the connection from client is established, then the  readStringUntil would catch it. if it sends the data later, the connection is already closed. if (!connected) connect

I don't know how to use the connected code you mentioned.

then you need project guidance and not an answer on a Q&A site. https://forum.arduino.cc/

I posted a topic exactly there under project guidance yesterday, nobody replied :/

I don't see it there.


text:
Multiple sensors I2C stop working suddenly
I am using multiple temperature sensors using I2C. Some of the sensors are connected via TCA9548 multiplexer. When I run the sketch it runs fine for a few minutes but then it suddenly stops working while printing the results. I have tried changing the baud rate, trying two different arduinos but it happens on both arduinos. So I wonder if it's some kind of buffer overflow (serial prints) or there is any collision happening on the I2C bus. Now the only other way I can think of is to run each sensor separately and see if I can find the problematic sensor. Or are there better ways to fix the issue?
/* 9 temperature & Humidity Sensors
    1 x BME280 #1 (0x77)[Ch 0]
    1 x BME280 #2 (0x77) [Ch 1]
    1 x BME280 #3 (0x76)
    1 x SHT21 (0x40) [Ch 7]
    1 x Si7021 (0x40) [Ch 5]
    1 x HTU21D (0x40) [Ch 6]
    1 x HDC1080 (0x40) [Ch 4]
    1 x AHT10 (0x38)
    1 x HDC2080 (0x41)

*/

#include <Wire.h>
#include <Adafruit_Sensor.h>
#include <Adafruit_BME280.h>
#include <Sodaq_SHT2x.h>
#include "SparkFunHTU21D.h"
#include <HDC2080.h>
#include "ClosedCube_HDC1080.h"
#include <AHT10.h>
#include "Adafruit_Si7021.h"

Adafruit_BME280 bme1; // I2C
Adafruit_BME280 bme2; // I2C
Adafruit_BME280 bme3; // I2C
HTU21D HTU;
HDC2080 HDC2080(0x41);
ClosedCube_HDC1080 hdc1080;
AHT10 AHT(AHT10_ADDRESS_0X38);

Adafruit_Si7021 Si7021 = Adafruit_Si7021();
bool enableHeater = false;
uint8_t loopCnt = 0;

unsigned long delayTime;

#define MPLXADR 0x70 // Address of TCA9548A I2C Multiplexer
void multiplexer (uint8_t ch) { //ch is the channel on Multiplexer
  if (ch > 7) return;

  Wire.beginTransmission(MPLXADR);
  Wire.write(1 << ch);
  Wire.endTransmission();
}

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

  while (AHT.begin() != true)
  {
    Serial.println(F("AHT10 not connected or fail to load calibration coefficient")); //(F()) save string to flash & keeps dynamic memory free
    delay(5000);
  }
  Serial.println(F("AHT10 OK"));

  HDC2080.begin();

  // Begin with a device reset
  HDC2080.reset();

  // Set up the comfort zone
  HDC2080.setHighTemp(28);         // High temperature of 28C
  HDC2080.setLowTemp(22);          // Low temperature of 22C
  HDC2080.setHighHumidity(55);     // High humidity of 55%
  HDC2080.setLowHumidity(40);      // Low humidity of 40%

  // Configure Measurements
  HDC2080.setMeasurementMode(TEMP_AND_HUMID);  // Set measurements to temperature and humidity
  HDC2080.setRate(ONE_HZ);                     // Set measurement frequency to 1 Hz
  HDC2080.setTempRes(FOURTEEN_BIT);
  HDC2080.setHumidRes(FOURTEEN_BIT);

  //begin measuring
  HDC2080.triggerMeasurement();

  Serial.println();

  Serial.println(F("BME280 test"));

  //BME280 sensor 1
  //  multiplexer(0);
  //  if (! bme1.begin(0x77, &Wire)) {
  //    Serial.println("Could not find a valid BME280 sensor, check wiring!");
  //    while (1);
  //  }

  // weather monitoring
  //  Serial.println("-- Weather Station Scenario --");
  //  Serial.println("forced mode, 1x temperature / 1x humidity / 1x pressure oversampling,");
  //  Serial.println("filter off");
  //  bme1.setSampling(Adafruit_BME280::MODE_FORCED,
  //                   Adafruit_BME280::SAMPLING_X1, // temperature
  //                   Adafruit_BME280::SAMPLING_X1, // pressure
  //                   Adafruit_BME280::SAMPLING_X1, // humidity
  //                   Adafruit_BME280::FILTER_OFF   );

  //BME280 sensor 2
  multiplexer(1);
  if (! bme2.begin(0x77, &Wire)) {
    Serial.println("Could not find a valid BME280 sensor, check wiring!");
    //while (1);
  }

  // weather monitoring
//  Serial.println("-- Weather Station Scenario --");
//  Serial.println("forced mode, 1x temperature / 1x humidity / 1x pressure oversampling,");
//  Serial.println("filter off");
  bme2.setSampling(Adafruit_BME280::MODE_FORCED,
                   Adafruit_BME280::SAMPLING_X1, // temperature
                   Adafruit_BME280::SAMPLING_X1, // pressure
                   Adafruit_BME280::SAMPLING_X1, // humidity
                   Adafruit_BME280::FILTER_OFF   );

  //BME280 sensor 3
//  if (! bme3.begin(0x76, &Wire)) {
//    Serial.println("Could not find a valid BME280 sensor, check wiring!");
//    //while (1);
//  }

  // weather monitoring
//  Serial.println("-- Weather Station Scenario --");
//  Serial.println("forced mode, 1x temperature / 1x humidity / 1x pressure oversampling,");
//  Serial.println("filter off");
//  bme3.setSampling(Adafruit_BME280::MODE_FORCED,
//                   Adafruit_BME280::SAMPLING_X1, // temperature
//                   Adafruit_BME280::SAMPLING_X1, // pressure
//                   Adafruit_BME280::SAMPLING_X1, // humidity
//                   Adafruit_BME280::FILTER_OFF   );
//
//  // suggested rate is 1/60Hz (1m)
//  delayTime = 10000; // in milliseconds

  Serial.println("Initiating HTU21D");
  multiplexer(6);
  HTU.begin();

  Serial.println("HDC1080 Arduino Test");

  // Default settings:
  //  - Heater off
  //  - 14 bit Temperature and Humidity Measurement Resolutions
  multiplexer(4);
  hdc1080.begin(0x40);

  Serial.println("Si7021 test!");

  multiplexer(5);
  if (!Si7021.begin()) {
    Serial.println("Did not find Si7021 sensor!");
    //while (true);
  }

}

void loop() {

  unsigned long newTime = millis();
  static unsigned long oldTime = 0;

  if (newTime - oldTime >= 60000) {
    oldTime = newTime;

    printValuesHDC2080();

    multiplexer(4);
    printValuesHDC1080();

//    bme3.takeForcedMeasurement(); // has no effect in normal mode
//    printValuesBME3();

    multiplexer(1);
    bme2.takeForcedMeasurement(); // has no effect in normal mode
    printValuesBME2();

    multiplexer(6);
    printValuesHTU();

    multiplexer(5);
    printValueSi7021();

    printValuesAHT();

    //  multiplexer(0);
    //  bme1.takeForcedMeasurement(); // has no effect in normal mode
    //  printValuesBME1();

    multiplexer(7);
    printValuesSHT21();

    Serial.println();
    Serial.println();
  }
}

//void printValuesBME1() {
//
//  Serial.println();
//  Serial.print("BME1 Readings");
//  Serial.write(9); // printing a tab using ASCII code
//  Serial.print("Temperature = ");
//  Serial.print(bme1.readTemperature());
//  Serial.println(" *C");
//  Serial.write(9); // printing a tab using ASCII code
//  Serial.print("Humidity = ");
//  Serial.print(bme1.readHumidity());
//  Serial.println(" %");
//}

void printValuesBME2() {

  Serial.print("BME2: ");
  Serial.write(9); // printing a tab using ASCII code
  Serial.print("T = ");
  Serial.print(bme2.readTemperature());
  Serial.write(9); // printing a tab using ASCII code
  Serial.print("H = ");
  Serial.println(bme2.readHumidity());
}

void printValuesBME3() {

  Serial.print("BME3: ");
  Serial.write(9); // printing a tab using ASCII code
  Serial.print("T = ");
  Serial.print(bme3.readTemperature());
  Serial.write(9); // printing a tab using ASCII code
  Serial.print("H = ");
  Serial.println(bme3.readHumidity());
}

void printValuesSHT21() {
  Serial.print("SHT21: ");
  Serial.write(9); // printing a tab using ASCII code
  Serial.print("T = ");
  Serial.print(SHT2x.GetTemperature());
  Serial.write(9); // printing a tab using ASCII code
  Serial.print("H = ");
  Serial.println(SHT2x.GetHumidity());
}

void printValuesHTU() {
  Serial.print("HTU: ");
  Serial.write(9); // printing a tab using ASCII code
  float humd = HTU.readHumidity();
  float temp = HTU.readTemperature();

  Serial.print("T = ");
  Serial.print(temp, 2);
  Serial.write(9); // printing a tab using ASCII code
  Serial.print("H = ");
  Serial.println(humd, 2);
}

void printValuesHDC2080() {
  Serial.print("HDC2080:");
  //Serial.write(9); // printing a tab using ASCII code
  Serial.print("T = "); Serial.print(HDC2080.readTemp());
  Serial.write(9); // printing a tab using ASCII code
  Serial.print("H = "); Serial.println(HDC2080.readHumidity());
}

void printValuesHDC1080() {
  Serial.print("HDC1080:");
  // Serial.write(9); // printing a tab using ASCII code
  Serial.print("T = ");
  Serial.print(hdc1080.readTemperature());
  Serial.write(9); // printing a tab using ASCII code
  Serial.print("H = ");
  Serial.println(hdc1080.readHumidity());
}

void printValuesAHT() {
  /* DEMO - 1, every temperature or humidity call will read 6 bytes over I2C, total 12 bytes */
  Serial.print(F("AHT10: "));
  Serial.write(9); // printing a tab using ASCII code
  Serial.print(F("T = ")); Serial.print(AHT.readTemperature()); //by default "AHT10_FORCE_READ_DATA"
  Serial.write(9); // printing a tab using ASCII code
  Serial.print(F("H = ")); Serial.println(AHT.readHumidity());    //by default "AHT10_FORCE_READ_DATA"
}

void printValueSi7021() {
  Serial.print(F("Si7021: "));
  // Serial.write(9); // printing a tab using ASCII code
  Serial.print("T = ");
  Serial.print(Si7021.readTemperature(), 2);
  Serial.write(9); // printing a tab using ASCII code
  Serial.print("H = ");
  Serial.println(Si7021.readHumidity(), 2);

  //
  //  // Toggle heater enabled state every 30 seconds
  //  // An ~1.8 degC temperature increase can be noted when heater is enabled
  //  if (++loopCnt == 30) {
  //    enableHeater = !enableHeater;
  //    Si7021.heater(enableHeater);
  //    // Serial.print("Heater Enabled State: ");
  //    if (Si7021.isHeaterEnabled()) {
  //      //  Serial.println("ENABLED");
  //    } else {
  //      // Serial.println("DISABLED");
  //
  //      loopCnt = 0;
}

Code with delay:
/* 9 temperature & Humidity Sensors
    1 x BME280 #1 (0x77)[Ch 0]
    1 x BME280 #2 (0x77) [Ch 1]
    1 x BME280 #3 (0x76)
    1 x SHT21 (0x40) [Ch 7]
    1 x Si7021 (0x40) [Ch 5]
    1 x HTU21D (0x40) [Ch 6]
    1 x HDC1080 (0x40) [Ch 4]
    1 x AHT10 (0x38)
    1 x HDC2080 (0x41)

*/

#include <Wire.h>
#include <Adafruit_Sensor.h>
#include <Adafruit_BME280.h>
#include <Sodaq_SHT2x.h>
#include "SparkFunHTU21D.h"
#include <HDC2080.h>
#include "ClosedCube_HDC1080.h"
#include <AHT10.h>
#include "Adafruit_Si7021.h"

Adafruit_BME280 bme1; // I2C
Adafruit_BME280 bme2; // I2C
Adafruit_BME280 bme3; // I2C
HTU21D HTU;
HDC2080 HDC2080(0x41);
ClosedCube_HDC1080 hdc1080;
AHT10 AHT(AHT10_ADDRESS_0X38);

Adafruit_Si7021 Si7021 = Adafruit_Si7021();
bool enableHeater = false;
uint8_t loopCnt = 0;

unsigned long delayTime;

#define MPLXADR 0x70 // Address of TCA9548A I2C Multiplexer
void multiplexer (uint8_t ch) { //ch is the channel on Multiplexer
  if (ch > 7) return;

  Wire.beginTransmission(MPLXADR);
  Wire.write(1 << ch);
  Wire.endTransmission();
}

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

  while (AHT.begin() != true)
  {
    Serial.println(F("AHT10 not connected or fail to load calibration coefficient")); //(F()) save string to flash & keeps dynamic memory free
    delay(5000);
  }
  Serial.println(F("AHT10 OK"));

  HDC2080.begin();

  // Begin with a device reset
  HDC2080.reset();

  // Set up the comfort zone
  HDC2080.setHighTemp(28);         // High temperature of 28C
  HDC2080.setLowTemp(22);          // Low temperature of 22C
  HDC2080.setHighHumidity(55);     // High humidity of 55%
  HDC2080.setLowHumidity(40);      // Low humidity of 40%

  // Configure Measurements
  HDC2080.setMeasurementMode(TEMP_AND_HUMID);  // Set measurements to temperature and humidity
  HDC2080.setRate(ONE_HZ);                     // Set measurement frequency to 1 Hz
  HDC2080.setTempRes(FOURTEEN_BIT);
  HDC2080.setHumidRes(FOURTEEN_BIT);

  //begin measuring
  HDC2080.triggerMeasurement();

  Serial.println();

  Serial.println(F("BME280 test"));

  //BME280 sensor 1
  //  multiplexer(0);
  //  if (! bme1.begin(0x77, &Wire)) {
  //    Serial.println("Could not find a valid BME280 sensor, check wiring!");
  //    while (1);
  //  }

  // weather monitoring
  //  Serial.println("-- Weather Station Scenario --");
  //  Serial.println("forced mode, 1x temperature / 1x humidity / 1x pressure oversampling,");
  //  Serial.println("filter off");
  //  bme1.setSampling(Adafruit_BME280::MODE_FORCED,
  //                   Adafruit_BME280::SAMPLING_X1, // temperature
  //                   Adafruit_BME280::SAMPLING_X1, // pressure
  //                   Adafruit_BME280::SAMPLING_X1, // humidity
  //                   Adafruit_BME280::FILTER_OFF   );

  //BME280 sensor 2
  multiplexer(1);
  if (! bme2.begin(0x77, &Wire)) {
    Serial.println("Could not find a valid BME280 sensor, check wiring!");
    //while (1);
  }

  // weather monitoring
  //  Serial.println("-- Weather Station Scenario --");
  //  Serial.println("forced mode, 1x temperature / 1x humidity / 1x pressure oversampling,");
  //  Serial.println("filter off");
  bme2.setSampling(Adafruit_BME280::MODE_FORCED,
                   Adafruit_BME280::SAMPLING_X1, // temperature
                   Adafruit_BME280::SAMPLING_X1, // pressure
                   Adafruit_BME280::SAMPLING_X1, // humidity
                   Adafruit_BME280::FILTER_OFF   );

  //BME280 sensor 3
  //  if (! bme3.begin(0x76, &Wire)) {
  //    Serial.println("Could not find a valid BME280 sensor, check wiring!");
  //    //while (1);
  //  }

  // weather monitoring
  //  Serial.println("-- Weather Station Scenario --");
  //  Serial.println("forced mode, 1x temperature / 1x humidity / 1x pressure oversampling,");
  //  Serial.println("filter off");
  //  bme3.setSampling(Adafruit_BME280::MODE_FORCED,
  //                   Adafruit_BME280::SAMPLING_X1, // temperature
  //                   Adafruit_BME280::SAMPLING_X1, // pressure
  //                   Adafruit_BME280::SAMPLING_X1, // humidity
  //                   Adafruit_BME280::FILTER_OFF   );
  //
  //  // suggested rate is 1/60Hz (1m)
  //  delayTime = 10000; // in milliseconds

  Serial.println("Initiating HTU21D");
  multiplexer(6);
  HTU.begin();

  Serial.println("HDC1080 Arduino Test");

  // Default settings:
  //  - Heater off
  //  - 14 bit Temperature and Humidity Measurement Resolutions
  multiplexer(4);
  hdc1080.begin(0x40);

  Serial.println("Si7021 test!");

  multiplexer(5);
  if (!Si7021.begin()) {
    Serial.println("Did not find Si7021 sensor!");
    //while (true);
  }

}

void loop() {

  unsigned long newTime = millis();
  static unsigned long oldTime = 0;

  if (newTime - oldTime >= 60000) {
    oldTime = newTime;

    printValuesHDC2080();
    delay(50);

    multiplexer(4);
    printValuesHDC1080();
    delay(50);

    //    bme3.takeForcedMeasurement(); // has no effect in normal mode
    //    printValuesBME3();

    multiplexer(1);
    bme2.takeForcedMeasurement(); // has no effect in normal mode
    printValuesBME2();
    delay(50);

    multiplexer(6);
    printValuesHTU();
    delay(50);

    multiplexer(5);
    printValueSi7021();
    delay(50);

    printValuesAHT();
    delay(50);

    //  multiplexer(0);
    //  bme1.takeForcedMeasurement(); // has no effect in normal mode
    //  printValuesBME1();

    multiplexer(7);
    printValuesSHT21();
    delay(50);

    Serial.println();
    Serial.println();
  }
}

//void printValuesBME1() {
//
//  Serial.println();
//  Serial.print("BME1 Readings");
//  Serial.write(9); // printing a tab using ASCII code
//  Serial.print("Temperature = ");
//  Serial.print(bme1.readTemperature());
//  Serial.println(" *C");
//  Serial.write(9); // printing a tab using ASCII code
//  Serial.print("Humidity = ");
//  Serial.print(bme1.readHumidity());
//  Serial.println(" %");
//}

void printValuesBME2() {

  Serial.print("BME2: ");
  Serial.write(9); // printing a tab using ASCII code
  Serial.print("T = ");
  Serial.print(bme2.readTemperature());
  Serial.write(9); // printing a tab using ASCII code
  Serial.print("H = ");
  Serial.println(bme2.readHumidity());
}

void printValuesBME3() {

  Serial.print("BME3: ");
  Serial.write(9); // printing a tab using ASCII code
  Serial.print("T = ");
  Serial.print(bme3.readTemperature());
  Serial.write(9); // printing a tab using ASCII code
  Serial.print("H = ");
  Serial.println(bme3.readHumidity());
}

void printValuesSHT21() {
  Serial.print("SHT21: ");
  Serial.write(9); // printing a tab using ASCII code
  Serial.print("T = ");
  Serial.print(SHT2x.GetTemperature());
  Serial.write(9); // printing a tab using ASCII code
  Serial.print("H = ");
  Serial.println(SHT2x.GetHumidity());
}

void printValuesHTU() {
  Serial.print("HTU: ");
  Serial.write(9); // printing a tab using ASCII code
  float humd = HTU.readHumidity();
  float temp = HTU.readTemperature();

  Serial.print("T = ");
  Serial.print(temp, 2);
  Serial.write(9); // printing a tab using ASCII code
  Serial.print("H = ");
  Serial.println(humd, 2);
}

void printValuesHDC2080() {
  Serial.print("HDC2080:");
  //Serial.write(9); // printing a tab using ASCII code
  Serial.print("T = "); Serial.print(HDC2080.readTemp());
  Serial.write(9); // printing a tab using ASCII code
  Serial.print("H = "); Serial.println(HDC2080.readHumidity());
}

void printValuesHDC1080() {
  Serial.print("HDC1080:");
  // Serial.write(9); // printing a tab using ASCII code
  Serial.print("T = ");
  Serial.print(hdc1080.readTemperature());
  Serial.write(9); // printing a tab using ASCII code
  Serial.print("H = ");
  Serial.println(hdc1080.readHumidity());
}

void printValuesAHT() {
  /* DEMO - 1, every temperature or humidity call will read 6 bytes over I2C, total 12 bytes */
  Serial.print(F("AHT10: "));
  Serial.write(9); // printing a tab using ASCII code
  Serial.print(F("T = ")); Serial.print(AHT.readTemperature()); //by default "AHT10_FORCE_READ_DATA"
  Serial.write(9); // printing a tab using ASCII code
  Serial.print(F("H = ")); Serial.println(AHT.readHumidity());    //by default "AHT10_FORCE_READ_DATA"
}

void printValueSi7021() {
  Serial.print(F("Si7021: "));
  // Serial.write(9); // printing a tab using ASCII code
  Serial.print("T = ");
  Serial.print(Si7021.readTemperature(), 2);
  Serial.write(9); // printing a tab using ASCII code
  Serial.print("H = ");
  Serial.println(Si7021.readHumidity(), 2);

  //
  //  // Toggle heater enabled state every 30 seconds
  //  // An ~1.8 degC temperature increase can be noted when heater is enabled
  //  if (++loopCnt == 30) {
  //    enableHeater = !enableHeater;
  //    Si7021.heater(enableHeater);
  //    // Serial.print("Heater Enabled State: ");
  //    if (Si7021.isHeaterEnabled()) {
  //      //  Serial.println("ENABLED");
  //    } else {
  //      // Serial.println("DISABLED");
  //
  //      loopCnt = 0;
}

Can you say, where exactly it stops working? Also please check the levels on the I2C lines. If the I2C interface is stuck, at least one of the lines will be at constant LOW.

It's mostly random. The last two times it was after printing all the sensor values and in the middle of printing the value for HTU21D sensor.

@chrisl How can I check the levels on the I2C lines? Do you mean checking it with a voltmeter?

Yes, I mean with a voltmeter. If one of the lines is constant low (0V) the I2C bus is stuck for some reason. In that case try to introduce small delays of a few ms between the readings of different sensors. Trying to read too fast might cause the bus to get stuck

The CLK line was stuck at 3.4V. After resetting the sketch (working normally) the CLK line alternates between 3.4V & 2.1V

I eventually want to use ESP8266 so wouldn't adding a delay() interfere with other internal timers on it? I don't remember exactly which ones but I read somewhere that using delay() on ESP8266 might cause it to reset

I tried adding a 50 millisecond delay after reading and printing each sensor value but now it gets stuck even more rapidly. However, it now always gets stuck at reading Si7021 sensor. I have uploaded the updated code as well

Are you relying solely on the internal pullup resistors of the Arduino for the SPI bus? Or are there discrete pullups on your bus or within some of the sensor modules you're using?

For the sensors connected to the multiplexer I have used additional pull up resistors while those connected directly to the arduino bus don't have any pull up resistors


text:
Huzzah feather scl sda
Trying to hook up an hazzah feather to a pca9685 scl sda connection and have a bno055 connected to that.The 5 volts to power the PCA is not taken from feather. I have a GPS module connected to pin 12 of feather again not powered from feather. Gps interface works fine. I see it though web page interface.
Then I hook up the PCA. the wifi chip overheats and feather is fried

you talked about +5 V, but you said nothing about grounds

The grounds are the individual power supplies

that means nothing ... how are all of the grounds connected?


text:
Atmega 2560 IR receiver returning random values with using NeoPixels
I am using atmega 2560 to control 590 LED lights with NeoPixels library.
I also got an IR receiver connected so I could control the LED properties and it does work but only when the LEDs are not engaged, the moment the code for LED's goes off the IR receiver keep returning random rubish.
Pressing the same button on a remote:
11:48:18.394 -> FF3AC5
11:48:19.550 -> D53AFF52
11:48:58.586 -> 24AE7D4E
11:48:59.341 -> 4CB0FADF
11:48:59.742 -> 4CB0FADF
11:49:00.491 -> 6BDBBF60
11:49:09.462 -> A8E05FBB
11:49:10.612 -> 40892F89
11:49:11.067 -> 3AD8A119
11:49:11.515 -> 2C1330B0
11:49:14.176 -> DDE32E9D
11:49:16.597 -> FF1AE5
11:49:17.445 -> A8E05FBB
11:49:17.499 -> FFFFFFFF
11:49:18.502 -> FF1AE5
11:49:18.548 -> FFFFFFFF
11:49:19.350 -> FF1AE5

IR connection diagram below:

My code below:
#include <IRremote.h>
#include <Adafruit_NeoPixel.h>

int LED_pin = 6;
int PIR_pin_D = 4;
int PIR_pin_U = 3;
int IR_pin = 2;

int LDR_pin = A0;

int pirInputU = LOW;
int pirInputD = LOW;
int ldrInput =  0;
int irInput = 0;

bool goignDown = false;
bool goingUp = false;

//states
bool lights = true;
bool constantMode = false;
byte ledBrightness = 50;
byte mode = 0;

int lightDuration = 8000;
int sensorDelay = 1500;

#define NUM_LEDS 590
#define NUM_STEPS 14

int numOfLEDs[NUM_STEPS] {41, 41, 41, 41, 41, 41, 41, 41, 41, 41, 41, 41, 57, 41};

Adafruit_NeoPixel strip(NUM_LEDS, LED_pin, NEO_GRB + NEO_KHZ800);
int32_t currentColour = strip.Color(255, 255, 255);

IRrecv irrecv(IR_pin);
decode_results results;

void setup()
{
  strip.begin();
  strip.setBrightness(ledBrightness);

  irrecv.enableIRIn();

  pinMode(LDR_pin, INPUT);    // declare sensor as input
  pinMode(IR_pin, INPUT);    // declare sensor as input
  pinMode(PIR_pin_U, INPUT_PULLUP);  // declare sensor as input
  pinMode(PIR_pin_D, INPUT_PULLUP);  // declare sensor as input

  strip.clear();
  strip.show();

  delay(10000);
  Serial.begin(9600);
}

void loop()
{
  ldrInput = analogRead(LDR_pin);    // read input value

  checkIrInput();

  if (ldrInput < 60 && lights)
  {
    pirInputU = digitalRead(PIR_pin_U); // read input value
    pirInputD = digitalRead(PIR_pin_D); // read input value
    checkIrInput();
    //UPSTAIRS SENSOR
    if (pirInputU == HIGH && pirInputD == LOW) // check if the input is HIGH
    {
      moveDown(currentColour);
      delay(lightDuration);
      moveDown(strip.Color(0, 0, 0));
      delay(sensorDelay);
      pirInputD = digitalRead(PIR_pin_D); // read input value
    }

    //DOWNSTAIRS
    if (pirInputD == HIGH && pirInputU == LOW) // check if the input is HIGH
    {
      moveUp(currentColour);
      delay(lightDuration);
      moveUp(strip.Color(0, 0, 0));
      delay(sensorDelay);
      pirInputU = digitalRead(PIR_pin_U); // read input value
    }
  }
}

void clearLedStrip()
{
  strip.clear();
  strip.show();
}

void checkIrInput()
{
  //Serial.println("pooling");

  while (!irrecv.isIdle());  // if not idle, wait till complete

  if (irrecv.decode(&results))
  {
    Serial.println(results.value, HEX);

    switch (results.value)
    {
      case 0xFF1AE5: //red
        {
          currentColour = strip.Color(255, 10, 10);
          break;
        }
      case 0xFF9A65: //green
        {
          currentColour = strip.Color(10, 255, 10);
          break;
        }
      case 0xFFA25D: //blue
        {
          currentColour = strip.Color(10, 10, 255);
          break;
        }
      case 0xFF22DD: //white
        {
          currentColour = strip.Color(255, 255, 255);
          break;
        }
      case 0xFF18E7: //yellow
        {
          currentColour = strip.Color(255, 255, 0);
          break;
        }
      case 0xFF58A7: //purple
        {
          currentColour = strip.Color(186,85,211);
          break;
        }
      case 0xFF02FD:
        {
          lights = !lights;
          break;
        }
      case 0xFF827D:
        {
          constantMode = !constantMode;
          break;
        }
      case 0xFF3AC5:
        {
          ledBrightness += 10;
          if (ledBrightness > 100)
            ledBrightness = 100;
          strip.setBrightness(ledBrightness);
          break;
        }
      case 0xFFBA45:
        {
          ledBrightness -= 10;
          if (ledBrightness < 10)
            ledBrightness = 10;
          strip.setBrightness(ledBrightness);
          break;
        }
    }
    irrecv.resume();
  }
}

void moveDown(uint32_t colour)
{
  int start = 0;

  for (int step = 0; step < NUM_STEPS; step++)
  {
    int end = (start + numOfLEDs[step]) - 1;
    int midPoint = start + numOfLEDs[step] * 0.5;

    checkIrInput();

    for (int led = start, temp = 0; led <= midPoint; led++, temp++)
    {
      strip.setPixelColor(led, colour);
      strip.setPixelColor(end - temp, colour);
      strip.show();
    }
    checkIrInput();
    start += numOfLEDs[step];
  }
}

void moveUp(uint32_t colour)
{
  int start = NUM_LEDS - numOfLEDs[NUM_STEPS - 1];

  for (int step = NUM_STEPS - 1; step >= 0; step--)
  {
    int end = (start + numOfLEDs[step]) - 1;
    int midPoint = start + numOfLEDs[step] * 0.5;

    checkIrInput();

    for (int led = start, temp = 0; led <= midPoint; led++, temp++)
    {
      strip.setPixelColor(led, colour);
      strip.setPixelColor(end - temp, colour);
      strip.show();
    }
    checkIrInput();
    start -= numOfLEDs[step];
  }
}

Is atmega 2560 not powerfull enough? Or is there something that I am doing wrong?
Any feedback welcome, thank you.

start with example IR receive code ... that will confirm the module functionality

Hi as mentioned in my question I got the IR receiver working but the moment the NeoPixel code get's run to turn on the LED lights the IR receiver starts returning random values and once LEDs stop changing the IR values go back to normal

then shield the IR receiver from the neopixels

you think it's a physical problem rathe than software?

no, i do not think that ... i have no preconceived opinion about the source of the problem ... shielding the IR receiver is the easiest troubleshooting step

you problem is that both libraries are accessing the same pin interrupt. But only one can use it. I never found a solution for the problem but your code is not working this way.


text:
Ardutester Millenium I2c Lcd Not Showing Anything!
Hiii Friends....,
I am Trying to Build Components tester Using Arduino Specifically Atmega328p Chip .
I Downloaded The Ardutester Millenium Code From Here ..  https://create.arduino.cc/projecthub/plouc68000/ardutester-millenium-the-ultimate-uno-mega-versions-c81db4
Edited Makefile.h By Enabling i2c lcd Interface And Adding My I2c Lcd Adress ...   But it wont work
I tried On Uno And Mega Also Serial Monitor Output seems ok But It Doesnt Display anything on 16*2 lcd
Thanks ...... :)

Code is available at that page sir...
Thanks for your reply

please add minimal code that exhibits the problem to your post ... also include the wiring diagram that you used to connect the modules

"By Enabling i2c lcd Interface And Adding My I2c Lcd Adress ... But it won't work", based on your schematic, it doesn't seem to be a I2C interface... Also please add your code.

The schematic you posted is not for I2C. You have a connection to the regular 2x16 LCD character display. For the I2C an SSD1306.


text:
Problems with Arduino Uno Usb 2.0 shield when using a keyboard
I have an Arduino Uno and a usb 2.0 shield in which I connected a keyboard to. I have all the necessary libraries installed but what I am trying to figure out is how to light an led when I press a specific key.
I am new to codding Arduino boards and I have done a lot of reading but I cant figure out my issue I feel like if I get this figured out I will be a lot better off in my future projects.
#include <hidboot.h>
#include <usbhub.h>
#ifdef dobogusinclude
#include <spi4teensy3.h>
#endif
#include <SPI.h>

int SKEY = 8;

class KbdRptParser : public KeyboardReportParser
{
    void PrintKey(uint8_t mod, uint8_t key);

  protected:

    void OnKeyDown  (uint8_t mod, uint8_t key);
    void OnKeyUp    (uint8_t mod, uint8_t key);
    void OnKeyPressed            (uint8_t key);
};

void KbdRptParser::PrintKey(uint8_t m, uint8_t key)
{
  MODIFIERKEYS mod;
  *((uint8_t*)&mod) = m;
  Serial.print((mod.bmLeftCtrl   == 1) ? "C" : " ");
  Serial.print((mod.bmLeftShift  == 1) ? "S" : " ");
  Serial.print((mod.bmLeftAlt    == 1) ? "A" : " ");
  Serial.print((mod.bmLeftGUI    == 1) ? "G" : " ");

  Serial.print(" >");
  PrintHex<uint8_t>(key, 0x80);
  Serial.print("< ");

  Serial.print((mod.bmRightCtrl   == 1) ? "C" : " ");
  Serial.print((mod.bmRightShift  == 1) ? "S" : " ");
  Serial.print((mod.bmRightAlt    == 1) ? "A" : " ");
  Serial.println((mod.bmRightGUI  == 1) ? "G" : " ");
};

void KbdRptParser::OnKeyDown(uint8_t mod, uint8_t key)
{
  Serial.print("DN ");
  PrintKey(mod, key);
  uint8_t c = OemToAscii(mod, key);

}

void KbdRptParser::OnKeyUp(uint8_t mod, uint8_t key)
{
  Serial.print("UP ");
  PrintKey(mod, key);
}

void KbdRptParser::OnKeyPressed(uint8_t key)
{
  Serial.print("ASCII: ");
  Serial.println((char)key);
};

USB Usb;
HIDBoot<USB_HID_PROTOCOL_KEYBOARD>    HidKeyboard(&Usb);

KbdRptParser Prs;

void setup() {

 Serial.begin(9600);
#if !defined(__MIPSEL__)
  while (!Serial);
  Serial.println("Start");

  if (Usb.Init() == -1)
    Serial.println("OSC did not start.");

  delay( 1 );

  HidKeyboard.SetReportParser(0, &Prs);

}

void loop() {
 Usb.Task();
}

Anyways I know how to make if statements and how to activate pins on the Arduino but I cant figure it out in this keyboard library. For now I just made it print "TRUE" since there is not need to get complicated if I cant get the first step to work. Before I made that if statement the serial monitor would show the value assigned to the key and label it DN # and when I let up on the key it would say UP # but how can I translate that to sending a pulse to whatever pin when I push a key and stop sending a pulse when I let up on the key?
Also in my if statement that I made I know I need something before == sign but I tried multiple things and they did not work so I just left it blank and the reason I used the number 16 was because that was the value assigned to the S key in which I wanted to use to light an led. Anyways any help would be greatly appreciated!

Does anyone have any ideas?


text:
Cant upload arduino code when ESP8266-01 module is connected
I'm using this tutorial to connect my ESP8266-01 WiFi Module to Arduino UNO with Arduino IDE v. 1.8.13.

It works and the module can connect to my WiFi.
However, when I try to upload my code, it says:
avrdude: stk500_getsync() attempt 1 of 10: not in sync: resp=0x30
What could be the problem, since when I remove the reset pin it uploads the code, but now the WiFi goes down.

Your problem is that there are two ways of wiring your ESP-01 module to the Arduino:

Wired so the PC has access to it and the Arduino is effectively disabled, and
Wired so the Arduino has access to it

You are wired in configuration 1 at the moment whereby the Arduino is effectively turned off and the USB connection goes direct to the ESP-01. When you try and upload code to the Arduino it's the ESP-01 that the computer is talking to, not the Arduino.
You need to wire it in configuration 2. In this configuration the TX/RX pins of the ESP-01 connect to any two pins of the Arduino except pins 0 and 1, and the RESET pin is not connected to anything. Then you can't talk to the ESP-01 through the serial monitor - instead you have to write code for the Arduino that uses SoftwareSerial to communicate for you.
There are many many tutorials online about communicating between the Arduino and the ESP-01.

This answers so many questions that I have had. Thanks for explaining in such a clear way. Appreciate it


text:
Size limitation on char Array on ESP8266
I'm creating a log of events, stored as a txt file. If it matters, I'm using ESP8266.
To display the log of each IOT, I'm publishing the txt file to a disgnated MQTT topic for all my IOT devices (later on to Telegram ). For sorting ( new first and old last ) I read each line into char array, post it to MQTT, and save it back to txt file.
Currently char array is defined as: char log_array[20][200] - meaning I'm keeping a log of 20 records, of 200 chars long.
Is it the right way ( declare a char array ) ? are there any limitation for size of array ( say 200 records )
Guy

That method looks fine to me. Are you having a specific problem with it, or are you just sanity checking?

@Majenko both. Since I do not initiate the char array, but only define it I'm worry that define it to 200 entries ( or more ) will cause sporadic crashes, ones which I will not be able to track

If you initialize it as a global then it will go in the BSS. That gets initialized to 0, so your array will be filled with 0. Since 0 is the "End Of String" marker you just end up with 20 empty strings of length 0.  If it's a local variable it'll be on the stack, and then will be filled with who knows what. In that case initializing it to 0 with memset(log_array, 0, 20*200); will do the same job.

@Majenko it will be defined as part of my iot library - an instance which is defined globally ( does it mean' defined globally ? )

In that case it should be in the BSS in which case it should be all 0. You can force that by adding the memset into the constructor of your class (I assume you're using a class?).

@Majenko yes, it is a class

Then I can't see a problem. You're using <4kB on a chip with 80kB of RAM (though not contiguous blocks), which is nothing really.


text:
ESP8266-01 WiFiEsp Timeout error
I am using WiFiEsp Library, ESP8266-01 Wifi Module, Arduino UNO and Arduino v.1.8.13.
ESP Details: AT version:1.2.0.0.
SDK version:1.5.4.1(39cb9a32)
v1.0.0.
The module is also in AT+CWMODE=1.
My module connection is as follows:
RX: Pin 6
TX: Pin 7
VCC: 3.3V
GND: GND
CH-PD: 3.3V
I have created a wifi hotspot on my phone which I try to connect to using the module, so that I can be able to pass some variables from arduino sensor to my php script which is hosted locally on phpMyadmin.
However, I can not seem to make the connection past connecting to wifi, since it says wifi shield is not present. Even the AT commands dont work.
What could I be doing wrong? Below is my code snippet:
#include "WiFiEsp.h"
// Emulate Serial1 on pins 6/7 if not present
#ifndef HAVE_HWSERIAL1
#include "SoftwareSerial.h"
SoftwareSerial Serial1(6, 7); // RX, TX
#endif
char ssid[] = "Googz";            // your network SSID (name)
char pass[] = "********";        // your network password
int status = WL_IDLE_STATUS;     // the Wifi radio's status
char server[] = "localhost/bella/espdata.php";

// Initialize the Ethernet client object
WiFiEspClient client;
void setup(){
  // initialize serial for debugging
  Serial.begin(115200);
  // initialize serial for ESP module
  Serial1.begin(9600);
  // initialize ESP module
  WiFi.init(&Serial1);
  // check for the presence of the shield
  if (WiFi.status() == WL_NO_SHIELD) {
    Serial.println("WiFi shield not present");
    // don't continue
    while (true);
  }

  // attempt to connect to WiFi network
  while ( status != WL_CONNECTED) {
    Serial.print("Attempting to connect to WPA SSID: ");
    Serial.println(ssid);
    // Connect to WPA/WPA2 network
    status = WiFi.begin(ssid, pass);
  }

  // you're connected now, so print out the data
  Serial.println("You're connected to the network");

  printWifiStatus();

  Serial.println();
  Serial.println("Starting connection to server...");
  // if you get a connection, report back via serial
  if (client.connect(server, 80)) {
    Serial.println("Connected to server");
    // Make a HTTP request
    client.println("GET /asciilogo.txt HTTP/1.1");
    client.println("Host: arduino.cc");
    client.println("Connection: close");
    client.println();
  }
}

void loop()
{
  // if there are incoming bytes available
  // from the server, read them and print them
  while (client.available()) {
    char c = client.read();
    Serial.write(c);
  }

  // if the server's disconnected, stop the client
  if (!client.connected()) {
    Serial.println();
    Serial.println("Disconnecting from server...");
    client.stop();

    // do nothing forevermore
    while (true);
  }
}

Swap your TX and RX pins. TX should connect to RX and RX should connect to TX.

Let me get this, so I should switch from using pins 6 and 7 and use 0 and 1 in arduino right?

No, you should switch from using 6 and 7 to using 7 and 6. The pin you designate as TX should connect to the RX of the ESP-01, not to the TX of the ESP-01. And vise-versa for the pin you designate as RX.

Still hits me with the same error. Even AT commands are not failing. Could it be the IDE version that's the problem?

Is there any other possible possibility of sending variables from Arduino to php local server.? considering I don't access internet since its localhost

Are you sure your ESP8266 runs at 9600 baud?

I tried on both 9600 and 115200. Doesnt work.

at what baud rate could you communicate with AT firmware from Serial Monitor and did you execute AT+UART=9600,8,1,0,0 to set the baud rate in AT firmware?


text:
OLED display on I2C causes esp8266 to reset

I have connected two temp sensors and an OLED display to a NodeMCU using I2C. When the program reaches the instruction to print the measurements on the display the program crashes and NodeMCU resets itself. In the serial monitor I see "rst cause 2". I did search about this online but couldn't find a similar issue involving an OLED. I wonder what is causing this reset and how to fix it?
#include <Wire.h>
#include <Adafruit_Sensor.h>
#include <Adafruit_BME280.h>
#include <Sodaq_SHT2x.h>
#include <Adafruit_SSD1306.h>

//defining OLED dimensions
#define WIDTH 128
#define HEIGHT 32
#define OLED_RESET -1

Adafruit_SSD1306 display(OLED_RESET);

Adafruit_BME280 bme1; // I2C

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

  Wire.begin();
  display.begin(SSD1306_SWITCHCAPVCC, 0x3C); // initiate OLED

  Serial.println(F("BME280 test"));

  //BME280 sensor 1
  if (! bme1.begin(0x77, &Wire)) {
    Serial.println("Could not find a valid BME280 sensor, check wiring!");
    while (1);
  }

  //  weather monitoring
//  Serial.println("-- Weather Station Scenario --");
//  Serial.println("forced mode, 1x temperature / 1x humidity / 1x pressure oversampling,");
//  Serial.println("filter off");
  bme1.setSampling(Adafruit_BME280::MODE_FORCED,
                   Adafruit_BME280::SAMPLING_X1, // temperature
                   Adafruit_BME280::SAMPLING_X1, // pressure
                   Adafruit_BME280::SAMPLING_X1, // humidity
                   Adafruit_BME280::FILTER_OFF   );
}

void loop() {
  unsigned long newTime = millis();
  static unsigned long oldTime = 0;

  if (newTime - oldTime >= 10000) {
    oldTime = newTime;

    float temp1 = 0.0;
    float humid1 = 0.0;
    float temp2 = 0.0;
    float humid2 = 0.0;

    takeReadingsBME(temp1, humid1);
    printValuesBME(temp1, humid1);

    takeReadingsSHT(temp2, humid2);
    printValuesSHT(temp2, humid2);
    displayResults(temp1, temp2, humid1, humid2);
  }
}

void printValuesBME(float temp, float humid) {

  Serial.println();
  Serial.print("BME: ");
  Serial.write(9);
  Serial.print("T = ");
  Serial.print(temp);
  Serial.write(9);
  Serial.print("H = ");
  Serial.println(humid);
}

void printValuesSHT(float temp2, float humid2) {
  Serial.print("SHT21: ");
  Serial.write(9);
  Serial.print("T = ");
  Serial.print(temp2);
  Serial.write(9);
  Serial.print("H = ");
  Serial.println(humid2);
}

void displayResults(float temp1, float temp2, float humid1, float humid2) {
  display.clearDisplay();
  display.setTextColor(WHITE);
  display.setTextSize(1);
  display.setCursor(0, 0);
  display.print("Sensor Data");
  display.println();
  display.print("BME ");
  display.print("T = ");
  display.print(temp1,1);
  display.print(" H = ");
  display.println(humid1,1);
  //display.setCursor(0, 0);
  //  display.print("ST: ");
  //  display.print("T = ");
  //  display.print(SHT2x.GetTemperature(), 1);
  //  display.print(" H1 = ");
  //  display.println(SHT2x.GetHumidity(), 1);
  display.display();
}

void takeReadingsBME(float &temp1, float &humid1) {

  bme1.takeForcedMeasurement();
  temp1 = bme1.readTemperature();
  humid1 = bme1.readHumidity();
}

void takeReadingsSHT(float &temp2, float &humid2) {

  temp2 = SHT2x.GetTemperature();
  humid2 = SHT2x.GetHumidity();
}

Sounds like power problems.

I am powering the components and the NodeMCU via external power supply. It should not be an issue normally

Can you provide a diagram detailing how it is all wired up? Including the power supply?

Reset cause 2 is a reset triggered by the reset button, JFYI (https://docs.espressif.com/projects/esp-idf/en/latest/esp32/api-reference/system/system.html#_CPPv418esp_reset_reason_t)

@Majenko I have added the circuit diagram. I could not find exact power adapter component so I have used a generic 9V power supply. In reality I have a breadboard power supply that converts 9V DC to 3.3V.

@SimSon yes I also found that but the OLED doesn't have a reset button and I am not at all pushing the reset button on ESP8266

Add a large capacitor (10uF or greater) across the 3.3V and GND pins of the ESP8266 right by the module.


text:
Where is the Arduino IDE log file located? Not the Serial Monitor
"An error ocurred while uploading the sketch"
I'm having this specific error when uploading a sketch to my board and the IDE doesn't specify the problem correctly.
It's version is 1.8.13 for Windows 10.
I would like to get a file with detailed information about the IDE's error. Where should I look for it?

Turn on verbose errors in preferences. It will display more errors. And use the scroll bar in the output panel to scroll back to see the error. There is no log file.

If there is no log file, this response seems like a proper answer.

There is no log file. Instead you need to turn on both "compilation" and "upload" under the "Show verbose output during:" option in Preferences.
This will give you far more information about any errors in the output scroll pane at the bottom of the IDE.
On Linux if you run the IDE from the command line you get large amounts of logging on stdout. There may be a way of doing the same from Windows.


text:
Run a dc motor for amount of time without delay
Hi everyone I have a project and I need to run a dc motor for amount of time without using delay I use DelayWithoutBlink technique.
In this code the motor should run for 5 second in cw then it will change the direction it will other 5second in ccw direction but it seems that there is something wrong with my code, any help would be greatly appreciated.
unsigned long timeRun = 5000;
boolean choiceOne = false;
boolean choiceTwo = false;
boolean directionOne;
boolean directionTwo;
unsigned long timeRunOne;
unsigned long timeRunTwo;

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

void loop() {
    char t = Serial.read();
    if (t == 'a') {
        while (choiceOne == false) {
            digitalWrite(9, HIGH);
            digitalWrite(8, LOW);
            directionOne = true;
            timeRunOne = millis();
            if (directionOne && (millis()-timeRunOne > timeRun)) {
                choiceOne = true;
            }
        }
    }
    if (t == 'b') {
        while (choiceTwo == false) {
            digitalWrite(9, LOW);
            digitalWrite(8, HIGH);
            timeRunTwo = millis();
            directionTwo = true;
            if (directionTwo && (millis()-timeRunTwo > timeRun)) {
                choiceTwo = true;
            }
        }
    }
}

I wonder if you understand the concept of blink without delay.  Because your code still has delay.  The whole point is that without the delay the loop can run really really fast over and over and will catch when it is time to do things.  Once you introduce a while loop you have broken that because now loop cannot finish and repeat fast, it has to wait for that while loop.

When you do this right there will be no while and no delay.  The code will read like, if the motor is on and it's time to turn it of then turn it off.  Else if it is off and time to turn it on, check which direction it should be and turn it on

You also need to brush up on the difference between = and ==.  Google that one.

ok I will delete delay

there is something wrong with my code is a useless description of a problem ... what is the observed behavior?

In the question you talk about the direction changing automatically, yet in the code it is controlled by the serial port. What gives? 2. There are too many variables in your program. When you have so many booleans, chances are you really need a finite state machine. Also, the variables directionOne and directionTwo serve no purpose, as they are always true when you read them.


text:
Relay + Arduino uses too much power for battery to handle. Which solution is best?
You can see in my crumby schematic that I am using a Non-latching relay to turn on a 3A circuit (one of them arc lighters), which is powered by a 25C (supposedly) lipo battery. That same battery also powers an Arduino through a TP4056. This works fine when I first turn it all on, but once the relay is activated by the Arduino, the lighter + Relay only turn on for a split second before stopping (when the Arduino is powered via USB, it works fine). I am thinking that the Arduino+Relay+Lighter is too much for the battery, even though it claims to be 25C. It is just strange because the Arduino+Activated Relay consume what, like 200 mA?
Notes:
When I manually turn on the lighter, the light on the Arduino dims a fair bit, but stays on.
The Arduino is running at logic level of 3.3V so that I didn't need a booster.

As for fixes, I was thinking about trying to use a transistor or SSR instead of the chunky relay I have now (which would be good, I need this to be compact). Or maybe the TP4056 is failing to provide enough output despite a decent input?
I am FAR from an electrical engineer so if anyone has any pro tips for improving this it would be much appreciated.

what is the voltage output of the battery when the lighter is energized?

When you put power to the LED lighters the current is high for a short time. You can't compare this value to the continuous current that you can detect with a multimeter. The best way is to use another power supply for the Arduino. The relais I used hat two different circuits: logic and power.

The TP4056 is a battery charger not a power supply.

The TP4056 is a battery charger, not a voltage regulator. It cannot be used to supply power to a device like an Arduino. It is designed for charging the Lithium Ion battery from a 5V (e.g., USB) source.
By trying to use it as a power supply you're asking for trouble. It thinks it's trying to charge a battery (from a 3.7V nominal source) and will be doing things like:

Running constant current making the voltage fluctuate wildly as current demands change
Running constant voltage with limited current causing starving of power
Shutting off when it thinks it sees the non-existent battery being fully charged.

The TP4056 should be connected to a 5V USB power source and to the battery for charging it. The battery should be then through a (very) low-dropout regulator (ideally a switching regulator with zero dropout bypass ability) to power the Arduino at 3.3V.
Alternatively, if you don't need a (reasonably) precise 3.3V then you can power the Arduino directly from the battery.


text:
I want 2 output pins to working alternately
I have given pwm output on pin(9) and I Want pin(10) to be high when pin(9) is low and pin(10) to be low when pin(9) is high.  So what should i add to my code?

"So what should i add to my code"? Know how to use if ... else ...?

Do you care if for few microseconds they are the same?

That depends on how you achieved your PWM on pin 9. analogWrite? Manual timer manipulation?
I'd set up one of the timers for PWM (timer mode 1 or 3) and have it call its interrupts (OCIExx).
In the interrupt, you'd then alternate between turning each pin on and off.

You can set pin 10 to run in “inverted PWM” mode, and leave
pin 9 in the default non-inverted mode. Pin 9 is the “OC1A”
pin of the AVR microcontroller (output compare of Timer 1,
channel A), whereas pin 10 is OC1B (channel B of the same
timer). Inverting the PWM mode of channel B is a matter of changing
a single bit in one of the control registers of Timer 1:
TCCR1A |= _BV(COM1B0);

You can do this once in setup(), the setting should persist. Then just
analogWrite() the same value to both pins. For some background on how
all this works, see the datasheet of the ATmega328P
microcontroller (the MCU at the hearth of your Uno),
especially section 16 “16-bit Timer/Counter1 with PWM” and table
16-3 “Compare Output Mode, Phase Correct and Phase and Frequency Correct
PWM”.

would something like the following work?
digitalWrite(9,  !digitalRead(10));

like this: https://forum.arduino.cc/index.php?topic=128698.0

The link you gave, has set a particular pin as input, but in my case i am giving pwm output from pin9 and i want that when pin 9 output is Low make other pin high and when the pin9 again goes high turn pin10 Low.  But i can't write analogwrite and analog read on same pin9

it looks like they suggest you can, but also lower down in the forum there is also a suggestion to try and just use a script that sets them as opposites whenever you set one. eg.
void setLed(bool v)
  digitalWrite(9, v);
  digitalWrite(10, !v);
}```


text:
Breaking out of the arduino fingerprint enroll loop
I am using the Arduino's Adafruit Finger Sensor library, and it has an example to enroll a fingerprint. I want it to enroll one print and exit/break out of the loop because it currently enrolls a user, then goes back to asking for a fingerprint.
Here is the code:
#include <Adafruit_Fingerprint.h>
SoftwareSerial mySerial(2, 3);
Adafruit_Fingerprint finger = Adafruit_Fingerprint(&mySerial);
uint8_t id;
void setup()
{
  Serial.begin(9600);
  while (!Serial);  // For Yun/Leo/Micro/Zero/...
  delay(100);
  Serial.println("\n\nAdafruit Fingerprint sensor enrollment");

  // set the data rate for the sensor serial port
  finger.begin(57600);

  if (finger.verifyPassword()) {
    Serial.println("Found fingerprint sensor!");
  } else {
    Serial.println("Did not find fingerprint sensor :(");
    while (1) { delay(1); }
  }
}

uint8_t readnumber(void) {
  uint8_t num = 0;

  while (num == 0) {
    while (! Serial.available());
    num = Serial.parseInt();
  }
  return num;
}

void loop()                     // run over and over again
{
  Serial.println("Ready to enroll a fingerprint!");
  Serial.println("Please type in the ID # (from 1 to 127) you want to save this finger as...");
  id = readnumber();
  if (id == 0) {// ID #0 not allowed, try again!
     return;
  }
  Serial.print("Enrolling ID #");
  Serial.println(id);

  while (!  getFingerprintEnroll() );
}

uint8_t getFingerprintEnroll() {

  int p = -1;
  Serial.print("Waiting for valid finger to enroll as #"); Serial.println(id);
  while (p != FINGERPRINT_OK) {
    p = finger.getImage();
    switch (p) {
    case FINGERPRINT_OK:
      Serial.println("Image taken");
      break;
    case FINGERPRINT_NOFINGER:
      Serial.println(".");
      break;
    case FINGERPRINT_PACKETRECIEVEERR:
      Serial.println("Communication error");
      break;
    case FINGERPRINT_IMAGEFAIL:
      Serial.println("Imaging error");
      break;
    default:
      Serial.println("Unknown error");
      break;
    }
  }

  // OK success!

  p = finger.image2Tz(1);
  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;
  }

  Serial.println("Remove finger");
  delay(2000);
  p = 0;
  while (p != FINGERPRINT_NOFINGER) {
    p = finger.getImage();
  }
  Serial.print("ID "); Serial.println(id);
  p = -1;
  Serial.println("Place same finger again");
  while (p != FINGERPRINT_OK) {
    p = finger.getImage();
    switch (p) {
    case FINGERPRINT_OK:
      Serial.println("Image taken");
      break;
    case FINGERPRINT_NOFINGER:
      Serial.print(".");
      break;
    case FINGERPRINT_PACKETRECIEVEERR:
      Serial.println("Communication error");
      break;
    case FINGERPRINT_IMAGEFAIL:
      Serial.println("Imaging error");
      break;
    default:
      Serial.println("Unknown error");
      break;
    }
  }

  // OK success!

  p = finger.image2Tz(2);
  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!
  Serial.print("Creating model for #");  Serial.println(id);

  p = finger.createModel();
  if (p == FINGERPRINT_OK) {
    Serial.println("Prints matched!");
  } else if (p == FINGERPRINT_PACKETRECIEVEERR) {
    Serial.println("Communication error");
    return p;
  } else if (p == FINGERPRINT_ENROLLMISMATCH) {
    Serial.println("Fingerprints did not match");
    return p;
  } else {
    Serial.println("Unknown error");
    return p;
  }

  Serial.print("ID "); Serial.println(id);
  p = finger.storeModel(id);
  if (p == FINGERPRINT_OK) {
    Serial.println("Stored!");
  } else if (p == FINGERPRINT_PACKETRECIEVEERR) {
    Serial.println("Communication error");
    return p;
  } else if (p == FINGERPRINT_BADLOCATION) {
    Serial.println("Could not store in that location");
    return p;
  } else if (p == FINGERPRINT_FLASHERR) {
    Serial.println("Error writing to flash");
    return p;
  } else {
    Serial.println("Unknown error");
    return p;
  }
}

Output is that after storing the fingerprint, it requests for finger to enroll, but I want it to exit after storing. Is this possible?

You are missing a return statement, when the fingerprint was enrolled correctly. Though to what do you want to exit the enrollment loop? Your code does not have anything else in it. When getting out of the while loop, it will just as again for the next ID, because it is the only thing, that you have programmed it for

I want it to ask for the ID....back at the loop instead of calling the getFingerprintEnroll() method again

Your getFingerprintEnroll() function is missing a return statement. Inside the if (p == FINGERPRINT_OK) statement, you need to insert
return 0;

after the Serial print. Only when returning zero, you will exit the while loop inside the loop() function.


text:
How to download a large text file using HTTPS on an ESP32?
Trying to create an ESP32 access to a public Spple calendar, but after connecting to the server and saving to SPIFFS it fails at the same point each time. I end up with a file of around 220 kB, when the total file should be 800 kB.
If it's helpful:
Headers from URL show:
Tranfer-Encoding: Chunked
Connection: keep-alive
Arduino IDE:
Sketch uses 891474 bytes (68%) of program storage space. Maximum is 1310720 bytes.
Global variables use 39640 bytes (12%) of dynamic memory, leaving 288040 bytes for local variables. Maximum is 327680 bytes.

Any help would be greatly appreciated, I've spent way more hours than I'd like to admit even getting here.
#include <WiFi.h>
#include <HTTPClient.h>
#include "FS.h"
#include "SPIFFS.h"

/* You only need to format SPIFFS the first time you run a
   test or else use the SPIFFS plugin to create a partition
   https://github.com/me-no-dev/arduino-esp32fs-plugin */
#define FORMAT_SPIFFS_IF_FAILED true

const char* ssid = "House N";     // your network SSID (name of wifi network)
const char* password = "Sebastian1963George"; // your network password
int LED_inbuilt = 2;

void setup() {
  Serial.end();
  delay(100);
  Serial.begin(115200);
  pinMode(LED_inbuilt, OUTPUT);
  delay(1000);
  Serial.print("WIFI status = ");
  Serial.println(WiFi.getMode());
  WiFi.disconnect(true);

  delay(1000);
  WiFi.mode(WIFI_STA);
  delay(1000);
  Serial.print("WIFI status = ");
  Serial.println(WiFi.getMode());

  digitalWrite(LED_inbuilt, HIGH);
  delay(500);
  digitalWrite(LED_inbuilt, LOW);
  delay(500);

  WiFi.begin(ssid, password);

  while (WiFi.status() != WL_CONNECTED) {
    delay(1000);
    Serial.println("Connecting to WiFi..");
  }

  Serial.println("Connected to the WiFi network");

  if (!SPIFFS.begin(FORMAT_SPIFFS_IF_FAILED)) {
    Serial.println("SPIFFS Mount Failed");
    return;
  }
}

const char* root_ca= \
"-----BEGIN CERTIFICATE-----\n" \
"MIICiTCCAg+gAwIBAgIQH0evqmIAcFBUTAGem2OZKjAKBggqhkjOPQQDAzCBhTEL\n" \
"MAkGA1UEBhMCR0IxGzAZBgNVBAgTEkdyZWF0ZXIgTWFuY2hlc3RlcjEQMA4GA1UE\n" \
"BxMHU2FsZm9yZDEaMBgGA1UEChMRQ09NT0RPIENBIExpbWl0ZWQxKzApBgNVBAMT\n" \
"IkNPTU9ETyBFQ0MgQ2VydGlmaWNhdGlvbiBBdXRob3JpdHkwHhcNMDgwMzA2MDAw\n" \
"MDAwWhcNMzgwMTE4MjM1OTU5WjCBhTELMAkGA1UEBhMCR0IxGzAZBgNVBAgTEkdy\n" \
"ZWF0ZXIgTWFuY2hlc3RlcjEQMA4GA1UEBxMHU2FsZm9yZDEaMBgGA1UEChMRQ09N\n" \
"T0RPIENBIExpbWl0ZWQxKzApBgNVBAMTIkNPTU9ETyBFQ0MgQ2VydGlmaWNhdGlv\n" \
"biBBdXRob3JpdHkwdjAQBgcqhkjOPQIBBgUrgQQAIgNiAAQDR3svdcmCFYX7deSR\n" \
"FtSrYpn1PlILBs5BAH+X4QokPB0BBO490o0JlwzgdeT6+3eKKvUDYEs2ixYjFq0J\n" \
"cfRK9ChQtP6IHG4/bC8vCVlbpVsLM5niwz2J+Wos77LTBumjQjBAMB0GA1UdDgQW\n" \
"BBR1cacZSBm8nZ3qQUfflMRId5nTeTAOBgNVHQ8BAf8EBAMCAQYwDwYDVR0TAQH/\n" \
"BAUwAwEB/zAKBggqhkjOPQQDAwNoADBlAjEA7wNbeqy3eApyt4jf/7VGFAkK+qDm\n" \
"fQjGGoe9GKhzvSbKYAydzpmfz1wPMOG+FDHqAjAU9JM8SaczepBGR7NjfRObTrdv\n" \
"GDeAU/7dIOA1mjbRxwG55tzd8/8dLDoWV9mSOdY=\n" \
"-----END CERTIFICATE-----\n";

void loop() {
  getCalendar();

  delay(1000);
  readFile(SPIFFS, "/calendar.txt");
}

void getCalendar() {
 File file = SPIFFS.open("/calendar.txt", "a");

 if (!file) {
   Serial.println("- failed to open file for writing");
   return;
 }

 if ((WiFi.status() == WL_CONNECTED)) { // Check the current connection status
   HTTPClient http;
   http.begin("https://p64-caldav.icloud.com/published/2/MTExOTIzNTUyNDExMTkyM_t4rBfkJzy02anGOy6aHJIsgECeJGkvldH8kJEjylMtRScq7BUY4vOst7NZU_0bLtKJ0JICjDL0ECuF9L_p8lQ", root_ca); //Specify the URL and certificate
    int httpCode = http.GET(); // Make the request

    if (httpCode == HTTP_CODE_OK) { // Check for the returning code
      http.writeToStream(&file);
    }

    file.close();
    Serial.println("you have finished downloading");
    http.end(); // Free the resources
  }

  delay(1000);
}

void readFile(fs::FS &fs, const char * path) {
  Serial.printf("Reading file: %s\r\n", path);

  File file = fs.open(path);
  if (!file || file.isDirectory()) {
    Serial.println("- failed to open file for reading");
    return;
  }

  Serial.println("- read from file:");

  while (file.available()) {
    Serial.write(file.read());
  }
}

void deleteFile(fs::FS &fs, const char * path) {
  Serial.printf("Deleting file: %s\r\n", path);
  if (fs.remove(path)) {
    Serial.println("- file deleted");
  } else {
    Serial.println("- delete failed");
  }
}

this sounds like it's begging to be pre-processed on a different computer/VPS, summarized, then provided to the ESP32 in no-mess form.

Haha, potentially, but I was hoping to get a standalone device that did everything, and it seems like ESP32 should be able to do it, plus I don't have much experience in either, and learning a whole new area of computer programming to get it working seems overwhelming!

You are basically running out of memory, use streamHttpClient.

Just wanted to say thanks to dandavis and hcheung! Got that bit working! The project as a whole has defeated me, but you both were really helpful, thanks!


text:
Digispark ATtiny85 not recognized (bootloader problem)
I recently bought an ATtiny85 based development board. (picture below)

I managed to install it correctly following the official guides, without a problem.
Drivers are installed correctly, and I used the Arduino IDE to actually upload a few sketches and tested them in two computers.
SUDDENLY
It has stopped working, based on my research, it seems that the bootloader got damaged. Any idea on how to fix this? I thought about burning the bootloader using Arduino, but I have barely got an idea on how to begin.
Backside of the Attiny85

You'd need a high voltage programmer to change the bootloader on the digispark. I've used a separate Arduino with a high voltage programmer sketch, a transistor and a stack of three coincells (for the high voltage), to change the fuses, to enable the reset pin. But it's not a very beginner friendly process. I'd cut my losses and get a new board.

That sounds like a wonderful beginner project! In any case, if I buy a new one, this will probably happen again, so it is time to start getting into it right away.
Do you have any resources on how to start doing this? I'm getting an Arduino Uno this week @Gerben

I like your enthusiasm. I'm not sure what code I used, but https://github.com/ArminJo/ATtiny-HighVoltageProgrammer_FuseEraser seems like it will do what you want. It will reset the fuses of the ATTiny85 to the default values, re-enabling ISP on the ATTiny. It uses a boost converter to generate the 12V, but you could also stack 3 coincells and hold two jumperwires to each end (like I did). After that you can program the bootloader using the Arduino-as-ISP method.

Wonderful @Gerben. I'll look at it and try it within a few days when my Arduino gets delivered. Thanks for the help (I'll let you know how it turns out).

The 3 default ways to re-program your tiny on that board are:

micronucleus bootloader (sketches only)
ISP prog. (sketches & set-fuses, InSystemProgramming)
HV prog. (re-set fuses, HighVoltage = 12V don't worry)

The bootloader in itself is like a sketch on the chip (at the beginning, taking up flash space) and talks through the software USB port on that board. It then rewrites parts of its own flash from the data the host sends, when you upload new sketches.
If that part gets damaged it won't get recognized by the host anymore and you can't use the board to reprogram itself. Unless the chip/parts died to ESD or other reasons, you still can use ISP/HV programming on the chip, which is the solution to your problem.
Read up on fuses, they are the init settings of your chip (like a BIOS) defining its behaviour. There are some fuses which can only be set once, after which they can only be changed by the HV method. Depending their setting on your chip, this could also be done with normal ISP programming.
This instructables shows how to build a HV programmer, but also demonstrates using an Arduino as normal ISP programmer (Step 4).
The original Digispark comes with the RSTDISBL fuse set, meaning you can't directly use ISP (which requires the reset pin). Thats why HV programming is neccessary, to regain the reset pin, after that you can reflash the bootloader via ISP. From then on you can use the bootloader again, to reprogram (upload) your sketches.

Whilst this may theoretically answer the question, it would be preferable to include the essential parts of the answer here, and provide the link for reference.


text:
How do I disable drag-and-drop text editing in Arduino IDE
How do I disable drag-and-drop text editing in Arduino IDE?  This is very annoying.  If not careful, this causes code to move around when trying to copy and paste...

I cannot find any settings in 'Preferences' that control drag-and-drop functionality.

If you cannot a corresponding setting in the preferences file, the IDE doesn't have this feature. The Arduino IDE is really not a good IDE, so you might want to move to a more professional IDE

ctrl-z is your friend

When I did a bigger (proof of concept) project, I use Visual Studio, Eclipse (or any decent IDE), and you still can use the Arduino IDE to compile.

@MichelKeijzers - what do you mean "still can use the Arduino IDE to compile"? do you mean - copy from the other IDE back into Arduino IDE for the compile and load?  Or do you mean, you can use the other IDE and somehow get the Arduino IDE to recognize changes in an external IDE to compile against?

I mean the last ... edit in the external IDE, and press the compile button (or shortcut) of the Arduino IDE. I remember there was an issue one way around (I think the Arduino does not recognize automatically changes), so you have to make the .ino file stable (just let it load a C++ (startup) class that executes everything.

Thanks @MichelKeijzers - I will give it a try!

In the preferences dialog, there is a checkbox labeled “Use external editor”.