项目介绍
- 平台:基于ESP32-S2模块的物联网/音频信号处理平台
- 项目:制作一个本地气象台
- 要求:利用OLED显示当前本地的时间、温度和气象信息
- 开发平台:Vscode+esp-idf
设计思路
- 板子供电启动后立刻进入初始化状态,进行外设初始化和内部数据初始化。在初始化结束后,ESP32进入空闲状态,等待用户调用功能。
- 在外设初始化中,板子进行OLED初始化、Key按键初始化、WIFI初始化。
- 在内部数据初始化中,板子先连接SNTP服务器校正ESP32本地时间,然后创建一个时间定时器,最后更新ESP32位置信息。
- ESP32进入空闲状态后,等待用户调用功能,可供调用的功能有:显示当前时间、显示本地实时天气、显示本地今明后天气。
实现功能及展示
- 显示当前时间
- 显示本地实时天气
- 显示本地今明后天气
主要代码及功能
- OLED屏幕代码
SSD1306芯片驱动的OLED屏幕是一个非常常用的外设,在硬禾学堂往期其他项目,或是各种其他交流论坛上等等,都有丰富的驱动代码文件可以下载。再不济也可以找桃宝商家直接要,事实上许多外设的驱动代码都可以找桃宝商家要。不再赘述。
- Key按键代码
3个Key按键利用中断分别实现下列功能
Key1:显示当前时间
Key2:显示本地实时天气
Key3:显示本地今明后天气
Key按键代码基于esp-idf\examples\peripherals\gpio\generic_gpio 工程修改而来。主要对gpio_isr_task函数进行了修改。
收到来自gpio_evt_queue的信号量(按键源)后,先进行按键抖动的识别操作,检测出该中断是否有效,然后根据信号量创建不同的任务,实现三个不同功能(在HTTP代码部分细讲)。
- WIFI代码
WIFI代码基本直接使用了esp-idf\examples\wifi\smart_config 工程。
smart_config的思路是利用手机给esp32配置WiFi。具体而言,手机先连接上WiFi(2.4Ghz),然后手机再使用EspTouch来将连接wifi所需要的信息(wifi名,密码)组包给wifi广播,esp32接收到广播后解包就可以得到所需的wifi信息,成功连接WiFi。
Esptouch手机界面如下:
EspTouch下载,Github搜索EspTouch,然后点击releases。
- SNTP代码
SNTP代码用于校正ESP32本地时间。
SNTP代码基于esp-idf\examples\protocols\sntp 工程修改而来。由于例程本身已经帮忙校正好了时间,因此代码修改的目标有两点:
1.得到已经校正好的时间。(位于esp32定义的系统时间结构体struct tm)
2.将校正好的时间展示在OLED上。
系统时间结构体struct tm定义如下代码段所示。其中包含了许多变量,但我们所关心的只是前面几个。
struct tm
{
int tm_sec;
int tm_min;
int tm_hour;
int tm_mday;
int tm_mon;
int tm_year;
int tm_wday;
int tm_yday;
int tm_isdst;
#ifdef __TM_GMTOFF
long __TM_GMTOFF;
#endif
#ifdef __TM_ZONE
const char *__TM_ZONE;
#endif
};
- Timer代码
Timer代码基于esp-idf\examples\system\esp_timer 工程修改而来。只需要在原工程的基础上把timer定时器的回调函数内容修改为SNTP代码中更新OLED时间的代码即可。
工程一共定义了两个Timer定时器,用于每隔一分钟更新时间数据到OLED屏幕上,一个是单次定时器,一个是周期定时器。周期定时器周期设定为一分钟,每隔一分钟启动一次更新OLED时间任务。单次定时器的仅在SNTP服务器校正时间后的第一分钟启动,在校正时间后的第一分钟并不需要完整等待一分钟后才进行更新OLED时间任务。例如从SNTP服务器获取时间为4点56分35秒,则单次定时器仅需定时60-35=25秒即可。
- HTTP 代码
HTTP代码用于访问丰富的网络API接口并得到返回的所需地理位置数据、天气数据。
HTTP代码基于C:\Users\M\Desktop\esp-idf\examples\protocols\esp_http_client修改而来。Esp32所给出的HTTP_Client例程展示了丰富的HTTP协议例子,这里仅仅用到了GET方法获取HTTP数据。
由于API接口返回的数据通常为CJSON数据结构,因此为了正确利用API返回的数据,首先应该对CJSON基础知识以及常用函数做一个相应的了解(自行百度)。
代码所用到的三个API接口如下:
1.获取地理位置信息API,该API通过分析数据报所走过的路由来得知ESP32的地理信息。API源于高德地图。我们所关心的是该API返回的经纬度。
https://restapi.amap.com/v3/ip?key=015ce8a4997fcb07ca81eccf5306902d
2.获取实时天气信息API,该API通过分析URL中的location变量(经纬度)来返回对应的实时天气信息。API源于心知天气。下面给出了查询北京实时天气的URL。
3.获取今明后天气信息API,该API通过分析URL中的location变量(经纬度)来返回对应的实时天气信息。API源于心知天气。下面给出了查询北京今明后天气的URL。
https://api.seniverse.com/v3/weather/daily.json?key=SUmWC7CegIIrYvj1w&language=en&unit=c&start=0&days=3&location=39.90:116.33
遇到的问题及解决方案
本次项目遇到的最大问题位于HTTP代码部分。由于我对HTTP协议并没有太多了解,也缺乏API,CJSON的相关知识,因此在编写代码时较为艰难。
所幸的是该项目对上述的知识要求并不高,可以说是仅仅接触皮毛即可,而且ESP32提供的HTTP_Client例程也比较详细。通过上网查阅HTTP协议GET,POST数据报的用法,以及CJSON的基础知识,结合各个API的返回值,经过一整天的奋战,终于鼓捣出了结果。
附件:工程文件下载链接:https://pan.baidu.com/s/1vI3ZCTsIbs3bf8KKvJyfRA
提取码:fkgz