Всем привет! Пилю счетчик подписчиков youtube, который тащит данные для подключения к wifi c sd карты. Проблема в том, что если нету void readWifiConfig (чтение данных с карты памяти) и переменные заданы вручную, то экран работает и выдает данные, но все, что идет после подключения void readWifiConfig не дает экрану включиться и работать нормально. Ничего не понимаю, может подскажете? Код (C++): #include <YoutubeApi.h> #include <ESP8266WiFi.h> #include <WiFiClientSecure.h> #include <ArduinoJson.h> #include <Wire.h> #include <LiquidCrystal_I2C.h> #include <SPI.h> #include <SD.h> #define API_KEY "стерто" #define CHANNEL_ID "стерто" File myFile; char wifiSsid[63]; char wifiKey[63]; char temp; char settingSsid[5] = "SSID"; char settingKey[4] = "KEY"; char settingTemp[10]; char valueTemp[63]; int settingTempLastPos = 0; int valueTempLastPos = 0; int percentCount = 0; int andCount = 0; bool isSetting = true; bool ssidValueFound = false; bool keyValueFound = false; int nextStatDelay = 100; LiquidCrystal_I2C lcd(0x27, 16, 2); WiFiClientSecure client; YoutubeApi api(API_KEY, client); unsigned long api_mtbs = 60000; unsigned long api_lasttime; long subs = 0; void readWifiConfig() { Serial.println("Initializing SD card..."); if (!SD.begin(4)) { Serial.println("Initialization failed!"); return; } lcd.clear(); lcd.setCursor(2, 0); Serial.println("Initialization done."); // lcd.print("Initialization done."); myFile = SD.open("CONFIG.TXT"); if (myFile) { Serial.println("CONFIG.TXT"); while (myFile.available()) { temp = myFile.read(); if (temp == '%') { percentCount++; isSetting = true; if (percentCount == 2) { //Serial.println(settingTemp); if (strcmp(settingSsid,settingTemp) == 0) { Serial.println("SSID SETTING FOUND"); //IF FOUND RAISE FLAG FOR ADDING VALUE TO SSID CHAR ARRAY ssidValueFound = true; } else if (strcmp(settingKey,settingTemp) == 0) { Serial.println("KEY SETTING FOUND"); //IF FOUND RAISE FLAG FOR ADDING VALUE TO SSID CHAR ARRAY keyValueFound = true; } memset(&settingTemp[0], 0, sizeof(settingTemp)); settingTempLastPos = 0; percentCount = 0; } } else if (temp == '&') { andCount++; isSetting = false; if (andCount == 2) { //Serial.println(valueTemp); if (ssidValueFound) { //Serial.println(valueTemp); memcpy(wifiSsid,valueTemp,63); //Serial.println(wifiSsid); ssidValueFound = false; } else if (keyValueFound) { //Serial.println(valueTemp); memcpy(wifiKey,valueTemp,63); //Serial.println(wifiKey); keyValueFound = false; } memset(&valueTemp[0], 0, sizeof(valueTemp)); valueTempLastPos = 0; andCount = 0; } } else { if (isSetting == true) { //setting settingTemp[settingTempLastPos] = temp; settingTempLastPos++; } else if (isSetting == false) { //value valueTemp[valueTempLastPos] = temp; valueTempLastPos++; } } } //Serial.println(settingTemp); myFile.close(); } else { Serial.println("Can't open CONFIG.TXT"); } } void setup() { lcd.begin(); lcd.backlight(); lcd.clear(); lcd.setCursor(2, 0); Serial.begin(115200); // Скорость загрузки Serial.println(); delay(10); readWifiConfig(); Serial.println(wifiSsid); Serial.println(wifiKey); // Попытка подключения к WIFI сети WiFi.begin(wifiSsid, wifiKey); Serial.print("connecting"); lcd.print("connecting"); while (WiFi.status() != WL_CONNECTED) { Serial.print("."); lcd.print("."); delay(500); } Serial.println(); Serial.print("connected: "); Serial.println(WiFi.localIP()); lcd.clear(); lcd.setCursor(2, 0); lcd.print(WiFi.localIP()); lcd.setCursor(2, 1); lcd.print("wait for data"); Serial.print("wait for data"); } void loop() { if (millis() - api_lasttime > api_mtbs) { if (api.getChannelStatistics(CHANNEL_ID)) { lcd.clear(); Serial.println(api.channelStats.subscriberCount); lcd.setCursor(4, 0); lcd.print("SUBSCIBER"); lcd.setCursor(6, 1); lcd.print(api.channelStats.subscriberCount); delay(20000); delay(nextStatDelay); lcd.clear(); Serial.println(api.channelStats.viewCount); lcd.setCursor(6, 0); lcd.print("VIEW "); lcd.setCursor(5, 1); lcd.print(api.channelStats.viewCount); delay(10000); } delay(nextStatDelay); } }
С большой вероятностью портится память. Вот например: Код (C++): if (isSetting == true) { //setting settingTemp[settingTempLastPos] = temp; settingTempLastPos++; } Вы пишите в память, и не проверяете на выход за пределы буфера.
Вы код сами писали, или нашли на просторах интернета? Вы понимаете что он делает, и как это работает? Перед тем как записать в буфер, нужно проверить не выходит ли значение указателя за пределы буфера. Хотя бы так: Код (C++): if (isSetting == true) { //setting if ( settingTempLastPos < sizeof(settingTemp)-1) { settingTemp[settingTempLastPos] = temp; settingTempLastPos++; } } Но я не знаю, что у Вас на карте памяти, и какие там строки. Во вторых, у вас строки получаются без завершающего 0. В Си признаком окончания строки является 0. Я для него оставил один байт буфера вычтя из размера 1 ( sizeof(settingTemp)-1) Но в коде вы ноль в конец строки нигде не записываете.
Код собрал из двух. Один - это счетчик подписчиков, но с настройками сразу в коде, второй код - это получение настроек с SD карты, оба выложены в открытый доступ. Только что изменил код по Вашему примеру, к сожалению все так же не работает. Так же добавлю, что компорт выдает все, что от него требуется, в том числе подписчиков и просмотры с необходимой периодичностью. К вайфаю подключается, данные получает. Не работает только экран. Я понимаю, как работает только та часть кода, которая количество подписчиков получает.
В коде много закомментированного вывода в монитор порта. Раскомментируйте и смотрите, что выводится в монитор порта. Или забейте данные в коде, зачем вам SD карта.
Initializing SD card... Initialization done. CONFIG.TXT SSID SSID SETTING FOUND "точка доступа" "точка доступа" KEY KEY SETTING FOUND "пароль" "пароль" "пароль" "точка доступа" "пароль" connecting. connected: 192.168.1.81 wait for data1120 57467
Код собран из двух (некоторые данные удалены) Код (C++): #include <YoutubeApi.h> #include <ESP8266WiFi.h> #include <WiFiClientSecure.h> #include <ArduinoJson.h> #include <Wire.h> #include <LiquidCrystal_I2C.h> char ssid[] = ""; char password[] = ""; #define API_KEY "" #define CHANNEL_ID "" int nextStatDelay = 100; LiquidCrystal_I2C lcd(0x27, 16, 2); WiFiClientSecure client; YoutubeApi api(API_KEY, client); unsigned long api_mtbs = 60000; unsigned long api_lasttime; long subs = 0; void setup() { Serial.begin(115200); // Скорость загрузки Serial.println(); lcd.begin(); lcd.backlight(); lcd.clear(); // Попытка подключения к WIFI сети WiFi.begin(ssid, password); Serial.print("connecting"); lcd.print("connecting"); while (WiFi.status() != WL_CONNECTED) { Serial.print("."); lcd.print("."); delay(500); } Serial.println(); Serial.print("connected: "); Serial.println(WiFi.localIP()); lcd.clear(); lcd.setCursor(2, 0); lcd.print(WiFi.localIP()); lcd.setCursor(2, 1); lcd.print("wait for data"); Serial.print("wait for data"); } void loop() { // Отображение информации на диплее if (millis() - api_lasttime > api_mtbs) { if (api.getChannelStatistics(CHANNEL_ID)) { // Количество ПОДПИСЧИКОВ lcd.clear(); Serial.println(api.channelStats.subscriberCount); lcd.setCursor(4, 0); // Курсор для сдвига слова lcd.print("SUBSCIBER"); // Слово SUBSCIBER (подписчики) можно изменить на свое ( например Имя канала) ТОЛЬКО на АНГЛ.ЯЗ! lcd.setCursor(6, 1); // Курсор для сдвига цифр lcd.print(api.channelStats.subscriberCount); delay(20000); // Время задержки надписи на дисплее (в миллисекундах) delay(nextStatDelay); // Количество ПРОСМОТРОВ lcd.clear(); Serial.println(api.channelStats.viewCount); lcd.setCursor(6, 0); // Курсор для сдвига слова lcd.print("VIEW "); // Слово VIEW (просмотры) можно изменить на свое. ТОЛЬКО на АНГЛ.ЯЗ! lcd.setCursor(5, 1); // Курсор для сдвига слова lcd.print(api.channelStats.viewCount); delay(10000); //Время задержки надписи на дисплее (в миллисекундах) } delay(nextStatDelay); } } Второй код взят с форума по 8266 Код (C++): #include #include File myFile; char wifiSsid[63]; char wifiKey[63]; char temp; char settingSsid[5] = "SSID"; char settingKey[4] = "KEY"; char settingTemp[10]; char valueTemp[63]; int settingTempLastPos = 0; int valueTempLastPos = 0; int percentCount = 0; int andCount = 0; bool isSetting = true; bool ssidValueFound = false; bool keyValueFound = false; void readWifiConfig() { Serial.println("Initializing SD card..."); if (!SD.begin(4)) { Serial.println("Initialization failed!"); return; } Serial.println("Initialization done."); myFile = SD.open("CONFIG.TXT"); if (myFile) { Serial.println("CONFIG.TXT"); while (myFile.available()) { temp = myFile.read(); if (temp == '%') { percentCount++; isSetting = true; if (percentCount == 2) { //Serial.println(settingTemp); if (strcmp(settingSsid,settingTemp) == 0) { Serial.println("SSID SETTING FOUND"); //IF FOUND RAISE FLAG FOR ADDING VALUE TO SSID CHAR ARRAY ssidValueFound = true; } else if (strcmp(settingKey,settingTemp) == 0) { Serial.println("KEY SETTING FOUND"); //IF FOUND RAISE FLAG FOR ADDING VALUE TO SSID CHAR ARRAY keyValueFound = true; } memset(&settingTemp[0], 0, sizeof(settingTemp)); settingTempLastPos = 0; percentCount = 0; } } else if (temp == '&') { andCount++; isSetting = false; if (andCount == 2) { //Serial.println(valueTemp); if (ssidValueFound) { //Serial.println(valueTemp); memcpy(wifiSsid,valueTemp,63); //Serial.println(wifiSsid); ssidValueFound = false; } else if (keyValueFound) { //Serial.println(valueTemp); memcpy(wifiKey,valueTemp,63); //Serial.println(wifiKey); keyValueFound = false; } memset(&valueTemp[0], 0, sizeof(valueTemp)); valueTempLastPos = 0; andCount = 0; } } else { if (isSetting == true) { //setting settingTemp[settingTempLastPos] = temp; settingTempLastPos++; } else if (isSetting == false) { //value valueTemp[valueTempLastPos] = temp; valueTempLastPos++; } } } //Serial.println(settingTemp); myFile.close(); } else { Serial.println("Can't open CONFIG.TXT"); } } void setup() { // put your setup code here, to run once: Serial.begin(115200); delay(10); readWifiConfig(); Serial.println(wifiSsid); Serial.println(wifiKey); } void loop() { // put your main code here, to run repeatedly: }
Это подарок для человека, живущего в другой стране. Было бы странно просить данные от вайфай сети, особенно при учете того, что это сюрприз
Тогда проще WEB страницу сделать, нет подключения к точке доступа, поднимается внутренняя точка доступа на ESP где вбиваются SSID и пароль. А что у вас по схеме подключений? Что то мне сдается у вас CS и I2C SCLна одном пине висят.
Сразу всплыла новая проблема при подключении к другой WiFi сети. Точно так же не горит экран и идет трансляция в компорт. Первый запуск проходит хорошо, а при втором ничего. В чем может быть проблема? Может что-то затирать надо при смене конфигурации?
Все, теперь проблема решена полностью. Плата оказалась не очень то и рабочей. Поменял и все заработало. Всем, кто помогал - большое спасибо!