Funpack第12期-基于Wio Terminal的联网天气预报仪
本项目基于Wio Terminal开发平台,通过板载WIFI模块联网,使用和风天气提供的免费API获取实时天气、空气质量及未来三天的变化情况,然后通过LVGL GUI在屏幕上进行显示。
标签
嵌入式系统
Funpack参赛
物联网
wio terminal
launcher
更新2021-12-29
1001
实现功能:
本项目基于Wio Terminal开发平台,通过板载WIFI模块联网,使用和风天气提供的免费API获取实时天气、空气质量及未来三天的变化情况,然后通过LVGL GUI在屏幕上进行显示。
 
项目来源

Funpack 第12期,任务二:

制作一个自动联网的天气预报仪,在设计界面显示温湿度、天气情况、空气质量以及未来三天内的天气变化。

本项目完成效果如下:

tab12

方案设计

Wio Terminal板载资源丰富,无需而外硬件资源,便可以完成联网、显示功能了,因而该项目关键在于找到合适的天气API。选择和风天气API的原因是:

  1. 免费且门槛低,普通免费用户既可有1000次/天的请求额度。
  2. 满足题目需求,普通免费用户既可获取实时天气温湿度、空气质量、未来3天的天气预报。
  3. 有Arduino平台参考软件库,开发简单。
  4. 提供了天气图标字体库,可以很方便的进行天气图标显示。
开发平台
  • 硬件平台:Wio Terminal
  • 软件环境:VS Code / Arduino
联网方案
  • 硬件:板载WIFI模块
  • 软件库:rpcWifi / WiFiClientSecure
天气API 显示方案
  • 硬件:板载2.4寸LCD
  • GUI库:LVGL

方案实现

WIFI联网

  1. 更新最新WIFI固件

    按照Seed官方WIKI步骤操作升级最新WIFI固件

  2. 联网代码

    1
    2
    3
    4
    5
    WiFi.mode(WIFI_STA);
    WiFi.disconnect();

    Serial.println("Connecting to wifi...");
    WiFi.begin(ssid,password);

LVGL初始化

  1. TFT初始化

    1
    2
    tft.begin(); /* TFT init */
    tft.setRotation(3); /* Landscape orientation */
  2. LVGL初始化

    • 实现LVGL缓存刷新到TFT函数
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    /* Display flushing */
    void my_disp_flush(lv_disp_drv_t *disp, const lv_area_t *area, lv_color_t *color_p)
    {
    uint16_t c;

    tft.startWrite(); /* Start new TFT transaction */
    tft.setAddrWindow(area->x1, area->y1, (area->x2 - area->x1 + 1), (area->y2 - area->y1 + 1)); /* set the working window */
    for (int y = area->y1; y <= area->y2; y++) {
    for (int x = area->x1; x <= area->x2; x++) {
    c = color_p->full;
    tft.writeColor(c, 1);
    color_p++;
    }
    }
    tft.endWrite(); /* terminate TFT transaction */
    lv_disp_flush_ready(disp); /* tell lvgl that flushing is done */
    }
    • 初始化LVGL相关参数
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    lv_init();

    lv_disp_buf_init(&disp_buf, buf, NULL, LV_HOR_RES_MAX * 10);

    /*Initialize the display*/
    lv_disp_drv_t disp_drv;
    lv_disp_drv_init(&disp_drv);
    disp_drv.hor_res = 320;
    disp_drv.ver_res = 240;
    disp_drv.flush_cb = my_disp_flush;
    disp_drv.buffer = &disp_buf;
    lv_disp_drv_register(&disp_drv);
    • 启动一个5ms定时器中断,用于执行LVGL定时任务。
    1
    2
    TimerTc3.initialize(5000);//5ms
    TimerTc3.attachInterrupt(lv_timer_int_handler);
    • 定时中断中执行如下LVGL任务
    1
    2
    3
    4
    5
    void lv_timer_int_handler(void)
    {
    lv_tick_handler();
    lv_task_handler(); /* let the GUI do its work */
    }

    这样做的好处是,你可以只管更新LVGL的组件、显示内容,在主循环中可以正常使用delay函数,而无需担心影响LVGL的显示刷新。

主循环

界面的整体UI,我使用的是LVGL建立了1个TableView,添加了3个标签。其中标签1用于显示当前实时天气、温湿度、空气质量,标签2用于显示未来三天天气变化,标签3则用于显示了项目源代码获取方式。

所以主循环事情则比较简单,主要处理:

  1. 处理按键,切换TableView各个标签的显示
  2. 每隔5分钟调用API更新天气信息,并更新到UI中
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
void loop(){
// put your main code here, to run repeatedly
key_press_handler();
delay(5);
update_timeout_cnt += 5;
if(update_timeout_cnt >= UPDATE_TIMEOUT)
{
update_timeout_cnt = 0;
weatherNow.get();
airquality.get();
weatherForecast.get();
airquality_get = airquality.getAqi();
weathernow_info_update_to_ui(weatherNow.getLastUpdate(),String(weatherNow.getTemp()),...);
weatherforecast_info_update_to_ui(weatherForecast.getFxDate(0),weatherForecast.getIconDay(0),...);
}
}

心得体会:

感谢电子森林提供的本次学习机会,感恩~

附件下载
SmartWeather-Launcher.zip
本项目完整源代码
团队介绍
个人昵称:launcher; 个人主页:www.ETRD.org
团队成员
launcher
评论
0 / 100
查看更多
目录
硬禾服务号
关注最新动态
0512-67862536
info@eetree.cn
江苏省苏州市苏州工业园区新平街388号腾飞创新园A2幢815室
苏州硬禾信息科技有限公司
Copyright © 2024 苏州硬禾信息科技有限公司 All Rights Reserved 苏ICP备19040198号