Multicore & Modularized
This commit is contained in:
parent
46734d537f
commit
9f6e80ff95
346
metesp.ino
346
metesp.ino
@ -5,7 +5,7 @@
|
|||||||
#include "src/epd/epd_driver.h"
|
#include "src/epd/epd_driver.h"
|
||||||
#include "src/epd/epd_paint.h"
|
#include "src/epd/epd_paint.h"
|
||||||
|
|
||||||
#include "src/ntpt/ntp.h"
|
#include "src/ntp/ntp.h"
|
||||||
#include "src/owm/owm.h"
|
#include "src/owm/owm.h"
|
||||||
|
|
||||||
#include "src/sensor/sensor.h"
|
#include "src/sensor/sensor.h"
|
||||||
@ -13,7 +13,11 @@
|
|||||||
|
|
||||||
#include "src/influxdb/influx.h"
|
#include "src/influxdb/influx.h"
|
||||||
|
|
||||||
|
#include "src/display/display.h"
|
||||||
|
#include "src/timedfun/timedfun.h"
|
||||||
|
|
||||||
#include <Arduino.h>
|
#include <Arduino.h>
|
||||||
|
|
||||||
#include <Wire.h>
|
#include <Wire.h>
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <WiFi.h>
|
#include <WiFi.h>
|
||||||
@ -25,83 +29,70 @@
|
|||||||
|
|
||||||
/* Global Variables -----------------------------------------------------------*/
|
/* Global Variables -----------------------------------------------------------*/
|
||||||
|
|
||||||
typedef enum {
|
|
||||||
VIEW_MAIN = 0,
|
|
||||||
VIEW_WEATHER_0, VIEW_WEATHER_1, VIEW_WEATHER_2, VIEW_WEATHER_3,
|
|
||||||
VIEW_TEMP, VIEW_AIR,
|
|
||||||
VIEW_CUSTOM,
|
|
||||||
|
|
||||||
VIEW_COUNT
|
|
||||||
} views_t;
|
|
||||||
|
|
||||||
static const uint8_t view_count = 5;
|
|
||||||
static uint8_t view_curr;
|
|
||||||
static const views_t view_tab[view_count] = {
|
|
||||||
VIEW_MAIN,
|
|
||||||
VIEW_WEATHER_0,VIEW_WEATHER_1,
|
|
||||||
VIEW_TEMP,VIEW_AIR
|
|
||||||
};
|
|
||||||
|
|
||||||
static WiFiMulti wifiMulti;
|
static WiFiMulti wifiMulti;
|
||||||
static TwoWire I2C = TwoWire(0);
|
static TwoWire I2C = TwoWire(0);
|
||||||
static strDateTime dateTime = {0};
|
|
||||||
|
|
||||||
|
static NTPtime* ntp = new NTPtime(NTP_URL);
|
||||||
static Sensor* sensor = new Sensor(&I2C);
|
static Sensor* sensor = new Sensor(&I2C);
|
||||||
static GT1151* touch = new GT1151(&I2C);
|
static GT1151* touch = new GT1151(&I2C);
|
||||||
static OWM* owm[6] = {new OWM(LOCATION_0, OPENWEATHER_API),
|
static OWM* owm[6] = {new OWM(LOCATION_0, OPENWEATHER_API),
|
||||||
new OWM(LOCATION_1, OPENWEATHER_API),
|
new OWM(LOCATION_1, OPENWEATHER_API),
|
||||||
new OWM(LOCATION_2, OPENWEATHER_API), 0,0,0};
|
new OWM(LOCATION_2, OPENWEATHER_API),
|
||||||
|
NULL,NULL,NULL};
|
||||||
|
|
||||||
static Influx* iflx = new Influx(NULL, owm);//add sensor
|
static Influx* iflx = new Influx(NULL, owm);//TODO: Add sensor
|
||||||
|
|
||||||
static NTPtime NTPch(NTP_URL);
|
|
||||||
static bool time_update = false,
|
|
||||||
ntp_update = true,
|
|
||||||
weather_update = true,
|
|
||||||
sensor_update = true,
|
|
||||||
influx_w_update = true, influx_s_update = true,
|
|
||||||
view_update = true, view_refresh = false;
|
|
||||||
|
|
||||||
|
static bool time_update = false, view_update = true, view_refresh = true;
|
||||||
static bool shutdownt = false;
|
static bool shutdownt = false;
|
||||||
static int shutdownc = 0;
|
static int shutdownc = 0;
|
||||||
|
|
||||||
uint8_t *BlackImage;
|
|
||||||
|
TaskHandle_t task_measure;
|
||||||
|
TaskHandle_t task_draw;
|
||||||
|
|
||||||
|
|
||||||
|
static TimedFun* tf = new TimedFun();
|
||||||
|
|
||||||
|
static const int8_t views_size = 5;
|
||||||
|
static DisplayWrapper* views[views_size] = {
|
||||||
|
new MainDisplay(),
|
||||||
|
new WeatherDisplay(owm[0]),
|
||||||
|
new WeatherDisplay(owm[1]),
|
||||||
|
new TempDisplay(sensor),
|
||||||
|
new AirDisplay(sensor)
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/* IRQ ------------------------------------------------------------------------*/
|
/* IRQ ------------------------------------------------------------------------*/
|
||||||
hw_timer_t * timer = NULL;
|
hw_timer_t * timer = NULL;
|
||||||
void IRAM_ATTR onSecondTimer() {
|
void IRAM_ATTR onSecondTimer() {
|
||||||
dateTime.second += 1;
|
strDateTime* dt = &(ntp->dt);
|
||||||
if (dateTime.second == 60) {
|
dt->second += 1;
|
||||||
dateTime.minute += 1;
|
if (dt->second == 60) {
|
||||||
dateTime.second = 0;
|
dt->minute += 1;
|
||||||
if (dateTime.minute == 60) {
|
dt->second = 0;
|
||||||
dateTime.hour += 1;
|
if (dt->minute == 60) {
|
||||||
dateTime.minute = 0;
|
dt->hour += 1;
|
||||||
if (dateTime.hour == 24) {
|
dt->minute = 0;
|
||||||
dateTime.hour = 0;
|
if (dt->hour == 24) {
|
||||||
dateTime.minute = 0;
|
dt->hour = 0;
|
||||||
dateTime.second = 0;
|
dt->minute = 0;
|
||||||
|
dt->second = 0;
|
||||||
}
|
}
|
||||||
ntp_update = true;
|
view_refresh =true;
|
||||||
}
|
}
|
||||||
if(dateTime.minute % 5) weather_update = true;
|
|
||||||
if(dateTime.minute % 5) sensor_update = true;
|
|
||||||
|
|
||||||
if(dateTime.minute % 5) influx_w_update = true;
|
|
||||||
if(dateTime.minute % 5) influx_s_update = true;
|
|
||||||
view_update = true;
|
view_update = true;
|
||||||
time_update = true;
|
time_update = true;
|
||||||
|
tf->minuteTick();
|
||||||
}
|
}
|
||||||
if(touch->dev.holding) shutdownc++;
|
if(touch->dev.holding) shutdownc++;
|
||||||
else shutdownc = 0;
|
else shutdownc = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void IRAM_ATTR onTouch(int8_t contacts, GTPoint *points) {
|
void IRAM_ATTR onTouch(int8_t contacts, GTPoint *points) {
|
||||||
if(touch->dev.holding) return;
|
if(touch->dev.holding) return;
|
||||||
Serial.printf("Contacts: %d\n", contacts);
|
Serial.printf("Contacts: %d\n", contacts);
|
||||||
@ -109,42 +100,14 @@ void IRAM_ATTR onTouch(int8_t contacts, GTPoint *points) {
|
|||||||
Serial.printf("C%d: #%d %d,%d s:%d\n", i, points[i].id, points[i].x, points[i].y, points[i].a);
|
Serial.printf("C%d: #%d %d,%d s:%d\n", i, points[i].id, points[i].x, points[i].y, points[i].a);
|
||||||
yield();
|
yield();
|
||||||
}
|
}
|
||||||
if(points[0].x < 125) view_curr = (++view_curr % view_count);
|
if(points[0].x < 125) Display::nextView();
|
||||||
else view_curr = (--view_curr % view_count);
|
else Display::prevView();
|
||||||
view_update = true;
|
view_update = true;
|
||||||
}
|
}
|
||||||
//x = 250 to 0
|
|
||||||
//y = ????
|
|
||||||
|
|
||||||
/* Setup Functions -----------------------------------------------------------*/
|
/* Setup Functions -----------------------------------------------------------*/
|
||||||
void setup_EPD(){
|
void setup_EPD(){
|
||||||
//START EPD
|
Display::setup();
|
||||||
DEV_Module_Init();
|
|
||||||
EPD_2IN13_V2_Init(EPD_2IN13_V2_FULL);
|
|
||||||
EPD_2IN13_V2_Clear();
|
|
||||||
delay(100);
|
|
||||||
|
|
||||||
//EPD STORAGE
|
|
||||||
uint16_t Imagesize = ((EPD_2IN13_V2_WIDTH % 8 == 0) ? (EPD_2IN13_V2_WIDTH / 8 ) : (EPD_2IN13_V2_WIDTH / 8 + 1)) * EPD_2IN13_V2_HEIGHT;
|
|
||||||
if ((BlackImage = (uint8_t *)malloc(Imagesize)) == NULL) exit(1);
|
|
||||||
Paint_NewImage(BlackImage, EPD_2IN13_V2_WIDTH, EPD_2IN13_V2_HEIGHT, 270, WHITE);
|
|
||||||
Paint_SelectImage(BlackImage);
|
|
||||||
Paint_SetMirroring(MIRROR_HORIZONTAL);
|
|
||||||
Paint_Clear(WHITE);
|
|
||||||
|
|
||||||
Paint_DrawIcon(89,54, ICON_LOGO, &FontIcon, BLACK, WHITE);
|
|
||||||
Paint_DrawString_EN(29, 5, "Helcel", &Font45, WHITE, BLACK);
|
|
||||||
Paint_SelectImage(BlackImage);
|
|
||||||
EPD_2IN13_V2_Display(BlackImage);
|
|
||||||
delay(100);
|
|
||||||
}
|
|
||||||
|
|
||||||
void setup_EPD_END(){
|
|
||||||
Paint_Clear(WHITE);
|
|
||||||
EPD_2IN13_V2_Init(EPD_2IN13_V2_FULL);
|
|
||||||
EPD_2IN13_V2_DisplayPartBaseImage(BlackImage);
|
|
||||||
EPD_2IN13_V2_Init(EPD_2IN13_V2_PART);
|
|
||||||
Paint_SelectImage(BlackImage);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void setup_TOUCH() {
|
void setup_TOUCH() {
|
||||||
@ -159,12 +122,28 @@ void setup_WIFI(){
|
|||||||
}
|
}
|
||||||
|
|
||||||
void setup_TIMER(){
|
void setup_TIMER(){
|
||||||
timer = timerBegin(0, 80, true);
|
timer = timerBegin(0, 80, true);
|
||||||
timerAttachInterrupt(timer, &onSecondTimer, true);
|
timerAttachInterrupt(timer, &onSecondTimer, true);
|
||||||
timerAlarmWrite(timer, 1000000, true);
|
timerAlarmWrite(timer, 1000000, true);
|
||||||
timerAlarmEnable(timer);
|
timerAlarmEnable(timer);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#define REGISTER_TIMEDFUN(name,code) static void name (){code;}
|
||||||
|
#define REGISTER_TIMEDFUN_CALL(name,min) tf->registerFun(name,min)
|
||||||
|
|
||||||
|
REGISTER_TIMEDFUN(SENSOR_MEASURE_TF, sensor->measure());
|
||||||
|
REGISTER_TIMEDFUN(OWM_MEASURE_TF, do{uint8_t i = 0;while(owm && owm[i]){owm[i]->update(); ++i;yield();}}while(0));
|
||||||
|
REGISTER_TIMEDFUN(RECORD_LOCAL_TF, iflx->record_local());
|
||||||
|
REGISTER_TIMEDFUN(RECORD_WEATHER_TF, iflx->record_weather());
|
||||||
|
REGISTER_TIMEDFUN(NTP_TF, ntp->updateNTPtime());
|
||||||
|
|
||||||
|
void setup_TIMEDFUN() {
|
||||||
|
REGISTER_TIMEDFUN_CALL(SENSOR_MEASURE_TF,5);
|
||||||
|
REGISTER_TIMEDFUN_CALL(OWM_MEASURE_TF,5);
|
||||||
|
REGISTER_TIMEDFUN_CALL(RECORD_LOCAL_TF,5);
|
||||||
|
REGISTER_TIMEDFUN_CALL(RECORD_WEATHER_TF,5);
|
||||||
|
REGISTER_TIMEDFUN_CALL(NTP_TF, 60);
|
||||||
|
}
|
||||||
|
|
||||||
/* Setup Functions --------------------------------------------------------------*/
|
/* Setup Functions --------------------------------------------------------------*/
|
||||||
void setup(){
|
void setup(){
|
||||||
@ -176,175 +155,58 @@ void setup(){
|
|||||||
setup_TOUCH();
|
setup_TOUCH();
|
||||||
setup_WIFI();
|
setup_WIFI();
|
||||||
setup_TIMER();
|
setup_TIMER();
|
||||||
|
setup_TIMEDFUN();
|
||||||
|
|
||||||
iflx->check();
|
iflx->check();
|
||||||
|
Display::setViews(views,views_size);
|
||||||
setup_EPD_END();
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* Update Functions-------------------------------------------------------------*/
|
tf->updateForce();
|
||||||
void updateNTP(){
|
|
||||||
if (!ntp_update) return;
|
|
||||||
if (wifiMulti.run() != WL_CONNECTED) return;
|
|
||||||
strDateTime nDateTime = NTPch.getNTPtime(1.0, 1);
|
|
||||||
if(nDateTime.valid){
|
|
||||||
dateTime = nDateTime;
|
|
||||||
time_update = true;
|
|
||||||
ntp_update = false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void updateWeather(){
|
xTaskCreatePinnedToCore(
|
||||||
if (!weather_update) return;
|
loop_MEASURE, "Task LMeasure",
|
||||||
if (wifiMulti.run() != WL_CONNECTED) return;
|
10000, NULL, 1, &task_measure, 0);
|
||||||
|
|
||||||
uint8_t i = 0, success = true;
|
xTaskCreatePinnedToCore(
|
||||||
while(owm && owm[i]){
|
loop_DRAW, "Task LDraw",
|
||||||
success &= owm[i]-> update();
|
10000, NULL, 1, &task_draw, 1);
|
||||||
++i;
|
|
||||||
}
|
|
||||||
if(success) weather_update = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
void updateTime(){
|
|
||||||
if (!time_update) return;
|
|
||||||
Paint_ClearWindows(170, EPD_2IN13_V2_WIDTH - Font24.Height, 170 + Font24.Width * 4.5, EPD_2IN13_V2_WIDTH, WHITE);
|
|
||||||
if (!dateTime.valid) return;
|
|
||||||
Paint_DrawTime(170, 98, &dateTime, &Font24, WHITE, BLACK);
|
|
||||||
EPD_2IN13_V2_DisplayPart(BlackImage);
|
|
||||||
time_update = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
void updateSensor(){
|
|
||||||
if (!sensor_update) return;
|
|
||||||
sensor->measure();
|
|
||||||
sensor_update = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
ICON_tpe getWeatherIcon(int id){
|
|
||||||
if(id>=200 && id<300){ //Thunder
|
|
||||||
return ICON_CLOUD_THUNDER;
|
|
||||||
}else if(id>=300 && id<400){//Drizzle
|
|
||||||
return ICON_CLOUD_RAIN;
|
|
||||||
}else if(id>=500 && id<600){//Rain
|
|
||||||
return ICON_CLOUD_RAIN;
|
|
||||||
}else if(id>=600 && id<700){//Snow
|
|
||||||
return ICON_CLOUD_SNOW;
|
|
||||||
}else if(id>=700 && id<800){//Warning
|
|
||||||
return ICON_WARN;
|
|
||||||
}else if(id>=800 && id<900){//Clear & Cloudy
|
|
||||||
if(id==800) return ICON_SUN;
|
|
||||||
else if(id==801) return ICON_CLOUD_SUN;
|
|
||||||
else return ICON_CLOUD;
|
|
||||||
}else{
|
|
||||||
return ICON_WARN;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void refreshDisplay(){
|
|
||||||
Paint_Clear(WHITE);
|
|
||||||
EPD_2IN13_V2_Init(EPD_2IN13_V2_FULL);
|
|
||||||
EPD_2IN13_V2_DisplayPartBaseImage(BlackImage);
|
|
||||||
EPD_2IN13_V2_Init(EPD_2IN13_V2_PART);
|
|
||||||
Paint_SelectImage(BlackImage);
|
|
||||||
}
|
|
||||||
|
|
||||||
OWM* viewToOWM(views_t view){
|
|
||||||
switch(view){
|
|
||||||
case VIEW_WEATHER_0: return owm[0];
|
|
||||||
case VIEW_WEATHER_1: return owm[1];
|
|
||||||
case VIEW_WEATHER_2: return owm[2];
|
|
||||||
case VIEW_WEATHER_3: return owm[3];
|
|
||||||
default: return NULL;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void updateDisplay(){
|
|
||||||
if (!view_update) return;
|
|
||||||
if (view_refresh) refreshDisplay();
|
|
||||||
Paint_ClearWindows(0, 0, EPD_2IN13_V2_HEIGHT, EPD_2IN13_V2_WIDTH - Font24.Height, WHITE);
|
|
||||||
Paint_ClearWindows(0, EPD_2IN13_V2_WIDTH - Font24.Height, 170, EPD_2IN13_V2_WIDTH, WHITE);
|
|
||||||
switch(view_tab[view_curr]){
|
|
||||||
case VIEW_MAIN:
|
|
||||||
Paint_DrawIcon(0,0, ICON_LOGO,&FontIcon, BLACK, WHITE);
|
|
||||||
Paint_DrawString_EN(60,0,"MAIN", &Font24, WHITE, BLACK);
|
|
||||||
Paint_DrawIntUnit(0,30, 69,"", &Font24, BLACK, WHITE);
|
|
||||||
break;
|
|
||||||
case VIEW_WEATHER_0:
|
|
||||||
case VIEW_WEATHER_1:
|
|
||||||
case VIEW_WEATHER_2:
|
|
||||||
case VIEW_WEATHER_3:
|
|
||||||
{
|
|
||||||
OWM* cowm = viewToOWM(view_tab[view_curr]);
|
|
||||||
if(cowm == NULL || !cowm->valid_weather) break;
|
|
||||||
JsonObject weather_0 = cowm->weather["weather"][0];
|
|
||||||
JsonObject weather_main = cowm->weather["main"];
|
|
||||||
JsonObject weather_wind = cowm->weather["wind"];
|
|
||||||
JsonObject weather_sys = cowm->weather["sys"];
|
|
||||||
if(!weather_0 || !weather_main || !weather_sys || !weather_wind) break;
|
|
||||||
Paint_DrawIcon(0,8, getWeatherIcon(weather_0["id"]), &FontIcon, BLACK, WHITE);
|
|
||||||
Paint_DrawString_EN(2,EPD_2IN13_V2_WIDTH - 4 - Font16.Height,weather_0["description"], &Font16, WHITE, BLACK);
|
|
||||||
Paint_DrawFltUnit(76,0,weather_main["temp"], "C", &Font24, BLACK, WHITE);
|
|
||||||
Paint_DrawFltUnit(186,6,weather_main["feels_like"], "C", &Font12, BLACK, WHITE);
|
|
||||||
Paint_DrawIntUnit(76,24,weather_main["pressure"], "hPa", &Font24, BLACK, WHITE);
|
|
||||||
Paint_DrawIntUnit(76,48,weather_main["humidity"], "%", &Font24, BLACK, WHITE);
|
|
||||||
Paint_DrawFltUnit(76,72,weather_wind["speed"], "m/s", &Font24, BLACK, WHITE);
|
|
||||||
strDateTime sunrisedt = NTPtime::ConvertUnixTimestamp(NTPtime::adjustTimeZone(weather_sys["sunrise"], 1.0, 1));
|
|
||||||
strDateTime sunsetdt = NTPtime::ConvertUnixTimestamp(NTPtime::adjustTimeZone(weather_sys["sunset"], 1.0, 1));
|
|
||||||
Paint_DrawTime(20, 6, &sunrisedt, &Font12, WHITE, BLACK);
|
|
||||||
Paint_DrawTime(20, 76, &sunsetdt, &Font12, WHITE, BLACK);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case VIEW_TEMP:
|
|
||||||
Paint_DrawIcon(0,Font24.Height, ICON_TEMPERATURE,&FontIcon, BLACK, WHITE);
|
|
||||||
Paint_DrawString_EN(2,0,"Temp", &Font24, WHITE, BLACK);
|
|
||||||
Paint_DrawFltUnit(76,0,sensor->heatidx, "C", &Font24, BLACK, WHITE);
|
|
||||||
Paint_DrawFltUnit(76,36,sensor->temp, "C", &Font24, BLACK, WHITE);
|
|
||||||
Paint_DrawFltUnit(160,36,sensor->hum, "%", &Font24, BLACK, WHITE);
|
|
||||||
Paint_DrawFltUnit(76,64,sensor->pres, "hPa", &Font24, BLACK, WHITE);
|
|
||||||
break;
|
|
||||||
case VIEW_AIR:
|
|
||||||
Paint_DrawIcon(0,Font24.Height, ICON_POLUTION,&FontIcon, BLACK, WHITE);
|
|
||||||
Paint_DrawString_EN(2,0,"Air", &Font24, WHITE, BLACK);
|
|
||||||
Paint_DrawIntUnit(150,10, 69,"", &Font24, BLACK, WHITE);
|
|
||||||
break;
|
|
||||||
case VIEW_CUSTOM:
|
|
||||||
Paint_DrawString_EN(60,0,"CUSTOM", &Font24, WHITE, BLACK);
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
EPD_2IN13_V2_DisplayPart(BlackImage);
|
|
||||||
view_update = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
void updateInflux(){
|
|
||||||
if(wifiMulti.run() != WL_CONNECTED) return;
|
|
||||||
iflx->record(influx_w_update, influx_s_update);
|
|
||||||
influx_w_update = false;
|
|
||||||
influx_s_update = false;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/* The main loop -------------------------------------------------------------*/
|
/* The main loop -------------------------------------------------------------*/
|
||||||
void loop(){
|
void loop(){
|
||||||
if(shutdownc >= 10){
|
delay(5000);
|
||||||
refreshDisplay();
|
yield();
|
||||||
EPD_2IN13_V2_Sleep();
|
}
|
||||||
esp_deep_sleep_start();
|
|
||||||
}
|
void loop_DRAW(void * pvParameters ){
|
||||||
|
for(;;){
|
||||||
updateNTP();
|
touch->update();
|
||||||
updateWeather();
|
if(shutdownc >= 10){
|
||||||
updateSensor();
|
Display::refresh();
|
||||||
updateInflux();
|
EPD_2IN13_V2_Sleep();
|
||||||
|
esp_deep_sleep_start();
|
||||||
touch->update();
|
}
|
||||||
updateDisplay();
|
if(!touch->dev.holding) shutdownc = 0;
|
||||||
updateTime();
|
|
||||||
delay(50);
|
if(view_refresh) Display::refresh();
|
||||||
if(!touch->dev.holding) shutdownc = 0;
|
if(view_update) Display::update();
|
||||||
|
if(time_update) Display::drawTime(&(ntp->dt));
|
||||||
|
|
||||||
|
view_refresh = false;
|
||||||
|
view_update = false;
|
||||||
|
time_update = false;
|
||||||
|
yield();
|
||||||
|
vTaskDelay(10);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void loop_MEASURE(void * pvParameters ){
|
||||||
|
for(;;){
|
||||||
|
tf->update();
|
||||||
|
yield();
|
||||||
|
vTaskDelay(10);
|
||||||
|
}
|
||||||
}
|
}
|
127
src/display/display.cpp
Normal file
127
src/display/display.cpp
Normal file
@ -0,0 +1,127 @@
|
|||||||
|
#include "display.h"
|
||||||
|
|
||||||
|
|
||||||
|
uint8_t *BlackImage = 0;
|
||||||
|
|
||||||
|
|
||||||
|
static int8_t view_count = -1;
|
||||||
|
static int8_t view_curr = 0;
|
||||||
|
static DisplayWrapper** views = 0;
|
||||||
|
|
||||||
|
void Display::setup(){
|
||||||
|
DEV_Module_Init();
|
||||||
|
EPD_2IN13_V2_Init(EPD_2IN13_V2_FULL);
|
||||||
|
EPD_2IN13_V2_Clear();
|
||||||
|
delay(100);
|
||||||
|
|
||||||
|
uint16_t Imagesize = ((EPD_2IN13_V2_WIDTH % 8 == 0) ? (EPD_2IN13_V2_WIDTH / 8 ) : (EPD_2IN13_V2_WIDTH / 8 + 1)) * EPD_2IN13_V2_HEIGHT;
|
||||||
|
if ((BlackImage = (uint8_t *)malloc(Imagesize)) == NULL) exit(1);
|
||||||
|
Paint_NewImage(BlackImage, EPD_2IN13_V2_WIDTH, EPD_2IN13_V2_HEIGHT, 270, WHITE);
|
||||||
|
Paint_SelectImage(BlackImage);
|
||||||
|
Paint_SetMirroring(MIRROR_HORIZONTAL);
|
||||||
|
Paint_Clear(WHITE);
|
||||||
|
|
||||||
|
Paint_DrawIcon(89,54, ICON_LOGO, &FontIcon, BLACK, WHITE);
|
||||||
|
Paint_DrawString_EN(29, 5, "Helcel", &Font45, WHITE, BLACK);
|
||||||
|
Paint_SelectImage(BlackImage);
|
||||||
|
EPD_2IN13_V2_Display(BlackImage);
|
||||||
|
delay(100);
|
||||||
|
}
|
||||||
|
|
||||||
|
void Display::drawTime(strDateTime* dt){
|
||||||
|
Paint_ClearWindows(170, EPD_2IN13_V2_WIDTH - Font24.Height, 170 + Font24.Width * 4.5, EPD_2IN13_V2_WIDTH, WHITE);
|
||||||
|
if (!dt->valid) return;
|
||||||
|
Paint_DrawTime(170, 98, dt, &Font24, WHITE, BLACK);
|
||||||
|
EPD_2IN13_V2_DisplayPart(BlackImage);
|
||||||
|
};
|
||||||
|
|
||||||
|
void Display::refresh(){
|
||||||
|
Paint_Clear(WHITE);
|
||||||
|
EPD_2IN13_V2_Init(EPD_2IN13_V2_FULL);
|
||||||
|
EPD_2IN13_V2_DisplayPartBaseImage(BlackImage);
|
||||||
|
EPD_2IN13_V2_Init(EPD_2IN13_V2_PART);
|
||||||
|
Paint_SelectImage(BlackImage);
|
||||||
|
};
|
||||||
|
|
||||||
|
void Display::update(){
|
||||||
|
Paint_ClearWindows(0, 0, EPD_2IN13_V2_HEIGHT, EPD_2IN13_V2_WIDTH - Font24.Height, WHITE);
|
||||||
|
Paint_ClearWindows(0, EPD_2IN13_V2_WIDTH - Font24.Height, 170, EPD_2IN13_V2_WIDTH, WHITE);
|
||||||
|
if(views && view_curr >=0)
|
||||||
|
views[view_curr]->drawDisplay();
|
||||||
|
EPD_2IN13_V2_DisplayPart(BlackImage);
|
||||||
|
}
|
||||||
|
|
||||||
|
void Display::setViews(DisplayWrapper** view_tab, int8_t size){
|
||||||
|
view_count = size;
|
||||||
|
views = view_tab;
|
||||||
|
};
|
||||||
|
|
||||||
|
void Display::nextView(){ view_curr++; view_curr = view_curr%view_count;}
|
||||||
|
void Display::prevView(){ view_curr--; view_curr = (view_curr+view_count) % view_count;}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
ICON_tpe getWeatherIcon(int id){
|
||||||
|
if(id>=200 && id<300){ //Thunder
|
||||||
|
return ICON_CLOUD_THUNDER;
|
||||||
|
}else if(id>=300 && id<400){//Drizzle
|
||||||
|
return ICON_CLOUD_RAIN;
|
||||||
|
}else if(id>=500 && id<600){//Rain
|
||||||
|
return ICON_CLOUD_RAIN;
|
||||||
|
}else if(id>=600 && id<700){//Snow
|
||||||
|
return ICON_CLOUD_SNOW;
|
||||||
|
}else if(id>=700 && id<800){//Warning
|
||||||
|
return ICON_WARN;
|
||||||
|
}else if(id>=800 && id<900){//Clear & Cloudy
|
||||||
|
if(id==800) return ICON_SUN;
|
||||||
|
else if(id==801) return ICON_CLOUD_SUN;
|
||||||
|
else return ICON_CLOUD;
|
||||||
|
}else{
|
||||||
|
return ICON_WARN;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void WeatherDisplay::drawDisplay() {
|
||||||
|
if(cowm == NULL || !cowm->valid_weather) return;
|
||||||
|
JsonObject weather_0 = cowm->weather["weather"][0];
|
||||||
|
JsonObject weather_main = cowm->weather["main"];
|
||||||
|
JsonObject weather_wind = cowm->weather["wind"];
|
||||||
|
JsonObject weather_sys = cowm->weather["sys"];
|
||||||
|
if(!weather_0 || !weather_main || !weather_sys || !weather_wind) return;
|
||||||
|
Paint_DrawIcon(0,8, getWeatherIcon(weather_0["id"]), &FontIcon, BLACK, WHITE);
|
||||||
|
Paint_DrawString_EN(2,EPD_2IN13_V2_WIDTH - 4 - Font16.Height,weather_0["description"], &Font16, WHITE, BLACK);
|
||||||
|
Paint_DrawFltUnit(76,0,weather_main["temp"], "C", &Font24, BLACK, WHITE);
|
||||||
|
Paint_DrawFltUnit(186,6,weather_main["feels_like"], "C", &Font12, BLACK, WHITE);
|
||||||
|
Paint_DrawIntUnit(76,24,weather_main["pressure"], "hPa", &Font24, BLACK, WHITE);
|
||||||
|
Paint_DrawIntUnit(76,48,weather_main["humidity"], "%", &Font24, BLACK, WHITE);
|
||||||
|
Paint_DrawFltUnit(76,72,weather_wind["speed"], "m/s", &Font24, BLACK, WHITE);
|
||||||
|
strDateTime sunrisedt = NTPtime::ConvertUnixTimestamp(NTPtime::adjustTimeZone(weather_sys["sunrise"], 1.0, 1));
|
||||||
|
strDateTime sunsetdt = NTPtime::ConvertUnixTimestamp(NTPtime::adjustTimeZone(weather_sys["sunset"], 1.0, 1));
|
||||||
|
Paint_DrawTime(20, 6, &sunrisedt, &Font12, WHITE, BLACK);
|
||||||
|
Paint_DrawTime(20, 76, &sunsetdt, &Font12, WHITE, BLACK);
|
||||||
|
}
|
||||||
|
|
||||||
|
void TempDisplay::drawDisplay() {
|
||||||
|
Paint_DrawIcon(0,Font24.Height, ICON_TEMPERATURE,&FontIcon, BLACK, WHITE);
|
||||||
|
Paint_DrawString_EN(2,0,"Temp", &Font24, WHITE, BLACK);
|
||||||
|
Paint_DrawFltUnit(76,0,sensor->heatidx, "C", &Font24, BLACK, WHITE);
|
||||||
|
Paint_DrawFltUnit(76,36,sensor->temp, "C", &Font24, BLACK, WHITE);
|
||||||
|
Paint_DrawFltUnit(160,36,sensor->hum, "%", &Font24, BLACK, WHITE);
|
||||||
|
Paint_DrawFltUnit(76,64,sensor->pres, "hPa", &Font24, BLACK, WHITE);
|
||||||
|
}
|
||||||
|
|
||||||
|
void AirDisplay::drawDisplay() {
|
||||||
|
Paint_DrawIcon(0,Font24.Height, ICON_POLUTION,&FontIcon, BLACK, WHITE);
|
||||||
|
Paint_DrawString_EN(2,0,"Air", &Font24, WHITE, BLACK);
|
||||||
|
Paint_DrawIntUnit(150,10, 69,"", &Font24, BLACK, WHITE);
|
||||||
|
}
|
||||||
|
|
||||||
|
void MainDisplay::drawDisplay() {
|
||||||
|
Paint_DrawIcon(0,0, ICON_LOGO,&FontIcon, BLACK, WHITE);
|
||||||
|
Paint_DrawString_EN(60,0,"MAIN", &Font24, WHITE, BLACK);
|
||||||
|
Paint_DrawIntUnit(0,30, 69,"", &Font24, BLACK, WHITE);
|
||||||
|
}
|
||||||
|
|
||||||
|
void CustomDisplay::drawDisplay() {
|
||||||
|
Paint_DrawString_EN(60,0,"CUSTOM", &Font24, WHITE, BLACK);
|
||||||
|
}
|
74
src/display/display.h
Normal file
74
src/display/display.h
Normal file
@ -0,0 +1,74 @@
|
|||||||
|
#ifndef TG_DISPLAY_H
|
||||||
|
#define TG_DISPLAY_H
|
||||||
|
|
||||||
|
#include "../epd/epd_cfg.h"
|
||||||
|
#include "../epd/epd_driver.h"
|
||||||
|
#include "../epd/epd_paint.h"
|
||||||
|
|
||||||
|
|
||||||
|
#include "../ntp/ntp.h"
|
||||||
|
#include "../owm/owm.h"
|
||||||
|
#include "../sensor/sensor.h"
|
||||||
|
|
||||||
|
|
||||||
|
#include <Arduino.h>
|
||||||
|
#include <Wire.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <WiFi.h>
|
||||||
|
#include <WiFiMulti.h>
|
||||||
|
class DisplayWrapper {
|
||||||
|
public:
|
||||||
|
virtual void drawDisplay();
|
||||||
|
};
|
||||||
|
|
||||||
|
class Display {
|
||||||
|
public:
|
||||||
|
static void setup();
|
||||||
|
static void drawTime(strDateTime* dt);
|
||||||
|
static void refresh();
|
||||||
|
static void update();
|
||||||
|
static void setViews(DisplayWrapper** views, int8_t size);
|
||||||
|
|
||||||
|
static void nextView();
|
||||||
|
static void prevView();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
class WeatherDisplay: public DisplayWrapper {
|
||||||
|
public:
|
||||||
|
WeatherDisplay(OWM* o) : cowm(o){}
|
||||||
|
void drawDisplay();
|
||||||
|
private:
|
||||||
|
OWM* cowm;
|
||||||
|
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
class TempDisplay: public DisplayWrapper {
|
||||||
|
public:
|
||||||
|
TempDisplay(Sensor* s) : sensor(s){}
|
||||||
|
void drawDisplay();
|
||||||
|
private:
|
||||||
|
Sensor* sensor;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
class AirDisplay: public DisplayWrapper {
|
||||||
|
public:
|
||||||
|
AirDisplay(Sensor* s) : sensor(s){}
|
||||||
|
void drawDisplay();
|
||||||
|
private:
|
||||||
|
Sensor* sensor;
|
||||||
|
};
|
||||||
|
|
||||||
|
class MainDisplay: public DisplayWrapper {
|
||||||
|
public:
|
||||||
|
void drawDisplay();
|
||||||
|
};
|
||||||
|
|
||||||
|
class CustomDisplay: public DisplayWrapper {
|
||||||
|
public:
|
||||||
|
void drawDisplay();
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
@ -4,7 +4,7 @@
|
|||||||
#include "debug.h"
|
#include "debug.h"
|
||||||
#include "epd_cfg.h"
|
#include "epd_cfg.h"
|
||||||
#include "fonts/fonts.h"
|
#include "fonts/fonts.h"
|
||||||
#include "../time/time.h"
|
#include "../ntp/ntp.h"
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Image attributes
|
* Image attributes
|
||||||
|
@ -118,6 +118,10 @@ class Influx {
|
|||||||
client.writePoint(dp);
|
client.writePoint(dp);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void record_weather(){
|
||||||
|
record(true,false);
|
||||||
|
}
|
||||||
|
|
||||||
void record_weather(OWM* owm){
|
void record_weather(OWM* owm){
|
||||||
if(!owm) return;
|
if(!owm) return;
|
||||||
if(!owm->valid_weather) return;
|
if(!owm->valid_weather) return;
|
||||||
|
@ -223,3 +223,9 @@ strDateTime NTPtime::getNTPtime(float _timeZone, boolean _DayLightSaving) {
|
|||||||
|
|
||||||
return _dateTime;
|
return _dateTime;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void NTPtime::updateNTPtime(){
|
||||||
|
strDateTime ndt = getNTPtime(1.0f, true);
|
||||||
|
if(ndt.valid) dt = ndt;
|
||||||
|
};
|
@ -2,22 +2,38 @@
|
|||||||
#define NTPtime_h
|
#define NTPtime_h
|
||||||
|
|
||||||
#include <WiFiUdp.h>
|
#include <WiFiUdp.h>
|
||||||
#include "../time/time.h"
|
|
||||||
|
struct strDateTime {
|
||||||
|
byte hour;
|
||||||
|
byte minute;
|
||||||
|
byte second;
|
||||||
|
int year;
|
||||||
|
byte month;
|
||||||
|
byte day;
|
||||||
|
byte dayofWeek;
|
||||||
|
boolean valid;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
class NTPtime {
|
class NTPtime {
|
||||||
public:
|
public:
|
||||||
NTPtime(String NTPtime);
|
NTPtime(String NTPtime);
|
||||||
|
strDateTime dt = {0};
|
||||||
|
|
||||||
strDateTime getNTPtime(float _timeZone, boolean _DayLightSaving);
|
strDateTime getNTPtime(float _timeZone, boolean _DayLightSaving);
|
||||||
|
|
||||||
|
void updateNTPtime();
|
||||||
|
|
||||||
bool setSendInterval(unsigned long _sendInterval); // in seconds
|
bool setSendInterval(unsigned long _sendInterval); // in seconds
|
||||||
bool setRecvTimeout(unsigned long _recvTimeout); // in seconds
|
bool setRecvTimeout(unsigned long _recvTimeout); // in seconds
|
||||||
|
|
||||||
|
|
||||||
static boolean summerTime(unsigned long _timeStamp );
|
static boolean summerTime(unsigned long _timeStamp );
|
||||||
static strDateTime ConvertUnixTimestamp( unsigned long _tempTimeStamp);
|
static strDateTime ConvertUnixTimestamp( unsigned long _tempTimeStamp);
|
||||||
static boolean daylightSavingTime(unsigned long _timeStamp);
|
static boolean daylightSavingTime(unsigned long _timeStamp);
|
||||||
static unsigned long adjustTimeZone(unsigned long _timeStamp, float _timeZone, byte _DayLightSavingSaving);
|
static unsigned long adjustTimeZone(unsigned long _timeStamp, float _timeZone, byte _DayLightSavingSaving);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
|
||||||
bool _sendPhase;
|
bool _sendPhase;
|
||||||
unsigned long _sentTime;
|
unsigned long _sentTime;
|
||||||
unsigned long _sendInterval;
|
unsigned long _sendInterval;
|
@ -1,16 +0,0 @@
|
|||||||
#ifndef time_h
|
|
||||||
#define time_h
|
|
||||||
|
|
||||||
struct strDateTime
|
|
||||||
{
|
|
||||||
byte hour;
|
|
||||||
byte minute;
|
|
||||||
byte second;
|
|
||||||
int year;
|
|
||||||
byte month;
|
|
||||||
byte day;
|
|
||||||
byte dayofWeek;
|
|
||||||
boolean valid;
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif
|
|
53
src/timedfun/timedfun.h
Normal file
53
src/timedfun/timedfun.h
Normal file
@ -0,0 +1,53 @@
|
|||||||
|
|
||||||
|
|
||||||
|
#ifndef TG_TIMEDFUN_H
|
||||||
|
#define TG_TIMEDFUN_H
|
||||||
|
|
||||||
|
#include <map>
|
||||||
|
#include <stdint.h>
|
||||||
|
#include <Arduino.h>
|
||||||
|
|
||||||
|
typedef void (*timedfun_ptr)();
|
||||||
|
|
||||||
|
class TimedFun {
|
||||||
|
public:
|
||||||
|
TimedFun(){};
|
||||||
|
|
||||||
|
void registerFun(timedfun_ptr p, uint64_t s){
|
||||||
|
funmap[p] = s;
|
||||||
|
};
|
||||||
|
|
||||||
|
void registerFunCond(timedfun_ptr p, uint64_t s){
|
||||||
|
funmap[p] = s;
|
||||||
|
};
|
||||||
|
|
||||||
|
void minuteTick(){
|
||||||
|
++counter;
|
||||||
|
}
|
||||||
|
|
||||||
|
void update(){
|
||||||
|
for (const auto &e : funmap){
|
||||||
|
if((counter % e.second == 0) ||
|
||||||
|
((counter-old_counter) >= e.second) ||
|
||||||
|
((counter%e.second) < (old_counter%e.second))){
|
||||||
|
e.first();
|
||||||
|
yield();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
old_counter = counter;
|
||||||
|
};
|
||||||
|
|
||||||
|
void updateForce(){
|
||||||
|
for (const auto &e : funmap){
|
||||||
|
e.first();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
uint64_t counter = 0;
|
||||||
|
uint64_t old_counter = 0;
|
||||||
|
std::map<timedfun_ptr,uint64_t> funmap;
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
Loading…
x
Reference in New Issue
Block a user