IoTLabs

Nghiên cứu, Sáng tạo và Thử nghiệm

ESP32-C3 SuperMini: Hướng dẫn test TFT TFT 1.47inch, Driver ST7789

(Bài viết dành cho người mới bắt đầu. Mục tiêu: cắm board → cài Arduino IDE → chọn đúng board → upload thành công → test màn TFT SPI.)

ESP32-C3 SuperMini (Tenstar Robot) là một board ESP32-C3 kích thước nhỏ gọn, phù hợp cho dự án IoT nhờ:

  • Wi‑Fi + BLE tích hợp
  • Tiêu thụ điện thấp, hỗ trợ deep sleep
  • Chân GPIO đủ cho các module phổ biến (SPI/I2C/UART)
  • Giá rẻ, dễ mua, phù hợp DIY/giáo dục

Trong bài này, mình hướng dẫn theo đúng quy trình thực chiến: cài toolchain → chọn đúng board → upload test → (tuỳ chọn) test màn hình TFT 1.47″ ST7789-P3 172×320.

Chuẩn bị

Phần cứng

  • ESP32-C3 SuperMini Tenstar Robot
  • 1× cáp USB có data (rất nhiều lỗi upload do cáp chỉ sạc)
  • (Tuỳ chọn) 1× TFT SPI (ví dụ: TFT 1.47″ IPS ST7789‑P3 172×320)

Phần mềm

  • Arduino IDE 2.x

Bước 1: Cài ESP32 core cho Arduino IDE

  1. Mở Arduino IDEPreferences
  2. Dán link sau vào Additional Boards Manager URLs:
https://espressif.github.io/arduino-esp32/package_esp32_index.json
  1. Vào Tools → Board → Boards Manager…
  2. Tìm ESP32 → cài “ESP32 by Espressif Systems” (phiên bản mới nhất)

Bước 2: Chọn đúng Board cho ESP32-C3 SuperMini

Nhiều board “SuperMini / Tenstar Robot” không có tên riêng trong Arduino IDE. Cách ổn định nhất là chọn:

  • Tools → Board → ESP32 Arduino → ESP32C3 Dev Module

Thiết lập khuyến nghị (Tools menu):

  • USB CDC On Boot: Enabled
  • Upload Speed: 460800 (nếu lỗi thì hạ 115200)
  • Các mục khác để mặc định

Bước 3: Chọn đúng Port và upload Blink

  1. Cắm board vào máy
  2. Tools → Port → chọn cổng mới xuất hiện
  3. Upload ví dụ Blink:
void setup(){
  pinMode(8, OUTPUT); // nếu LED onboard khác chân, bạn đổi theo board
}

void loop(){
  digitalWrite(8, HIGH);
  delay(500);
  digitalWrite(8, LOW);
  delay(500);
}

Gợi ý: nhiều board C3 mini có LED ở GPIO8 hoặc GPIO10. Nếu không nháy, không sao — mục tiêu bước này là upload thành công.

Bước 4: Xử lý lỗi upload thường gặp

1) Không thấy Port

  • Đổi cáp USB (cáp data)
  • Đổi cổng USB
  • macOS: kiểm tra quyền/driver (thường dùng CDC nên không cần driver riêng)

2) Upload bị “Connecting…” rồi timeout

  • Hạ Upload Speed xuống 115200
  • Nếu board có nút BOOT: giữ BOOT khi bắt đầu upload (một số board cần)

Test màn TFT SPI 1.47″ ST7789‑P3 (172×320)

Pinout TFT (thứ tự header phổ biến)

VCC, GND, SCL, SDA, RST, DC, CS, BLK

Map dây sang ESP32‑C3 SuperMini (khuyến nghị)

  • VCC → 3V3
  • GND → GND
  • SCL(SCK) → GPIO4
  • SDA(MOSI) → GPIO6
  • RST → GPIO3
  • DC → GPIO2
  • CS → GPIO7 (nếu màn là “7 pin không CS” thì bỏ CS và cấu hình CS = -1 trong code)
  • BLK → GPIO10 (hoặc test BLK nối thẳng 3V3 để chắc chắn backlight sáng)

Lưu ý quan trọng: ST7789‑P3 172×320 thường là vùng hiển thị nằm trong frame 240×320 → cần offset X (hay gặp 34). Nếu dùng sai driver/offset, màn có thể đen hoặc lệch.


Code test TFT (Adafruit_ST7789) – hiển thị chữ + counter

Thư viện cần cài (Library Manager):

  • Adafruit GFX Library
  • Adafruit ST7735 and ST7789 Library

Dán đúng đoạn code dưới đây vào 1 file .ino (đúng wiring như phần pinout) rồi upload:

/**
 * Date: 2025-10-21
 * Project: ESP32-C3 Tenstar + TFT 1.47" (ST7789-P3 172x320) Test
 * Agenda:
 * - Khởi tạo ST7789-P3 & tô màu nền
 * - Kỳ vọng: Màn lần lượt đổi đỏ → xanh lá → xanh dương mỗi 1 giây.
 * Notes:
 * - TFT header order: VCC, GND, SCL, SDA, RST, DC, CS, BLK
 * - Board: ESP32-C3 SuperMini (Tenstar Robot)
 */
#include <Arduino.h>
#include <SPI.h>
#include <Adafruit_GFX.h>
#include <Adafruit_ST7789.h>

// ===== ESP32-C3 Tenstar wiring =====
#define TFT_SCL_SCK   4
#define TFT_SDA_MOSI  6
#define TFT_RST   3
#define TFT_DC    2
#define TFT_CS    7
#define TFT_BL   10 // GPIO10 hoặc nối thẳng 3.3V để test backlight
#define TFT_MISO -1

// ===== Display size =====
#define TFT_W 172
#define TFT_H 320

SPIClass spi(FSPI);
Adafruit_ST7789 tft(&spi, TFT_CS, TFT_DC, TFT_RST);

// Backlight
void blInit() {
  pinMode(TFT_BL, OUTPUT);
  digitalWrite(TFT_BL, HIGH);
}
void setBL(uint8_t pct) {
  digitalWrite(TFT_BL, (pct > 0) ? HIGH : LOW);
}

// ---- Draw text helper ----
void drawTextLines() {
  tft.setTextWrap(false);
  tft.setTextSize(2);
  tft.setTextColor(ST77XX_WHITE, ST77XX_BLACK);

  // Nền đen để chữ rõ
  tft.fillScreen(ST77XX_BLACK);

  // In nhiều dòng
  tft.setCursor(10, 20);
  tft.println("IoTLabs.vn");

  tft.setTextSize(1);
  tft.setCursor(10, 40);
  tft.println("Nghien cu - Sang tao - Thu nghiem");

  tft.setCursor(10, 65);
  tft.println("TFT 1.47 inch, 172x320, Driver: ST7789-P3");

  tft.setCursor(10, 80);
  tft.println("ESP32-C3 Tenstar Robot");

  tft.setCursor(10, 110);
  tft.print("Pins: SCL_SCK=");
  tft.print(TFT_SCL_SCK);
  tft.print(" SDA_MOSI=");
  tft.print(TFT_SDA_MOSI);

  tft.setCursor(10, 130);
  tft.print("DC=");
  tft.print(TFT_DC);
  tft.print(" RST=");
  tft.print(TFT_RST);
  tft.print(" CS=");
  tft.print(TFT_CS);
  tft.print(" BL=");
  tft.print(TFT_BL);
}

void setup() {
  Serial.begin(115200);
  delay(200);

  blInit();
  setBL(100);

  // SPI init đúng chân ESP32-C3
  spi.begin(TFT_SCL_SCK, TFT_MISO, TFT_SDA_MOSI, TFT_CS);
  spi.setFrequency(8000000);

  // Init ST7789
  tft.init(TFT_W, TFT_H);
  tft.setRotation(1);

  // Nếu màu bị ngược / màn đen: thử bật/tắt invert (mở 1 cái)
  // tft.invertDisplay(true);
  // tft.invertDisplay(false);

  // ---- HIỂN THỊ CHỮ ----
  drawTextLines();
}

void loop() {
  // Demo: cập nhật 1 dòng “counter” mỗi 1 giây
  static uint32_t n = 0;

  // Xóa vùng nhỏ rồi in lại để không nhòe chữ
  tft.fillRect(10, 190, 160, 20, ST77XX_BLACK);
  tft.setTextSize(2);
  tft.setTextColor(ST77XX_GREEN, ST77XX_BLACK);
  tft.setCursor(10, 190);
  tft.print("Count: ");
  tft.print(n++);

  delay(1000);

  // Nếu bạn muốn test đổi màu như agenda, comment counter và bật đoạn này:
  /*
  tft.fillScreen(ST77XX_RED);   delay(1000);
  tft.fillScreen(ST77XX_GREEN); delay(1000);
  tft.fillScreen(ST77XX_BLUE);  delay(1000);
  */
}

Giải thích code (ngắn gọn, đúng phần quan trọng)

1) Khai báo chân (pin mapping)

  • TFT_SCL_SCK = 4: Clock SPI (SCL/SCK)
  • TFT_SDA_MOSI = 6: Data SPI (SDA/MOSI)
  • TFT_DC = 2: phân biệt dữ liệu (pixel/text) hay lệnh (command)
  • TFT_RST = 3: reset màn hình
  • TFT_CS = 7: chip select (chọn màn trên bus SPI)
  • TFT_BL = 10: backlight (bật/tắt đèn nền)

2) SPI và khởi tạo driver

  • SPIClass spi(FSPI); tạo SPI bus dùng phần cứng trên ESP32-C3.
  • spi.begin(SCK, MISO, MOSI, CS); gán đúng chân SPI.
  • spi.setFrequency(8000000); đặt 8MHz để ổn định (lên hình trước đã, sau tăng).
  • tft.init(TFT_W, TFT_H); khởi tạo màn theo kích thước bạn khai báo.
  • tft.setRotation(1); xoay màn cho đúng chiều.

3) Backlight

  • blInit() set chân BLK là OUTPUT và bật HIGH (đa số module HIGH = sáng).
  • Nếu màn tối đen, test nhanh nhất: nối BLK → 3V3.

4) In text

  • setTextWrap(false) tránh tự xuống dòng.
  • setTextSize() đổi cỡ chữ (1 nhỏ, 2 lớn).
  • setTextColor(fg, bg) đặt màu chữ và màu nền để không bị “dính” chữ cũ.
  • setCursor(x,y) chọn vị trí rồi print/println().

5) Cập nhật 1 dòng động (counter)

  • Dùng fillRect() xóa vùng nhỏ trước khi in lại để không nhòe.

Nếu vẫn không hiển thị (fix nhanh)

  • Test backlight: nối BLK → 3V3.
  • Thử tft.invertDisplay(true/false) (mở từng cái).
  • Loại ST7789-P3 172×320 có thể cần offset vùng hiển thị; nếu đổi màu OK nhưng chữ lệch/không thấy, nên chuyển sang LovyanGFX hoặc TFT_eSPI (setViewport) để cấu hình offset X (hay gặp ~34).

Câu hỏi thường gặp (FAQ)

ESP32-C3 Tenstar chọn board nào?

Chọn ESP32C3 Dev Module là ổn định nhất.

Vì sao TFT 172×320 hay bị đen?

Do panel thường chạy ST7789 “frame” 240×320 nhưng vùng hiển thị thật 172×320 → cần offset đúng.

Có dùng được Adafruit_ST7789 không?

Có thể, nhưng với ST7789‑P3 172×320 nhiều module cần init/offset đặc thù. LovyanGFX thường ít lỗi hơn.