Beyond CoWoS: Why CoWoP (Chip on Wafer on PCB) is the Next Game-Changer for High-Performance Computing
For the past three years, the AI and High-Performance Computing (HPC) industry has been held hostage by a single, critical
Are you looking to create sleek, responsive touchscreen interfaces for your IoT projects without complex display wiring? The ESP32 Cheap Yellow Display (CYD) combined with the LVGL graphics library offers the most cost-effective and powerful way to build graphical user interfaces (GUIs). This guide walks you through everything from hardware selection to running your first interactive LVGL project.

The ESP32-2432S028R (Cheap Yellow Display) integrates an ESP32 module with a 2.8-inch TFT touchscreen, eliminating the hassle of connecting separate displays. When paired with LVGL (Light and Versatile Graphics Library) , you can create professional interfaces with:
Rich UI Elements: Buttons, sliders, charts, keyboards, and animations
Touch Interaction: Full resistive touch support out-of-the-box
Low Resource Usage: Runs efficiently on ESP32 with only 64KB Flash and 16KB RAM
Open-Source & Free: No licensing costs for commercial projects
This combination is ideal for smart home controllers, industrial panels, wearable devices, and interactive art projects.
ESP32 Cheap Yellow Display (CYD) – Model ESP32-2432S028R (Check current price and buy here)
USB cable (data transfer capable)
Computer with Arduino IDE installed
Arduino IDE (configured for ESP32)
Three key libraries:
TFT_eSPI by Bodmer (display driver)
XPT2046_Touchscreen by Paul Stoffregen (touch driver)
LVGL version 9.2 by kisvegabor (graphics library)
New to the CYD? If you haven’t used this board before, we recommend first reading our ESP32 CYD Getting Started Guide to understand the basics.
Open your Arduino IDE and install these libraries via the Library Manager (Sketch > Include Library > Manage Libraries):
Search for TFT_eSPI by Bodmer → Install
Search for XPT2046_Touchscreen by Paul Stoffregen → Install
Search for LVGL by kisvegabor → Install version 9.2
The default library configurations won’t work with the CYD. You must replace two critical configuration files with our custom versions.
Locate your Arduino sketchbook folder (File > Preferences > Sketchbook location)
Navigate to: [Sketchbook]\libraries\TFT_eSPI\
Replace the existing User_Setup.h with the downloaded file
Place lv_conf.h directly in the [Sketchbook]\libraries\ folder (not inside lvgl folder)
Find your sketchbook location (Arduino IDE > Settings > Sketchbook location)
Navigate to: [Sketchbook]/libraries/TFT_eSPI/
Replace User_Setup.h with the downloaded version
Place lv_conf.h in [Sketchbook]/libraries/ (not inside lvgl folder)
⚠️ IMPORTANT: Using any other User_Setup.h or lv_conf.h files from the internet will likely cause compilation errors. Always use the exact files provided above.
Here’s a complete example that creates an interactive GUI with buttons and a slider. Copy this code to your Arduino IDE and upload it to your CYD.
/* Rui Santos & Sara Santos - Random Nerd Tutorials Complete LVGL example for ESP32 Cheap Yellow Display (CYD) Hardware: ESP32-2432S028R Libraries: LVGL 9.2, TFT_eSPI, XPT2046_Touchscreen */ #include <lvgl.h> #include <TFT_eSPI.h> #include <XPT2046_Touchscreen.h> // Touchscreen pin definitions for CYD #define XPT2046_IRQ 36 #define XPT2046_MOSI 32 #define XPT2046_MISO 39 #define XPT2046_CLK 25 #define XPT2046_CS 33 SPIClass touchscreenSPI = SPIClass(VSPI); XPT2046_Touchscreen touchscreen(XPT2046_CS, XPT2046_IRQ); #define SCREEN_WIDTH 240 #define SCREEN_HEIGHT 320 int touchX, touchY, touchZ; // LVGL draw buffer #define DRAW_BUF_SIZE (SCREEN_WIDTH * SCREEN_HEIGHT / 10 * (LV_COLOR_DEPTH / 8)) uint32_t draw_buf[DRAW_BUF_SIZE / 4]; // LVGL logging void log_print(lv_log_level_t level, const char * buf) { LV_UNUSED(level); Serial.println(buf); Serial.flush(); } // Read touchscreen input for LVGL void touchscreen_read(lv_indev_t * indev, lv_indev_data_t * data) { if(touchscreen.tirqTouched() && touchscreen.touched()) { TS_Point p = touchscreen.getPoint(); touchX = map(p.x, 200, 3700, 1, SCREEN_WIDTH); touchY = map(p.y, 240, 3800, 1, SCREEN_HEIGHT); touchZ = p.z; data->state = LV_INDEV_STATE_PRESSED; data->point.x = touchX; data->point.y = touchY; } else { data->state = LV_INDEV_STATE_RELEASED; } } // Button 1 event handler static void event_handler_btn1(lv_event_t * e) { static int count = 0; if(lv_event_get_code(e) == LV_EVENT_CLICKED) { count++; LV_LOG_USER("Button 1 clicked %d times", count); } } // Button 2 (toggle) event handler static void event_handler_btn2(lv_event_t * e) { lv_obj_t * btn = (lv_obj_t*) lv_event_get_target(e); if(lv_event_get_code(e) == LV_EVENT_VALUE_CHANGED) { LV_LOG_USER("Toggle: %s", lv_obj_has_state(btn, LV_STATE_CHECKED) ? "ON" : "OFF"); } } // Slider event handler static lv_obj_t * slider_label; static void slider_event_callback(lv_event_t * e) { lv_obj_t * slider = (lv_obj_t*) lv_event_get_target(e); char buf[8]; lv_snprintf(buf, sizeof(buf), "%d%%", (int)lv_slider_get_value(slider)); lv_label_set_text(slider_label, buf); lv_obj_align_to(slider_label, slider, LV_ALIGN_OUT_BOTTOM_MID, 0, 10); LV_LOG_USER("Slider value: %d%%", (int)lv_slider_get_value(slider)); } // Create the main GUI void lv_create_main_gui(void) { // Title label lv_obj_t * title = lv_label_create(lv_scr_act()); lv_label_set_text(title, "ESP32 CYD + LVGL"); lv_obj_align(title, LV_ALIGN_TOP_MID, 0, 10); // Button 1 - Standard button lv_obj_t * btn1 = lv_btn_create(lv_scr_act()); lv_obj_align(btn1, LV_ALIGN_CENTER, 0, -50); lv_obj_add_event_cb(btn1, event_handler_btn1, LV_EVENT_ALL, NULL); lv_obj_t * btn1_label = lv_label_create(btn1); lv_label_set_text(btn1_label, "Click Me"); // Button 2 - Toggle button lv_obj_t * btn2 = lv_btn_create(lv_scr_act()); lv_obj_align(btn2, LV_ALIGN_CENTER, 0, 10); lv_obj_add_flag(btn2, LV_OBJ_FLAG_CHECKABLE); lv_obj_add_event_cb(btn2, event_handler_btn2, LV_EVENT_VALUE_CHANGED, NULL); lv_obj_t * btn2_label = lv_label_create(btn2); lv_label_set_text(btn2_label, "Toggle"); // Slider with value display lv_obj_t * slider = lv_slider_create(lv_scr_act()); lv_obj_align(slider, LV_ALIGN_CENTER, 0, 70); lv_obj_set_width(slider, 150); lv_obj_add_event_cb(slider, slider_event_callback, LV_EVENT_VALUE_CHANGED, NULL); slider_label = lv_label_create(lv_scr_act()); lv_label_set_text(slider_label, "0%"); lv_obj_align_to(slider_label, slider, LV_ALIGN_OUT_BOTTOM_MID, 0, 10); } void setup() { Serial.begin(115200); Serial.println("Starting LVGL on ESP32 CYD..."); // Initialize touchscreen touchscreenSPI.begin(XPT2046_CLK, XPT2046_MISO, XPT2046_MOSI, XPT2046_CS); touchscreen.begin(touchscreenSPI); touchscreen.setRotation(1); // Landscape orientation // Initialize LVGL lv_init(); lv_log_register_print_cb(log_print); // Initialize display lv_display_t * disp; disp = lv_tft_espi_create(SCREEN_WIDTH, SCREEN_HEIGHT, draw_buf, sizeof(draw_buf)); lv_display_set_rotation(disp, LV_DISPLAY_ROTATION_270); // Initialize touch input device lv_indev_t * indev = lv_indev_create(); lv_indev_set_type(indev, LV_INDEV_TYPE_POINTER); lv_indev_set_read_cb(indev, touchscreen_read); // Create GUI lv_create_main_gui(); Serial.println("Setup complete!"); } void loop() { lv_task_handler(); // Let LVGL handle GUI tasks lv_tick_inc(5); // Tell LVGL time passed delay(5); // Small delay }
After uploading, you’ll see:
A title at the top of the screen
A “Click Me” button that increments a counter (viewable in Serial Monitor)
A toggle button that switches between ON/OFF states
A slider that displays its current percentage value below it
The touchscreen is fully functional—tapping any element triggers the corresponding event.
After uploading, the display should show the GUI elements
Open Serial Monitor (115200 baud) to see event logs
Touch each element to verify interaction
Blank display: Check that you replaced User_Setup.h correctly
Touch not working: Verify XPT2046_Touchscreen library is installed and pins match your board
Compilation errors: Ensure you’re using LVGL version 9.2 and the custom lv_conf.h is in the correct location
Note: If you update your libraries later, you’ll need to reapply both configuration files.
With LVGL working on your CYD, you can now build:
Smart home dashboard with Wi-Fi controls
Weather station displaying forecasts and graphs
Data logger with SD card storage and touch controls
Game console with custom UI
👉 Click here to check prices and buy ESP32 CYD
Get your ESP32 CYD today and start creating professional touchscreen interfaces with LVGL!
======================================
1.54 Inch Black White Epaper Display
$3.20
LOLIN D1 Mini V4.0.0 - WEMOS WIFI Internet of Things Board based ESP8266 4MB MicroPython Nodemcu Arduino Compatible
LoRa32 V2.1_1.6 Version 433/868/915Mhz ESP32 LoRa OLED 0.96 Inch SD Card Bluetooth WIFI Wireless Module ESP-32 SMA
$24.90
ESP32-S3 WROOM N16R8 Development Board 2.4G Wifi BT Camera Module OV2640 OV5640 16MB FLASH 8MB PSRAM ESP32 S3 N16R8 CAM
Type-C / Micro USB CH340 Nano 3.0 ATmega328P Controller Board Compatible For Arduino Nano CH340 USB Driver Nano V3.0 ATmega328
$6.50
For the past three years, the AI and High-Performance Computing (HPC) industry has been held hostage by a single, critical
The AI hardware landscape is undergoing a tectonic shift. Driven by the exorbitant costs and supply chain monopolies of merchant
The AI hardware landscape is undergoing a massive schism. For the past three years, the industry has been entirely defined
In the high-stakes world of AI hardware manufacturing, the industry obsesses over bare board fabrication. Signal Integrity (SI) engineers spend
For Hardware Engineering Directors and Supply Chain VPs in the AI sector, the year 2026 presents a brutal paradox. While
The era of standard through-hole routing for high-performance compute is dead. As AI silicon evolves—from NVIDIA’s Blackwell architecture to custom
No account yet?
Create an Account