Display issue with SSD1306

Hello everyone,

I am facing a strange problem. The code I wrote (which is not yet complete) works fine but as soon as I uncheck the comments on lines 124 and 125 I have nothing left on the SSD1306 display. That said, if I comment out other things (eg the StartUp routine), I have the same phenomenon. As if the program is lost when displayed (but continues to run anyway).

Can you help me ?
Please, I am new to arduino, I started writing in C 2 weeks ago.

Thanks for your help.

Steve

[code]
/************************************************************************************
   Code pour ARduino Uno (Webasto contôle)
   TITLE : Start Stop du webasto, contôle des températures : intérieures, extérieurs, webasto out
           Contrôle depuis l'application "Blink"
   
   Date de création : 07.08.2021 - V0
   Date de modification :  - V
 ************************************************************************************/
#include <SPI.h>
#include <Wire.h>
#include <EEPROM.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>
#include <DHT.h>

//Auto Control settings
byte cpt;
const float maxTemp = 32.5;
const float minTemp = 31.7;

int adresse = 0;
byte val_EEPROM;
bool Alim_Flag = LOW;
byte bouton;
byte CPT_menu;
bool Erreur_Flag = LOW;
bool Err_Flag = LOW;
byte menu;
bool Webasto_Flag = LOW;
bool Pompe_Flag = LOW;
bool Test_Flag = LOW;

//Define PIN constant
const int Alim = 2;
const int Webasto = 3;
const int RELAY_PIN_3 = 4;
const int RELAY_PIN_4 = 5;
const int RELAY_PIN_5 = 6;

const int Pompe = 7;
const int Enter = 8;
const int Up = 9;
const int Down = 10;
const int mswitch_5 = 11;
const int cmode = 12;
const int smode = 13;

// Uncomment the type of sensor in use:
//#define DHTTYPE    DHT11     // DHT 11
#define DHTPIN_EXT A1
#define DHTPIN_D_G A2
#define DHTPIN_D_P A3

#define DHTTYPE    DHT22     // DHT 22

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

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

DHT dht0(DHTPIN_EXT, DHTTYPE);
DHT dht1(DHTPIN_D_G, DHTTYPE);
DHT dht2(DHTPIN_D_P, DHTTYPE);
//DHT dht(DHTPIN, DHTTYPE);

DHT dht[3] = {
  {DHTPIN_EXT, DHT22},
  {DHTPIN_D_G, DHT22},
  {DHTPIN_D_P, DHT22},
};

float temperature[3];

char toggleState_1 = 'a'; //Define integer to remember the toggle state for switch 1
char toggleState_2 = 'b'; //Define integer to remember the toggle state for switch 2
char toggleState_3 = 'c'; //Define integer to remember the toggle state for switch 3
char toggleState_4 = 'd'; //Define integer to remember the toggle state for switch 4
char toggleState_5 = 'e'; //Define integer to remember the toggle state for switch 5

String pinStatus = "abcde000.0000.00";

int switchMode = 0;
int ModeFlag = 0;
float temperatureRead;
float humidityRead;
float ldrVal;
String displayText;

/******************************************************************************************/

void setup() {

  pinMode(Pompe, INPUT);
  pinMode(Enter, INPUT);
  pinMode(Up, INPUT);
  pinMode(Down, INPUT);
  pinMode(Alim, OUTPUT);
  pinMode(Webasto, OUTPUT);
  Serial.begin(9600);

  // Initialise la communication I²C à l’adresse 0x3C.
  display.begin( SSD1306_SWITCHCAPVCC, 0x3C );
  display.clearDisplay();

  for (auto& sensor : dht) {
    sensor.begin();
  }
}

/******************************************************************************************/

void loop() {
  //StartUp();
  
    //WiFi Control
    if (Serial.available() > 0)
    {
      char c_val = Serial.read(); // reading the data received from the ESP01
      
      switch (c_val)
      {
        //case 'A': digitalWrite(Alim, HIGH);  toggleState_1 = 'A'; Serial.println ( "A on" ); break; // when A is pressed on the app Turn on Pin 2
        //case 'a': digitalWrite(Alim, LOW);   toggleState_1 = 'a'; Serial.println ( "a off" ); break; // when a is pressed on the app Turn off Pin 2
        case 'B': digitalWrite(Webasto, HIGH);  toggleState_2 = 'B'; Serial.println ( "B on" ); break; // when B is pressed on the app Turn on Pin 3
        case 'b': digitalWrite(Webasto, LOW);   toggleState_2 = 'b'; Serial.println ( "b off" ); break; // when b is pressed on the app Turn off Pin 3
        case 'C': digitalWrite(RELAY_PIN_3, HIGH);  toggleState_3 = 'C'; Serial.println ( "C on" ); break; // when C is pressed on the app Turn on Pin 4
        case 'c': digitalWrite(RELAY_PIN_3, LOW);   toggleState_3 = 'c'; Serial.println ( "c off" ); break; // when c is pressed on the app Turn off Pin 4
        case 'D': digitalWrite(RELAY_PIN_4, HIGH);  toggleState_4 = 'D'; Serial.println ( "D on" ); break; // when D is pressed on the app Turn on Pin 5
        case 'd': digitalWrite(RELAY_PIN_4, LOW);   toggleState_4 = 'd'; Serial.println ( "d off" ); break; // when d is pressed on the app Turn off Pin 5
        case 'E': digitalWrite(RELAY_PIN_5, HIGH);  toggleState_5 = 'E'; Serial.println ( "E on" ); break; // when E is pressed on the app Turn on Pin 6
        case 'e': digitalWrite(RELAY_PIN_5, LOW);   toggleState_5 = 'e'; Serial.println ( "e off" ); break; // when e is pressed on the app Turn off Pin 6
        default : break;
        
      }
      
      delay(100);
    }
    Serial.print("A");
    Serial.print(cpt);

  // Effectue un envoi des données toutes les x secondes
  if (++cpt >= 10) {
    cpt = 0;
    readSensors();
    displayData();
    gestion();
    //sendStatus();
  }
delay(100);
}

/******************************************************************************************/
/* Foramatage de l'EEPROM au tout 1er start (après programmation) */
void StartUp() {

  if (val_EEPROM = EEPROM.read(250) != 10) {
    for (int i = 0 ; i < EEPROM.length() ; i++) {
      EEPROM.write(i, 10);
    }
    Serial.println("EEPROM formated");

    //Valeurs par défaut des consignes
    EEPROM.put(10, 28.5); // Start Alim génerale
    EEPROM.put(14, 30.0); // Stop Alim générale
    EEPROM.put(18, 28.0); // Start Webasto
    EEPROM.put(22, 29.0); // Stop Webasto
    EEPROM.put(26, 30.0); // Température intérieur dôme
  }
}
/******************************************************************************************/
//Lecture de la température des différents sensors et stock les valeurs dans un tableau de float.
void readSensors() {

  for (int i = 0; i < 3; i++) {
    temperature[i] = dht[i].readTemperature();

    if (isnan(temperature[i])) { //if (isnan(humidity[i]) || isnan(temperature[i])) {
      //Serial.print("Failed to read from DHT sensor!");
      //Serial.println(i);
      //return;
    }
    else {
      temperatureRead = temperature[i];
    }
  }
}

/******************************************************************************************/
void displayData() {
  // readSensors();
  display.clearDisplay();
  display.setTextSize(1);
  display.setTextColor(WHITE);

  display.setCursor(0, 0);
  display.print("T.ext    ");
  display.print(temperature[0]);
  display.print(" ");
  display.print("C    ");

  display.setCursor(0, 10);
  display.print("T.g.dome ");
  display.print(temperature[1]);
  display.print(" ");
  display.print("C    ");

  display.setCursor(0, 20);
  display.print("T.p.dome ");
  if (isnan(temperature[2])) {
    display.print("Error");
  }
  else {
    display.print(temperature[2]);
    display.print(" ");
    display.print("C    ");
  }
  display.drawLine(0, 30, display.width() - 1, 30, WHITE);

    if (Pompe_Flag == LOW) {
      display.setCursor(0, 33);
      display.print("Error Webasto");
    }
  display.display();
}

/******************************************************************************************/
void sendStatus() {
  displayData();
  pinStatus = String(toggleState_1) + String(toggleState_2) + String(toggleState_3) + String(toggleState_4) + String(toggleState_5) + String("0") + String(temperatureRead) + String(humidityRead);
  //pinStatus ="abcdE023.1055.00";
  Serial.print(pinStatus);
}

/******************************************************************************************/
//Dès que la température extérieur est en dessous de X, allumer l'alimentation. Sauf si celle-ci est déjà allumée
//Dès que la température extérieur est en dessous de X, allumer le webasto
void gestion() {
  float eevalue;
  if (temperature[0] <= EEPROM.get(10, eevalue)) {  //Température extérieur plus petite
    if (Alim_Flag == LOW) {
      digitalWrite(Alim, HIGH);
      for (int compteur = 5; compteur > 0; compteur--) {  //50
        display.clearDisplay();
        display.setTextSize(1);
        display.setCursor(8, 2);
        display.print("Alim turn ON");
        display.setCursor(10, 15);
        display.print(compteur);
        display.display();
        delay(1000);
      }
      Alim_Flag = HIGH;
    }
    if (Erreur_Flag == LOW) {
      if (temperature[0] <= EEPROM.get(18, eevalue)) {
        if (Webasto_Flag == LOW) {
          digitalWrite(Webasto, HIGH);
          delay(2000);
          digitalWrite(Webasto, LOW);
          Webasto_Flag = HIGH;
          for (int compteur = 3; compteur > 0; compteur--) {  //30
            display.clearDisplay();
            display.setTextSize(1);
            display.setCursor(8, 2);
            display.print("Webasto turn ON");
            display.setCursor(10, 15);
            display.print(compteur);
            display.display();
            delay(1000);
          }
        }
        else {
          if (temperature[1] >= EEPROM.get(22, eevalue)) {  //Température à l'intérieur trop haute alors que dehors il fait trop froid.
            goto stopWeb;                                  //Le soleil tape sur la serre. Donc stopper le webasto
          }
        }
      }
    }
    else {
      display.clearDisplay();
      display.setTextSize(1);
      display.setCursor(8, 2);
      display.print("Erreur sonde Ext");
      display.display();
      delay(1000);

    }
  }
  else {
    if ((temperature[0] >= EEPROM.get(14, eevalue)) && (Webasto_Flag == LOW)) {
      digitalWrite(Alim, LOW);
      Alim_Flag = LOW;
    }
  }
  //Stop webasto
  if ((temperature[0] >= EEPROM.get(22, eevalue)) && (Webasto_Flag == HIGH) && (Pompe_Flag == HIGH)) {
stopWeb:
    digitalWrite(Webasto, HIGH);
    delay(3000);
    digitalWrite(Webasto, LOW);

    for (int compteur = 18; compteur > 0; compteur--) {  //18
      display.clearDisplay();
      display.setTextSize(1);
      display.setCursor(8, 2);
      display.print("Webasto turn OFF");
      display.setCursor(10, 15);
      display.print(compteur);
      display.display();
      delay(1000);
    }
    Webasto_Flag = LOW;
  }
  Pompe_Flag = digitalRead(Pompe);
}
[/code]

What is connected to pin 2 ?

A relay to control a power supply

which lines are those? I don't feel like going through your code and counting lines...

in the switch case

//case 'A': digitalWrite(Alim, HIGH); toggleState_1 = 'A'; Serial.println ( "A on" ); break; // when A is pressed on the app Turn on Pin 2
//case 'a': digitalWrite(Alim, LOW); toggleState_1 = 'a'; Serial.println ( "a off" ); break; // when a is pressed on the app Turn off Pin 2

Ok, please post a complete wiring diagram. It does sound like a hardware problem.

No, nor do I. I let the IDE do it for me

That is something I save for my code. But I think it's hardware anyway...

Here is the diagram

Yeah, what is "pompe" in reality? What are the current/voltage requirements, does it have a freewheeling diode if it has a bare coil?

It's likely that the pompe is disturbing the power supply when it's turned on, because the Arduino is not an appropriate power source for it.

This is the problem with Fritzing diagrams - a black box with a name doesn't really explain what it is.

Currently I am working on test plate like the diagram. For now the pump is just an on / off switch. There is no disturbance from the outside.

The display works except when I activate the commented lines (this is an example because if I activate the 2 commented lines and I deactivate the "StartUp" function, it also works ".

But why doesn't it work when all my code is active?

But, you mentioned a relay on pin 2. At least, that's what you told us in reply #3. I don't see that in the diagram... the error caused a huge time waste. If you have an LED connected, please tell us it's a LED. So, which is it, a relay or a LED?

By the way, a SPDT switch connected to +5 and ground is not the normal way to connect a switch to a microprocessor. Usually, you would use the INPUT_PULLUP option and simply connect the switch between the I/O and ground.

What do you mean, "deactivate the startup function"? Are you saying that the EEPROM code crashes the program also? It's an EEPROM initialization so it should need to be run only once. It could even be run in a different sketch, doesn't need to be in this one.

How much memory are you using? When you compile the program, what flash and RAM memory allocations are reported?

So now it's like the diagram. It is only when I have written and tested the whole program that I will connect a relay. Sorry for the ambiguity.

Indeed, I could have used the internal pull up. I apologize, as I said, I've been coding in C. For a few weeks now, an external pull up is often used. It is not a mistake to connect it this way.

Yes, the "StartUp" sketch (which I called that) crashes the display ONLY. But only if the other 2 lines are not commented out. But this is just one example. If it's not the 2 lines or the "StartUP" sketch, it's something else I need to turn off for the display to show something.

I had also thought about memory but from what the IDE tells me after compilation, it's normal. Flash memory: 60%, SRAM: 41%

That is fairly suspect. The Adafruit_SSD1306 library allocates 1024 bytes for a 128x64 buffer at run time. Which means SRAM: 91%

I suggest that you try to reduce the SRAM usage. e.g. put anonymous xxx.print("text") messages into Flash like xxx.print(F("text"))

David.

Thanks David :hugs:

I put in flash all the texts to be displayed on the OLED. Everything is working. good.
Flash: 60%, SRAM: 36%

So does that mean that IDE is showing wrong memory values? So I can't trust it? :thinking:

No, the IDE is fine.

Adafruit_SSD1306 is a bit naughty. Nothing wrong with allocating memory at runtime. It would be wise to provide a PROMINENT build message.

Just remember to allow for the 1024 bytes.

David.

Thanks a lot, I'll think about it and maybe use greiman's library which requires less memory.