113 lines
3.2 KiB
C
113 lines
3.2 KiB
C
|
/* LVGL Example project
|
||
|
*
|
||
|
* Basic project to test LVGL on ESP32 based projects.
|
||
|
*
|
||
|
* This example code is in the Public Domain (or CC0 licensed, at your option.)
|
||
|
*
|
||
|
* Unless required by applicable law or agreed to in writing, this
|
||
|
* software is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
|
||
|
* CONDITIONS OF ANY KIND, either express or implied.
|
||
|
*/
|
||
|
#include <stdbool.h>
|
||
|
#include <stdio.h>
|
||
|
#include <stdlib.h>
|
||
|
#include <string.h>
|
||
|
|
||
|
#include "freertos/FreeRTOS.h"
|
||
|
#include "freertos/task.h"
|
||
|
#include "esp_freertos_hooks.h"
|
||
|
#include "freertos/semphr.h"
|
||
|
|
||
|
|
||
|
#include "esp_system.h"
|
||
|
#include "driver/gpio.h"
|
||
|
|
||
|
/* Littlevgl specific */
|
||
|
#include "lvgl/lvgl.h"
|
||
|
#include "lvgl_driver.h"
|
||
|
//#include "lv_examples/lv_apps/demo/demo.h"
|
||
|
#include "lv_examples/lv_apps/sysmon/sysmon.h"
|
||
|
|
||
|
/*********************
|
||
|
* DEFINES
|
||
|
*********************/
|
||
|
|
||
|
/**********************
|
||
|
* STATIC PROTOTYPES
|
||
|
**********************/
|
||
|
static void IRAM_ATTR lv_tick_task(void *arg);
|
||
|
|
||
|
|
||
|
/**********************
|
||
|
* APPLICATION MAIN
|
||
|
**********************
|
||
|
void app_main() {
|
||
|
|
||
|
//If you want to use a task to create the graphic, you NEED to create a Pinned task
|
||
|
//Otherwise there can be problem such as memory corruption and so on
|
||
|
xTaskCreatePinnedToCore(guiTask, "gui", 4096*2, NULL, 0, NULL, 1);
|
||
|
}
|
||
|
**/
|
||
|
static void IRAM_ATTR lv_tick_task(void *arg) {
|
||
|
(void) arg;
|
||
|
|
||
|
lv_tick_inc(portTICK_RATE_MS);
|
||
|
}
|
||
|
|
||
|
//Creates a semaphore to handle concurrent call to lvgl stuff
|
||
|
//If you wish to call *any* lvgl function from other threads/tasks
|
||
|
//you should lock on the very same semaphore!
|
||
|
SemaphoreHandle_t xGuiSemaphore;
|
||
|
|
||
|
void guiTask() {
|
||
|
xGuiSemaphore = xSemaphoreCreateMutex();
|
||
|
|
||
|
lv_init();
|
||
|
|
||
|
lvgl_driver_init();
|
||
|
|
||
|
static lv_color_t buf1[DISP_BUF_SIZE];
|
||
|
static lv_color_t buf2[DISP_BUF_SIZE];
|
||
|
static lv_disp_buf_t disp_buf;
|
||
|
lv_disp_buf_init(&disp_buf, buf1, buf2, DISP_BUF_SIZE);
|
||
|
|
||
|
lv_disp_drv_t disp_drv;
|
||
|
lv_disp_drv_init(&disp_drv);
|
||
|
disp_drv.flush_cb = disp_driver_flush;
|
||
|
disp_drv.buffer = &disp_buf;
|
||
|
lv_disp_drv_register(&disp_drv);
|
||
|
|
||
|
#if CONFIG_LVGL_TOUCH_CONTROLLER != TOUCH_CONTROLLER_NONE
|
||
|
lv_indev_drv_t indev_drv;
|
||
|
lv_indev_drv_init(&indev_drv);
|
||
|
indev_drv.read_cb = touch_driver_read;
|
||
|
indev_drv.type = LV_INDEV_TYPE_POINTER;
|
||
|
lv_indev_drv_register(&indev_drv);
|
||
|
#endif
|
||
|
|
||
|
const esp_timer_create_args_t periodic_timer_args = {
|
||
|
.callback = &lv_tick_task,
|
||
|
/* name is optional, but may help identify the timer when debugging */
|
||
|
.name = "periodic_gui"
|
||
|
};
|
||
|
esp_timer_handle_t periodic_timer;
|
||
|
ESP_ERROR_CHECK(esp_timer_create(&periodic_timer_args, &periodic_timer));
|
||
|
//On ESP32 it's better to create a periodic task instead of esp_register_freertos_tick_hook
|
||
|
ESP_ERROR_CHECK(esp_timer_start_periodic(periodic_timer, 10*1000)); //10ms (expressed as microseconds)
|
||
|
|
||
|
//demo_create();
|
||
|
sysmon_create();
|
||
|
|
||
|
while (1) {
|
||
|
vTaskDelay(1);
|
||
|
//Try to lock the semaphore, if success, call lvgl stuff
|
||
|
if (xSemaphoreTake(xGuiSemaphore, (TickType_t)10) == pdTRUE) {
|
||
|
lv_task_handler();
|
||
|
xSemaphoreGive(xGuiSemaphore);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
//A task should NEVER return
|
||
|
vTaskDelete(NULL);
|
||
|
}
|