This is my first posting in these forums, so please forgive me if this is the wrong place for my post.
I have built several projects using SSD1306 OLED displays with ESP-01, NodeMCU etc. I use the Arduino IDE and the Adafruit GFX and SSD1306 libraries. I have not had any display problems until now.
On this one project, which was working fine, I made some changes to the sketch, and now the display has gone haywire. Starting with the Adafruit logo, the pixels jump around the screen, text changes size and position. Reverting to the older sketch, everything is fine again, so it's not hardware.
I thought it might be a memory problem, but I have no experience with debugging memory problems. I'm using an ESP-01s. Strangely, the compiled sketch (.bin) with problems is smaller than the one that works.
I would appreciate any suggestions including where to post this :)
Problem with SSD1306 and ESP8266
Moderators: adafruit_support_bill, adafruit
Please be positive and constructive with your questions and comments.
- barshatriplee
- Posts: 200
- Joined: Wed Mar 22, 2023 10:11 am
Re: Problem with SSD1306 and ESP8266
Sounds like the issue is with the code inteself.
- helzayat
- Posts: 5
- Joined: Sun Mar 26, 2023 8:29 am
Re: Problem with SSD1306 and ESP8266
What in the code could make the Adafruit logo appear distorted on initializing the display?
- millercommamatt
- Posts: 831
- Joined: Tue Jul 31, 2018 4:57 pm
Re: Problem with SSD1306 and ESP8266
Post your code.
- helzayat
- Posts: 5
- Joined: Sun Mar 26, 2023 8:29 am
Re: Problem with SSD1306 and ESP8266
OK, here it is. The RemoteXY code works and the app on my Android phone does what I want it to do.
The IFTTT code works and I get the notifications I expect.
The communication between the ESP-01 controlling the front lights and the one controlling the back lights works and they turn on and off together.
The lights come on and go off at the expected times as shown on the RemoteXY display and the OLED display (when it is legible).
Replacing the OLED makes no difference, and an earlier version of this sketch works on this hardware with no display problems.
:)Please be kind, I am not a programmer and am an Arduino/8266 newbie and strictly an amateur.
The IFTTT code works and I get the notifications I expect.
The communication between the ESP-01 controlling the front lights and the one controlling the back lights works and they turn on and off together.
The lights come on and go off at the expected times as shown on the RemoteXY display and the OLED display (when it is legible).
Replacing the OLED makes no difference, and an earlier version of this sketch works on this hardware with no display problems.
:)Please be kind, I am not a programmer and am an Arduino/8266 newbie and strictly an amateur.
Code: Select all
// -- OutdoorLights --
// -- 30 April, 2023
//////////////////////////////////////////////
// RemoteXY include library //
//////////////////////////////////////////////
// RemoteXY select connection mode and include library
#define REMOTEXY_MODE__ESP8266WIFI_LIB_CLOUD
#include <ESP8266WiFi.h>
#include <RemoteXY.h>
// RemoteXY connection settings
#define REMOTEXY_WIFI_SSID "RCG"
#define REMOTEXY_WIFI_PASSWORD "password"
#define REMOTEXY_CLOUD_SERVER "cloud.remotexy.com"
#define REMOTEXY_CLOUD_PORT 6376
#define REMOTEXY_CLOUD_TOKEN "BANNED"
// RemoteXY configurate
#pragma pack(push, 1)
uint8_t RemoteXY_CONF[] = // 220 bytes
{ 255, 2, 0, 81, 0, 213, 0, 16, 24, 1, 70, 33, 53, 11, 5, 5, 26, 31, 8, 0,
67, 4, 6, 16, 20, 5, 176, 24, 10, 67, 4, 6, 33, 20, 5, 218, 24, 10, 67, 4,
36, 52, 20, 5, 2, 24, 10, 67, 4, 6, 52, 20, 5, 2, 24, 10, 67, 4, 36, 33,
20, 5, 218, 24, 10, 129, 0, 5, 10, 24, 4, 98, 67, 117, 114, 114, 101, 110, 116, 32,
84, 105, 109, 101, 0, 129, 0, 5, 27, 14, 4, 98, 83, 117, 110, 114, 105, 115, 101, 0,
129, 0, 35, 46, 15, 4, 98, 79, 110, 32, 84, 105, 109, 101, 0, 129, 0, 5, 46, 13,
4, 98, 83, 117, 110, 115, 101, 116, 0, 129, 0, 35, 27, 15, 4, 98, 79, 102, 102, 32,
84, 105, 109, 101, 0, 129, 0, 49, 17, 11, 4, 98, 76, 105, 103, 104, 116, 115, 0, 2,
1, 37, 68, 22, 11, 31, 26, 12, 31, 79, 78, 0, 79, 70, 70, 0, 10, 48, 8, 67,
15, 15, 4, 26, 31, 78, 111, 114, 109, 97, 108, 0, 31, 79, 118, 101, 114, 114, 105, 100,
101, 0, 67, 5, 21, 88, 20, 5, 24, 31, 7, 67, 1, 5, 2, 53, 5, 178, 26, 23
};
// this structure defines all the variables and events of your control interface
struct {
// input variables
uint8_t switch_1; // =1 if switch ON and =0 if OFF
uint8_t pushSwitch_1; // =1 if state is ON, else =0
// output variables
uint8_t led_1; // led state 0 .. 2
char curr_time[10]; // string UTF8 end zero
char sunr_time[10]; // string UTF8 end zero
char on_time[10]; // string UTF8 end zero
char suns_time[10]; // string UTF8 end zero
char off_time[10]; // string UTF8 end zero
char day_night[7]; // string UTF8 end zero
char show_date[23]; // string UTF8 end zero
// other variable
uint8_t connect_flag; // =1 if wire connected, else =0
} RemoteXY;
#pragma pack(pop)
/////////////////////////////////////////////
// END RemoteXY include //
/////////////////////////////////////////////
//***************************************
// Added for OTA
//***************************************
#include <ESP8266mDNS.h>
#include <WiFiUdp.h>
#include <ArduinoOTA.h>
//***************************************
#include <TimeLib.h>
//#include <JsonListener.h>
//#include <time.h>
#include <SimpleTimer.h>
#include <Sun.h>
#include <Wire.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>
#include <fonts/freeSans9pt7b.h>
#define OLED_address 0x3c
#define SCREEN_WIDTH 128
#define SCREEN_HEIGHT 64
#define OLED_RESET -1
Adafruit_SSD1306 display(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, OLED_RESET);
SimpleTimer timer;
IPAddress server(192, 168, 5, 81); // the fixed IP address of the server
WiFiClient client;
int relay_control = 2;
int old_relay_control = HIGH;
const char* ssid = "RCG";
const char* pass = "password";
const int EPOCH_1_1_2019 = 1546300800;
char timeString[32];
char this_day[22];
long t_offset;
time_t its_now;
time_t tset;
time_t trise;
time_t t_on;
time_t t_off;
int old_day;
String O_status;
/******************************
IFTTT stuff
*******************************/
// Set IFTTT Webhooks event name and key
#define IFTTT_Key "BANNED"
#define IFTTT_Event "Outdoor_Lights"
#define IFTTT_Value1 "Outdoor Lights are now "
//#define IFTTT_Value2 "OFF"
String IFTTT_Value2 = "OFF";
#define IFTTT_Value3 "value 3"
void setup()
{
RemoteXY_Init();
RemoteXY.switch_1 = 0;
RemoteXY.pushSwitch_1 = 1;
Wire.begin(0, 3);
Serial.begin(115200);
delay(3000);
if (!display.begin(SSD1306_SWITCHCAPVCC, 0x3C)) {
Serial.println("SSD1306 allocation failed");
for (;;);
}
Serial.println("SSD1306 allocation succeeded");
pinMode(relay_control, OUTPUT);
digitalWrite(relay_control, HIGH);
delay(random(500));
randomSeed(millis());
display.display();
delay(1000);
display.clearDisplay();
display.setFont(&FreeSans9pt7b);
display.setTextColor(WHITE, BLACK);
display.setCursor(0, 0x10);
display.println("Getting ready...");
Serial.println("Getting ready...");
display.display();
Serial.println("\n\r======================================================================================");
Serial.println("- connecting to Home Router SSID: " + String(ssid));
WiFi.begin(ssid, pass);
while (WiFi.status() != WL_CONNECTED) {
Serial.print("*");
delay(2500);
}
Serial.println();
Serial.print("- succesfully connected - IP address: ");
Serial.println(WiFi.localIP());
display.println(WiFi.localIP());
display.display();
delay(2000);
//*****************************************
// Added for OTA
//*****************************************
// Port defaults to 8266
// ArduinoOTA.setPort(8266);
// Hostname defaults to esp8266-[ChipID]
// ArduinoOTA.setHostname("OutdoorLightsOTA-2");
ArduinoOTA.setHostname("OutdoorLightsOTA");
// No authentication by default
// ArduinoOTA.setPassword("admin");
// Password can be set with it's md5 value as well
// MD5(admin) = 21232f297a57a5a743894a0e4a801fc3
// ArduinoOTA.setPasswordHash("21232f297a57a5a743894a0e4a801fc3");
ArduinoOTA.onStart([]() {
String type;
if (ArduinoOTA.getCommand() == U_FLASH) {
type = "sketch";
} else { // U_FS
type = "filesystem";
}
// NOTE: if updating FS this would be the place to unmount FS using FS.end()
Serial.println("\r\\n\n\nStart updating " + type);
});
ArduinoOTA.onEnd([]() {
Serial.println("\nEnd");
});
ArduinoOTA.onProgress([](unsigned int progress, unsigned int total) {
Serial.printf("Progress: %u%%\r", (progress / (total / 100)));
});
ArduinoOTA.onError([](ota_error_t error) {
Serial.printf("Error[%u]: ", error);
if (error == OTA_AUTH_ERROR) {
Serial.println("Auth Failed");
} else if (error == OTA_BEGIN_ERROR) {
Serial.println("Begin Failed");
} else if (error == OTA_CONNECT_ERROR) {
Serial.println("Connect Failed");
} else if (error == OTA_RECEIVE_ERROR) {
Serial.println("Receive Failed");
} else if (error == OTA_END_ERROR) {
Serial.println("End Failed");
}
});
ArduinoOTA.begin();
//*****************************************
// End Added for OTA
//*****************************************
GetOWM;
timer.setInterval(2000L, TimeCheck); // Update Time Check every 2 seconds
}
void loop()
{
timer.run();
//***************************************
// Added for OTA
//***************************************
ArduinoOTA.handle();
//***************************************
// yield();
}
void GetOWM() {
configTime(10800, 0, "eg.pool.ntp.org"); // get UTC time via NTP
while (its_now < EPOCH_1_1_2019) {
its_now = time(nullptr);
delay(500);
}
time(&its_now);
formatTimestamp("%H:%M:%S", its_now).toCharArray(timeString, 9);
Serial.print("\r\nNew day at: " + String(timeString));
old_day = day(its_now);
Sun sun(29.97, 31.28);
formatTimestamp(" %B %e, %Y", its_now).toCharArray(this_day, 22);
Serial.println(this_day);
strcpy (RemoteXY.show_date, this_day);
//Sunrise
trise = (sun.getRise(its_now));
formatTimestamp("%H:%M:%S on %B %e, %Y", trise).toCharArray(timeString, 32);
Serial.println("Sunrise is at: " + String(timeString) + " ");
formatTimestamp("%H:%M:%S", trise).toCharArray(timeString, 9);
strcpy (RemoteXY.sunr_time, timeString);
//Off time
t_off = trise + random(-600, 600);
formatTimestamp("%H:%M:%S on %B %e, %Y", t_off).toCharArray(timeString, 32);
display.clearDisplay();
Serial.println("Off Time: " + String(timeString) + " ");
formatTimestamp("%H:%M:%S", t_off).toCharArray(timeString, 9);
strcpy (RemoteXY.off_time, timeString);
display.setCursor(0x00, 0x26);
display.print("Off ");
display.print(timeString);
//Sunset
tset = (sun.getSet(its_now));
formatTimestamp("%H:%M:%S on %B %e, %Y", tset).toCharArray(timeString, 32);
Serial.println("Sunset is at: " + String(timeString) + " ");
formatTimestamp("%H:%M:%S", tset).toCharArray(timeString, 9);
strcpy (RemoteXY.suns_time, timeString);
//On time
t_on = tset + random(-600, 600);
formatTimestamp("%H:%M:%S on %B %e, %Y", t_on).toCharArray(timeString, 32);
display.setCursor(0x00, 0x39);
display.print("On ");
display.print(timeString);
Serial.println("On Time: " + String(timeString));
formatTimestamp("%H:%M:%S", t_on).toCharArray(timeString, 9);
strcpy (RemoteXY.on_time, timeString);
Serial.println();
display.display();
yield();
} //End GetOWM()
void TimeCheck() {
RemoteXY_Handler();
time(&its_now);
int today = day(its_now);
//Current time
formatTimestamp("%H:%M:%S", its_now).toCharArray(timeString, 9);
Serial.print("\rCurrent time: " + String(timeString) + " ");
display.fillRect(0, 0, 127, 20, BLACK);
display.setCursor(0x00, 0x12);
display.print("Now ");
display.print(timeString);
// display.display();
strcpy (RemoteXY.curr_time, timeString);
//check for a new day
if (today != old_day) {
GetOWM();
}
//Check RemoteXY app settings
if (RemoteXY.pushSwitch_1 == 0)
{
// Serial.print(" OVERRIDE\r");
O_status = " OVERRIDE";
digitalWrite(relay_control, (RemoteXY.switch_1 == 1) ? LOW : HIGH);
}
else
{
//**********
if (secs_since(its_now) > secs_since(t_off) && secs_since(its_now) < secs_since(t_on))
// if ((localtime(&its_now)->tm_hour == localtime(&t_off)->tm_hour) && (localtime(&its_now)->tm_min == localtime(&t_off)->tm_min))
{ // We are in daylight
strcpy (RemoteXY.day_night, "DAY");
// Serial.print(" DAY ");
O_status = " DAY ";
digitalWrite(relay_control, HIGH);
}
else
// if ((localtime(&its_now)->tm_hour == localtime(&t_on)->tm_hour) && (localtime(&its_now)->tm_min == localtime(&t_on)->tm_min))
{ // We are at night
strcpy (RemoteXY.day_night, "NIGHT");
// Serial.print(" NIGHT ");
O_status = " NIGHT ";
digitalWrite(relay_control, LOW);
}
// Serial.print("\r");
}
//Indicators
if (!digitalRead(relay_control)) {
RemoteXY.led_1 = 1;
display.fillRect(114, 0, 13, 63, WHITE);
}
else {
RemoteXY.led_1 = 0;
display.fillRect(114, 0, 13, 63, BLACK);
}
//*****************************************
// For IFTTT
if (digitalRead(relay_control) != old_relay_control) {
// Send Webhook to IFTTT
IFTTT_Value2 = (digitalRead(relay_control) == LOW ? "ON" : "OFF");
send_webhook();
// Serial.println("Sent webhook ");
old_relay_control = digitalRead(relay_control);
}
//*****************************************
display.display();
SetBackLights();
} //End TimeCheck()
void SetBackLights() {
// Serial.print("----------");
// Serial.print(client.connect(server, 80)); // Connection to the server
client.connect(server, 80); // Connection to the server
// Serial.print(".");
String mesg = "HIGH";
if (!digitalRead(relay_control)) {
mesg = "LOW";
}
client.println(mesg); // sends the message to the server
client.println("\r");
String answer = client.readStringUntil('\r'); // receives the answer from the sever
// Serial.print(" - from server: " + answer);
client.flush();
} //End SetBackLights
String formatTimestamp(const char* fmt, time_t ctm ) {
char buf[80];
struct tm* t = localtime(&ctm);
strftime(buf, sizeof(buf), fmt, t);
return String(buf);
} //End formatTimestamp
void send_webhook() {
// construct the JSON payload
String jsonString = "";
jsonString += "{\"value1\":\"";
jsonString += IFTTT_Value1;
jsonString += "\",\"value2\":\"";
jsonString += IFTTT_Value2;
jsonString += "\",\"value3\":\"";
jsonString += IFTTT_Value3;
jsonString += "\"}";
int jsonLength = jsonString.length();
String lenString = String(jsonLength);
// construct the POST request
String postString = "";
postString += "POST /trigger/";
postString += IFTTT_Event;
postString += "/with/key/";
postString += IFTTT_Key;
postString += " HTTP/1.1\r\n";
postString += "Host: maker.ifttt.com\r\n";
postString += "Content-Type: application/json\r\n";
postString += "Content-Length: ";
postString += lenString + "\r\n";
postString += "\r\n";
postString += jsonString; // combine post request and JSON
// connect to the Maker event server
client.connect("maker.ifttt.com", 80);
client.print(postString);
// Serial.println("\r\n" + postString);
delay(500);
client.stop();
} //End send_webhook
long secs_since(time_t given_time){
struct tm *gtime;
gtime = localtime(&given_time);
return(gtime->tm_sec + 60L*(60L*gtime->tm_hour + gtime->tm_min));
}
- adafruit_support_carter
- Posts: 29151
- Joined: Tue Nov 29, 2016 2:45 pm
Re: Problem with SSD1306 and ESP8266
Try using setPins() to set the I2C pins instead of passing them in the call to begin()
https://github.com/espressif/arduino-esp32/issues/3779
https://github.com/espressif/arduino-esp32/issues/3779
- helzayat
- Posts: 5
- Joined: Sun Mar 26, 2023 8:29 am
Re: Problem with SSD1306 and ESP8266
Seems setPins is not supported in the library I have.
Code: Select all
'class TwoWire' has no member named 'setPins'
- helzayat
- Posts: 5
- Joined: Sun Mar 26, 2023 8:29 am
Re: Problem with SSD1306 and ESP8266
I thought I would illustrate this. The top part of the image shows how sometimes the Adafruit logo is distorted right from the begining. The middle part is what the display should look like, and does sometimes. The bottom is an example of the distortion I am talking about.
- Attachments
-
- Adafruit.jpg (97.72 KiB) Viewed 922 times
- adafruit_support_carter
- Posts: 29151
- Joined: Tue Nov 29, 2016 2:45 pm
Re: Problem with SSD1306 and ESP8266
Oh, that's right, setPins() is in the ESP32 BSP, but not the ESP8266.
What's the change made to the working code that makes it no longer work?
What's the change made to the working code that makes it no longer work?
Please be positive and constructive with your questions and comments.