使用Blinker、Arduino和ESP32 OLED打造功能强大的天气时钟

提示:自己做的一个小的项目

文章目录

前言

一、开发环境

二、硬件连接

二、代码介绍

1.引入库

         2.WIFI获取时间以及温湿度

         3.APP端

三、主要代码

1.完整代码

总结


前言

第一次写博客,分享一个自己和另一位同学做的一个小的项目,入门级别。

结果展示​​​​


一、开发环境

arduino的开发环境以及blinker APP的使用参考这位佬的博客(130条消息) Arduino+esp32+blinker第一课点灯_blinker esp32_大话物联网的博客-CSDN博客

二、硬件连接

使用的是ESP-WEOOM-32小模块,连接0.96寸的OLED。OLED采用硬件I2C驱动,杜邦线连接就可使用(部分情况需要加4.7K上拉电阻)。

iic esp32引脚 功能
SDA GPIO21 数据线
SCL GPIO22 时钟线

二、代码介绍

1.引入库

使用Blinker库,以及Adafruit_SSD1306.h库

#include <WiFi.h>
#include <HTTPClient.h>
#include <WiFiClientSecure.h>
/* 中国天气网,101210401代表宁波 */
#define URL "http://www.weather.com.cn/data/sk/101210401.html"  

#define BLINKER_WIFI
#include <Blinker.h>
#include <Adafruit_SSD1306.h>

2.WIFI获取时间以及温湿度

使用NTP获取时间详细可以看这个

(130条消息) Arduino ESP32 最简单直接获取网络时间方法_esp32获取网络时间_perseverance52的博客-CSDN博客

    Blinker.run();
    /* NTP校准时间以及显示也写在这个函数内部 */
    setClock();
    /*********************************获取温湿度************************************/
      WiFiClient client;
      HTTPClient https;  
      Serial.print("[HTTPS] begin...\n");
      //配置请求地址。此处也可以不使用端口号和PATH而单纯的
      https.begin(URL); 
      Serial.print("URL: "); Serial.println(URL);
      //启动连接并发送HTTP请求
      int httpCode = https.GET();
      if (httpCode > 0) {
        // HTTP header has been send and Server response header has been handled
        Serial.printf("[HTTPS] GET... code: %d\n", httpCode); 
        // file found at server
        if (httpCode == HTTP_CODE_OK || httpCode == HTTP_CODE_MOVED_PERMANENTLY) {
              String payload = https.getString();
              Serial.println(payload);
                display.display();
              /* 得到温湿度数据,也可采用json解析的方法,本程序采用截取固定字符串法 */
              strcpy(global_tmp, payload.substring(61,65).c_str());
              strcpy(global_sd, payload.substring(105,108).c_str());
            }
          } else {
            Serial.printf("[HTTPS] GET... failed, error: %s\n", https.errorToString(httpCode).c_str());
          }
        https.end();

3.APP端

添加文本框并命名为TextKey。每次输入以1打头就回去现在第一个文本框,以此类退。

三、主要代码

1.完整代码

代码如下(示例):

#include <WiFi.h>
#include <HTTPClient.h>
#include <WiFiClientSecure.h>
/* 中国天气网,101210401代表宁波 */
#define URL "http://www.weather.com.cn/data/sk/101210401.html"  

#define BLINKER_WIFI
#include <Blinker.h>
#include <Adafruit_SSD1306.h>

/* 屏幕参数 地址0x3c 128x64 */
#define OLED_ADDR 0x3C
#define SCREEN_WIDTH 128
#define SCREEN_HEIGHT 64
#define OLED_RESET -1

/* 三个文本输入框的暂存变量 */
char global_data1[50]="task1";
char global_data2[50]="task2";
char global_data3[50]="task3";
/* 中国天气网获取的温湿度全局变量 */
char global_tmp[20]="";
char global_sd[20]="";

int cnt=0;

Adafruit_SSD1306 display(SCREEN_WIDTH, SCREEN_HEIGHT, &Wire, OLED_RESET);

/* BLINKER配网信息 */ 
//char auth[] = "d3d6ec0850d9";
//char ssid[] = "wanglu";
//char pswd[] = "123456789";
char auth[] = "9f032f669150";
char ssid[] = "iQOO7";
char pswd[] = "yx1656907246";


/* 文本框控件 */
#define TEXTE_1 "TextKey"
BlinkerText Text1(TEXTE_1);

/****************************************************
 * 文本框获取输入回调函数callback()
 * 首字符是1,存入第一个文本框暂存变量中
 * 首字符是2,存入第二个文本框暂存变量中
 * 首字符是3,存入第一个文本框暂存变量中
 * ***************************************************/
void dataRead(const String &data)
{
    /* 测试函数 */
    BLINKER_LOG("Blinker readString: ", data);
    Blinker.vibrate();
    uint32_t BlinkerTime = millis();
    Blinker.print("millis", BlinkerTime);
    Text1.print("os time", BlinkerTime);

    if (data[0] == '1') {
      // 处理第一个文本框控件的数据
      strcpy(global_data1, data.c_str());
      Serial.println(global_data1);
    } else if (data[0] == '2') {
        // 处理第二个文本框控件的数据
        strcpy(global_data2, data.c_str());
        Serial.println(global_data2);
    } else if (data[0] == '3') {
        // 处理第三个文本框控件的数据
        strcpy(global_data3, data.c_str());
        Serial.println(global_data3);
    }
}
/*****************************************
 * 初始化函数
 * **************************************/
void setup()
{
    // 串口
    Serial.begin(115200);
    BLINKER_DEBUG.stream(Serial);
    
    //按键和灯,暂时无用
    pinMode(LED_BUILTIN, OUTPUT);
    digitalWrite(LED_BUILTIN, LOW);

    // wifi和显示屏的初始化
    Wire.begin();
    display.begin(SSD1306_SWITCHCAPVCC, OLED_ADDR);
    display.display();
    display.clearDisplay();
    
    //Blinker初始化
    Blinker.begin(auth, ssid, pswd);
    Blinker.attachData(dataRead);
    

}

void loop()
{
    /* 清屏函数 */
    display.clearDisplay();
    Blinker.run();
    /* NTP校准时间以及显示也写在这个函数内部 */
    setClock();
    /*********************************获取温湿度************************************/
      WiFiClient client;
      HTTPClient https;  
      Serial.print("[HTTPS] begin...\n");
      //配置请求地址。此处也可以不使用端口号和PATH而单纯的
      https.begin(URL); 
      Serial.print("URL: "); Serial.println(URL);
      //启动连接并发送HTTP请求
      int httpCode = https.GET();
      if (httpCode > 0) {
        // HTTP header has been send and Server response header has been handled
        Serial.printf("[HTTPS] GET... code: %d\n", httpCode); 
        // file found at server
        if (httpCode == HTTP_CODE_OK || httpCode == HTTP_CODE_MOVED_PERMANENTLY) {
              String payload = https.getString();
              Serial.println(payload);
                display.display();
              /* 得到温湿度数据,也可采用json解析的方法,本程序采用截取固定字符串法 */
              strcpy(global_tmp, payload.substring(61,65).c_str());
              strcpy(global_sd, payload.substring(105,108).c_str());
            }
          } else {
            Serial.printf("[HTTPS] GET... failed, error: %s\n", https.errorToString(httpCode).c_str());
          }
        https.end();
}

/***************************************************************************************
 * NTP校准时间
 * 显示
 * **************************************************************************************/
void setClock() {
  //对于我们东八区,8 * 3600,使用夏令时 
  configTime(8 * 3600, 0, "2.cn.pool.ntp.org", "time.nist.gov","3.cn.pool.ntp.org");
  Serial.print(F("Waiting for NTP time sync: "));
  time_t nowSecs = time(nullptr);
  while (nowSecs < 8 * 3600 * 2) {
    delay(500);
    Serial.print(F("."));
    yield();
    nowSecs = time(nullptr);
  }
  Serial.println();
  struct tm timeinfo;
    if (!getLocalTime(&timeinfo))
    {
        Serial.println("Failed to obtain time");
        return;
    }
    Serial.println(&timeinfo, "%F %T %A"); // 格式化输出:2021-10-24 23:00:44 Sunday

    /*******************************************打印输出****************************************/
    //时间日期
    display.setTextSize(2);
    display.setTextColor(SSD1306_WHITE);
    display.setCursor(0, 0);
    display.println(&timeinfo, "%F %T");
    //温湿度
    display.setTextSize(1);
    display.setTextColor(SSD1306_WHITE);
    display.setCursor(100, 30);
    display.println("temp");
    display.setCursor(100, 38);
    display.setTextSize(1);
    display.println(global_tmp);
    display.setTextSize(1);
    display.setCursor(100, 47);
    display.println("humi");
    display.setCursor(100, 55);
    display.setTextSize(1);
    display.println(global_sd);
    //文本数据
    display.setTextSize(1.3);
    display.setCursor(0, 32);
    display.println(global_data1);
    display.println(global_data2);
    display.println(global_data3);
    display.display();
    
}

总结

以上就是今天要讲的内容,本文因为作者代码水平非常一般,所以写的臃肿低效,非常欢迎大家留言或提出建议。

物联沃分享整理
物联沃-IOTWORD物联网 » 使用Blinker、Arduino和ESP32 OLED打造功能强大的天气时钟

发表评论