#include <WiFi.h>
#include <HTTPClient.h>
#include <ArduinoJson.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>
#include <NTPClient.h> // Библиотека для работы с NTP
#include <WiFiUdp.h> // Для работы с UDP
#include <Timezone.h> // Добавили библиотеку Timezone
// Настройки дисплея SSD1306
#define SCREEN_WIDTH 128 // Ширина экрана
#define SCREEN_HEIGHT 64 // Высота экрана
#define OLED_RESET -1 // GPIO пин сброса (-1 если не используется)
Adafruit_SSD1306 display(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, OLED_RESET);
// Настройки Wi-Fi
const char* ssid = "Wokwi-GUEST"; // Имя сети
const char* password = ""; // Пароль
// Настройки OpenWeatherMap
const String OPENWEATHERMAP_API_KEY = "2188c81e67a8234303646ae918f7767e"; // Ваш API ключ
const String CITY_NAME = "Tashla,Russia"; // Название города
// Настройка временной зоны
TimeChangeRule myDST = {"EEST", Last, Sun, Mar, 2, 120}; // Летнее время
TimeChangeRule mySTD = {"EET", Last, Sun, Oct, 3, 60}; // Зимнее время
Timezone myTZ(myDST, mySTD);
// Настройка NTP клиента
WiFiUDP ntpUDP;
NTPClient timeClient(ntpUDP, "pool.ntp.org", 14400, 1000); // Сервер NTP, смещение времени UTC+5, интервал обновления 1 секунда
void setup() {
Serial.begin(115200);
// Инициализация дисплея
if (!display.begin(SSD1306_SWITCHCAPVCC, 0x3C)) {
Serial.println(F("SSD1306 allocation failed"));
for (;;) { /* Блокировка программы при ошибке инициализации */ }
}
display.clearDisplay();
display.setTextSize(1);
display.setTextColor(SSD1306_WHITE);
display.setCursor(0, 0);
display.println("Connecting to WiFi.");
display.display();
WiFi.begin(ssid, password);
while (WiFi.status() != WL_CONNECTED) {
delay(500);
Serial.print(".");
}
Serial.println("\nWiFi connected");
Serial.print("IP address: ");
Serial.println(WiFi.localIP());
display.clearDisplay();
display.setCursor(0, 0);
display.println("Connected!");
display.setCursor(0, 10);
display.println("Getting Weather Data.");
display.display();
delay(1000);
// Запускаем клиент NTP
timeClient.begin();
}
void loop() {
if (WiFi.status() == WL_CONNECTED) {
HTTPClient http;
String url = "https://api.openweathermap.org/data/2.5/weather?q=" + CITY_NAME + "&units=metric&appid=" + OPENWEATHERMAP_API_KEY;
http.begin(url.c_str());
int httpResponseCode = http.GET();
if (httpResponseCode > 0) {
String response = http.getString();
// Уменьшаем размер JSON-документа для экономии памяти
StaticJsonDocument<256> doc; // Увеличиваем размер документа, если потребуется больше данных
DeserializationError error = deserializeJson(doc, response);
if (error) {
Serial.print(F("deserializeJson() failed with code "));
Serial.println(error.c_str());
return;
}
const char* weatherDescription = doc["weather"][0]["description"]; // Используем константный указатель вместо копирования строки
float temperature = doc["main"]["temp"];
// Получение текущей даты и времени
timeClient.update(); // Обновляем данные от NTP-сервера
time_t utc = timeClient.getEpochTime(); // Получаем время в формате Unix Timestamp
TimeChangeRule *tcr; // Указатель на правило смены времени
time_t localTime = myTZ.toLocal(utc, &tcr); // Конвертируем UTC в местное время
// Формируем строки даты и времени
char dateTimeBuffer[32];
snprintf(dateTimeBuffer, sizeof(dateTimeBuffer), "%02d/%02d/%04d %02d:%02d",
day(localTime), month(localTime), year(localTime),
hour(localTime), minute(localTime)); // Форматируем дату и время
display.clearDisplay();
display.setCursor(0, 0);
display.println(dateTimeBuffer); // Выводим дату и время на одну строку
display.setCursor(0, 15);
display.println("Current Weather:");
display.setCursor(0, 25);
display.println(CITY_NAME);
display.setCursor(0, 35);
display.println(weatherDescription);
display.setCursor(0, 45);
display.print("Temperature: ");
display.print(temperature);
display.println(" C");
// display.print((char)247);display.print("C");
display.display();
} else {
Serial.print("Error on HTTP request: ");
Serial.println(httpResponseCode);
}
http.end();
}
delay(30000); // Обновление каждые 30 секунд
}