LVGL8.3 集成 ST7789V 显示驱动和 CST816T 触摸屏驱动

news2024/9/26 1:24:32

LVGL8.3 集成 ST7789V 显示驱动和 CTS816S 触摸屏驱动

  • 起因
  • 效果(正常显示,触摸屏可调换X,Y轴)
  • 使用方式
    • 前提
    • 操作步骤
    • 最后
    • 参考

起因

LVGLESP32 Drivers库中已经包含了大多数显示和触摸芯片的驱动,基本上只需要在MenuConfig中选择即可,大大方便了屏幕适配工作。最近在一个项目中,屏幕总成使用的屏幕是ST7789V芯片和CST816T芯片。虽然给了对应Ardunio的驱动,但是在使用ESP-IDF进行开发时,还是需要进行一些简单的移植工作的。

效果(正常显示,触摸屏可调换X,Y轴)

在这里插入图片描述

使用方式

前提

  • 已经掌握了ESP-IDF点灯编程技能
  • 已经可以集成LVGL并正常显示demo。

操作步骤

那么,与集成LVGL_ESP32_Drivers 的方式相同。
GITEE: https://gitee.com/exp-pi/lvgl_esp32_drivers

  1. 从以上Git仓库 Clone代码到 ESP-IDF 项目中的 components文件夹下。
    在这里插入图片描述

  2. 修改 lvgl_esp32_drivers/lvgl_helpers.h 文件。定义最大的宽度高度,如我使用的屏幕是240x280。
    在这里插入图片描述

#define LV_HOR_RES_MAX 240
#define LV_VER_RES_MAX 280
  1. TFT屏幕的设置
    • 打开MenuConfig。在LVGL configuration 中的 “Color Settings”,Color depth 选择 RGB565
    • 勾选 Swap the 2 bytes of RGB565 color. Useful if the display has an 8-bit interface (e.g. SPI).
    • 在 LVGL TFT Display controller 中 “Select a display controller model.” 选择 “ST7789V”
    • 勾选 “Invert colors in display”
      在这里插入图片描述
      在这里插入图片描述

注意:如果没有勾选“Swap the 2 bytes of RGB565 color. Useful if the display has an 8-bit interface (e.g. SPI).” 和 “Invert colors in display”,会导致色彩不对,如:偏色、反色,重影

  1. 触摸屏的设置
  • 在“LVGL Touch controller” 选择 “CTS816T”
  • Touchpanel Configuration (CST816T) 下 对调 X、Y轴,或单一翻转X、Y轴的设置可根据自己需求选择。
    在这里插入图片描述
  1. 测试验证,以下代码保存为 main.c 文件,编译、烧录。如果接线正确的话,应该就可以看到效果了。
#include <stdio.h>
#include "freertos/FreeRTOS.h"
#include "freertos/event_groups.h"
#include "lvgl.h"
#include "freertos/semphr.h"
#include "esp_system.h"
#include "lvgl_helpers.h"
#include <esp_log.h>
 
/*********************
 *      DEFINES
 *********************/
#define LV_TICK_PERIOD_MS 1
 
/**********************
 *  STATIC PROTOTYPES
 **********************/
static void lv_tick_task(void *arg);
static void guiTask(void *pvParameter);
static void create_demo_application(void);
 
/**********************
 *   APPLICATION MAIN
 **********************/
void app_main(void)
{
    // xTaskCreate(guiTask, "gui", 4096*2, NULL, 1, NULL);
    // xTaskCreatePinnedToCore(guiTask, "gui", 4096*2, NULL, 1, NULL, 1);
    /* NOTE: When not using Wi-Fi nor Bluetooth you can pin the guiTask to core 0 */
    xTaskCreatePinnedToCore(guiTask, "gui", 4096*2, NULL, 0, NULL, 1);
}
 
/* 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;
 
static void guiTask(void *pvParameter)
{
    (void) pvParameter;
    xGuiSemaphore = xSemaphoreCreateMutex();
 
    lv_init();
 
    /* Initialize SPI or I2C bus used by the drivers */
    lvgl_driver_init();
 
    lv_color_t *buf1 = heap_caps_malloc(DISP_BUF_SIZE * sizeof(lv_color_t), MALLOC_CAP_DMA);
    assert(buf1 != NULL);
    /* Use double buffered when not working with monochrome displays */
    lv_color_t* buf2 = heap_caps_malloc(DISP_BUF_SIZE * sizeof(lv_color_t), MALLOC_CAP_DMA);
    assert(buf2 != NULL);
    static lv_disp_draw_buf_t disp_buf;
    uint32_t size_in_px = DISP_BUF_SIZE;
    /* Initialize the working buffer depending on the selected display. */
    lv_disp_draw_buf_init(&disp_buf, buf1, buf2, size_in_px);
 
    lv_disp_drv_t disp_drv;
    lv_disp_drv_init(&disp_drv);
    disp_drv.hor_res = LV_HOR_RES_MAX;
    disp_drv.ver_res = LV_VER_RES_MAX;
    disp_drv.flush_cb = disp_driver_flush;
    disp_drv.draw_buf = &disp_buf;
    lv_disp_drv_register(&disp_drv);
    #if CONFIG_LV_TOUCH_CONTROLLER != TOUCH_CONTROLLER_NONE
        ESP_LOGI("LVGL","TOUCH INIT");
        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
    /* Create and start a periodic timer interrupt to call lv_tick_inc */
    const esp_timer_create_args_t periodic_timer_args = {
        .callback = &lv_tick_task,
        .name = "periodic_gui"
    };
    esp_timer_handle_t periodic_timer;
    ESP_ERROR_CHECK(esp_timer_create(&periodic_timer_args, &periodic_timer));
    ESP_ERROR_CHECK(esp_timer_start_periodic(periodic_timer, LV_TICK_PERIOD_MS * 1000));
 
    /* Create the demo application */
    create_demo_application();
 
    while (1)
    {
        /* Delay 1 tick (assumes FreeRTOS tick is 10ms */
        vTaskDelay(pdMS_TO_TICKS(10));
        lv_task_handler();
 
        /* Try to take the semaphore, call lvgl related function on success */
        if (pdTRUE == xSemaphoreTake(xGuiSemaphore, portMAX_DELAY)) {
            lv_task_handler();
            xSemaphoreGive(xGuiSemaphore);
       }
    }
}
static void event_handler(lv_event_t * e)
{
    lv_event_code_t code = lv_event_get_code(e);

    if(code == LV_EVENT_CLICKED) {
        LV_LOG_USER("Clicked");
        ESP_LOGI("Main","Clicked");
    }
    else if(code == LV_EVENT_VALUE_CHANGED) {
        LV_LOG_USER("Toggled");
        ESP_LOGI("Main","Toggled");
    }
}

 
static void create_demo_application(void)
{
    /* Get the current screen  */
    // lv_obj_t * scr = lv_disp_get_scr_act(NULL);    
    /*Create a Label on the currently active screen*/
    lv_obj_t * scr = lv_scr_act(); //创建scr
    // lv_obj_set_pos(scr,0,0);
    // lv_obj_set_style_bg_color(scr, lv_color_hex(0x000000), 0); 
    // lv_scr_load(scr);
    lv_obj_t * label1 =  lv_label_create(scr);
    /*Modify the Label's text*/
    lv_label_set_text(label1, "Hello\nworld");
    lv_obj_t * label2 =  lv_label_create(scr);
    lv_label_set_recolor(label2, true);
    lv_label_set_text_fmt(label2, "Good Day #FF0000 best#");
    /* Align the Label to the center
     * NULL means align on parent (which is the screen now)
     * 0, 0 at the end means an x, y offset after alignment*/
    lv_obj_align(label1, LV_ALIGN_CENTER, -50, 0);
    lv_obj_align(label2, LV_ALIGN_CENTER, 50, 0);
    lv_obj_t * label;

    lv_obj_t * btn1 = lv_btn_create(lv_scr_act());
    lv_obj_add_event_cb(btn1, event_handler, LV_EVENT_ALL, NULL);
    lv_obj_align(btn1, LV_ALIGN_CENTER, 0, 0);

    label = lv_label_create(btn1);
    lv_label_set_text(label, "Button");
    lv_obj_center(label);


    lv_obj_t * label3 = lv_label_create(lv_scr_act());
    lv_label_set_long_mode(label3, LV_LABEL_LONG_SCROLL_CIRCULAR);     /*Circular scroll*/
    lv_obj_set_width(label3, 150);
    lv_label_set_text(label3, "It is a circularly scrolling text. ");
    lv_obj_align(label3, LV_ALIGN_CENTER, 0, 40);
}
 
static void lv_tick_task(void *arg) {
    (void) arg;
 
    lv_tick_inc(LV_TICK_PERIOD_MS);
}

最后

  • TFT的驱动代码: “lvgl_esp32_drivers/lvgl_tft/st7789v.h”和“lvgl_esp32_drivers/lvgl_tft/st7789v.c”。
  • 触摸屏的驱动代码在“lvgl_esp32_drivers/touch/cst816t.h”和“lvgl_esp32_drivers/touch/cst816t.c”

并非相关领域专家,仅对找到的驱动代码进行了“搬运”、“整理”。如有挖坑,多多包涵。

参考

  • idf lvgl8显示触摸移植,st7789v+cst816
  • ESP32 ESP-IDF LVGL8.3.3移植

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/376279.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

高级前端面试题汇总

iframe 有那些优点和缺点&#xff1f; iframe 元素会创建包含另外一个文档的内联框架&#xff08;即行内框架&#xff09;。 优点&#xff1a; 用来加载速度较慢的内容&#xff08;如广告&#xff09;可以使脚本可以并行下载可以实现跨子域通信 缺点&#xff1a; iframe 会…

【ssm框架】从0开始搭建ssm框架(idea版本)

SSM&#xff08;SpringSpringMVCMyBatis&#xff09;框架集由Spring、MyBatis两个开源框架整合而&#xff08;SpringMVC是Spring中的部分内容&#xff09;&#xff0c;常作为数据源较简单的web项目的框架。 一、 环境介绍 先创建一个web工程。这里使用SSM最终完成一个员工信息的…

驾驭云端之风1——Spring Cloud微服务架构实践指南

本博客纯属个人总结&#xff0c;非原创。喜欢技术交流的&#xff0c;可关注博主&#xff0c;武汉有后端开发群&#xff0c;可支持内推&#xff0c;了解武汉行情等。 前沿 优惠卷平台项目的整体功能和模块&#xff0c;以及每个功能点的技术选型和背后的依据。 搭建一个简化版的…

窃密恶意软件Raccoon最新样本Stealer v2分析

Raccoon 是一个恶意软件家族&#xff0c;2019 年来一直在地下犯罪论坛中以恶意软件即服务的身份进行售卖。2022 年 7 月&#xff0c;该恶意软件家族发布了 C 语言编写的新版本 Raccoon Stealer v2&#xff0c;打破了以往使用 C 开发的传统。 Raccoon 是一个信息窃密恶意软件&a…

JavaEE高阶---Redis

一:缓存简介 1.1 缓存定义 缓存是一个高速数据交换的存储器&#xff0c;使用它可以快速的访问和操作数据 . 1.2 程序中的缓存 当没有使用缓存时 : 但随着业务的发展&#xff0c;公司的框架慢慢变成了多个程序调用一个数据库的情况了&#xff1a; 这是大部分公司的普遍的架构…

设备加密狗

场景描述 随着科技的飞速发展&#xff0c;越来越多的智能设备走进生产加工车间。例如智能雕刻机、钣金机、榫槽机、钻孔机、磨刀机等等。 这些智能设备存在很大共性&#xff0c;就是都内嵌完整的操作系统。有的是windows&#xff0c;有的是linux。设备制造商提供的专业软件运…

pycharm的下载讲解以及安装步骤

目录 Python安装 这时&#xff0c;有人要问了&#xff0c;下载pycharm一定要下载Python么&#xff1f; Python官网 Pycharm安装 完成 推荐书籍 写在最后 Python安装 首先我们进入Python的官方下载网站 这时&#xff0c;有人要问了&#xff0c;下载pycharm一定要下载Py…

算法设计与分析期末考试复习(五)

回溯法 回溯法是一种试探法&#xff0c;将n元问题P的状态空间E表示成为一棵高为n的带权有序数T&#xff0c;把在E中求问题P的解转换为在T中搜索问题P的解。 解题方法&#xff1a;按选优条件对T进行深度优先搜索&#xff0c;以达到目标。 从根节点出发深度优先搜索解空间树。当…

初学网络安全不可不知的:10款开源安全工具

随着互联网的不断发展&#xff0c;安全问题也越来越受到企业的重视。但安全问题往往需要大量资金的投入&#xff0c;例如聘请安全工程师&#xff0c;产品研发&#xff0c;测试等流程。这对于那些原本就资金紧缺的企业而言&#xff0c;是绝对无法接受的。因此&#xff0c;为了减…

Python3+Selenium3自动化测试-(准备)

最近在学习selenium自动化测试相关的内容&#xff0c;所以将实际准备情况做一记录&#xff0c; # 系统&#xff1a;win10(64位) # 浏览器&#xff1a;Chrome(67.0)、Firefox(61.0)、IE # python版本&#xff1a;3.6.5 # Selenium&#xff1a;3.13.0Selenium简介 Selenium是一…

JUC并发编程——线程安全问题

目录一、共享问题1.1 共享带来的问题1.2 临界区与竞态条件二、解决方案2.1 上下文切换——synchronized-解决2.2 上下文切换——synchronized-理解2.3 上下文切换——synchronized-思考2.4 锁面向对象改进2.5 方法上的 synchronized三、synchronized习题3.1 synchronized-加在方…

记住这些快捷键,让你轻松玩转mac(macOS 常用快捷键分享)

适当运用键盘快捷键可以帮助用户提高效率&#xff0c;这里小编为大家带来了一些macOS 常用快捷键&#xff0c;掌握这些快捷键可以帮你解放鼠标手&#xff0c;成为键盘侠&#xff0c;一起来看看吧&#xff01; 快捷键标识简介 当你在应用菜单中发现部分操作项后边有一些特殊标…

搜广推 AutoRec与 Deep Crossing - 推荐系统深度学习模型开篇

😄 AutoRec:2015年由澳大利亚国立大学提出。【后文简称AR】 😄 DeepCrossing:2016年,微软基于ResNet的经典DNN结构。【后文简称DC】 文章目录 1、AutoRec1.1、原理1.2、优点1.3、缺点2、Deep Crossing2.1、原理2.2、优点:2.3、缺点:Reference1、AutoRec 1.1、原理 -…

IEEE SLT 2022论文丨如何利用x-vectors提升语音鉴伪系统性能?

分享一篇IEEE SLT 2022收录的声纹识别方向的论文&#xff0c;《HOW TO BOOST ANTI-SPOOFING WITH X-VECTORS》由AuroraLab&#xff08;极光实验室&#xff09;发表。 来源丨AuroraLab AuroraLab源自清华大学电子工程系与新疆大学信息科学与工程学院&#xff0c;以说话人识别和…

Qt 第9课、计算器中缀转后缀算法

计算器核心算法&#xff1a; 1、将中缀表达式进行数字和运算符的分离 2、将中缀表达式转换成后缀表达式 3、通过后缀表达式计算最后的结果 二、计算器中缀转后缀算法 计算器中缀转后缀算法的意义在于把中缀表达式转换成后缀表达式&#xff0c;能够更好地计算 算法的基本思路…

【RabbitMQ笔记08】消息队列RabbitMQ之防止消息丢失的三种方式(生产者消息确认、消费者消息确认、消息持久化)

这篇文章&#xff0c;主要介绍消息队列RabbitMQ之防止消息丢失的三种方式&#xff08;生产者消息确认、消费者消息确认、消息持久化&#xff09;。 目录 一、防止消息丢失 1.1、消息确认机制&#xff08;生产者&#xff09; &#xff08;1&#xff09;生产者丢失消息 &…

字节跳动软件测试岗4轮面经(已拿34K+ offer)...

没有绝对的天才&#xff0c;只有持续不断的付出。对于我们每一个平凡人来说&#xff0c;改变命运只能依靠努力幸运&#xff0c;但如果你不够幸运&#xff0c;那就只能拉高努力的占比。 2021年10月&#xff0c;我有幸成为了字节跳动的一名测试工程师&#xff0c;从外包辞职了历…

一文读懂自动驾驶运行设计域ODD

/ 导读 /在自动驾驶技术发展如此迅速的今天&#xff0c;很多量产车上已经配备了多种的辅助驾驶功能&#xff0c;例如自适应巡航ACC、紧急制动AEB、车道居中保持LKA等等&#xff0c;很多的车主也都体验到了技术带给驾驶的改变。另一方面&#xff0c;由于现在的自动驾驶技术还处于…

量化选股——基于动量因子的行业风格轮动策略(第2部分—策略回测)

文章目录1. 交易策略2. Backtrader回测程序3. 回测效果3.1 2020年1月1日 - 2021年1月1日3.2 2021年1月1日 — 2022年1月1日3.3 2022年1月1日 — 2023年1月1日动量因子的概述与测算&#xff0c;阿隆指标测算请参考&#xff1a;https://blog.csdn.net/weixin_35757704/article/de…

react源码解析1.开篇介绍和面试题

怎样学习react源码 作为前端最常用的js库之一&#xff0c;熟悉react源码成了高级或资深前端工程师必备的能力&#xff0c;如果你不想停留在api的使用层面或者想在前端技能的深度上有所突破&#xff0c;那熟悉react源码将是你进步的很好的方式。 react的纯粹体现在它的api上&a…