Table of Contents

โมดูลหน้าจอ TFT LCD ST7789 SPI 1.3 1.54 2.0 inch Touch IPS Display with Module SD card Massmore

ภาพรวม (Overview)

LCD_ST7789 (1)

แนะนำ (Introduction)

          โมดูลหน้าจอแสดงผลซีรีส์ ST7789 จาก Massmore เป็นจอภาพชนิด IPS (In-Plane Switching) ที่ให้ความคมชัดสูง สีสันสดใส และมีมุมมองที่กว้างถึง 170 องศา เชื่อมต่อผ่านโปรโตคอล SPI ซึ่งใช้สายสัญญาณน้อย เหมาะสำหรับการใช้งานร่วมกับไมโครคอนโทรลเลอร์หลากหลายชนิด เช่น Arduino, ESP32, STM32 และ Raspberry Pi โดยมีให้เลือกใช้งานตั้งแต่ขนาดเล็กกะทัดรัดไปจนถึงขนาด 2.0 นิ้วที่รองรับการอ่านข้อมูลจาก SD card และระบบสัมผัสแม่นยำ เพื่อตอบโจทย์การสร้างสรรค์อุปกรณ์อัจฉริยะ (Smart Devices) และโปรเจกต์ IoT ในยุคปัจจุบัน

คุณสมบัติ (Features)

  • เทคโนโลยี IPS: ให้สีสันที่แม่นยำและมองเห็นได้ชัดเจนจากทุกมุมมอง

  • ไดรเวอร์ ST7789: เป็นมาตรฐานสากล รองรับไลบรารีการเขียนโปรแกรมที่หลากหลาย

  • ความละเอียดสูง: 240×240 และ 240×320 พิกเซล ให้ภาพที่เนียนละเอียด

  • การเชื่อมต่อ SPI: ใช้พินน้อย ประหยัดทรัพยากรของไมโครคอนโทรลเลอร์

  • ฟังก์ชันเสริม (รุ่น 2.0″): มาพร้อมช่องเสียบ Micro SD Card สำหรับจัดเก็บรูปภาพหรือข้อมูล

  • ระบบสัมผัส (รุ่น Touch): ใช้เทคโนโลยี Capacitive ผ่านชิป CST816 รองรับการตอบสนองที่รวดเร็วและลื่นไหล

ข้อมูลสินค้า (Spec Data)

  • ไดรเวอร์ไอซี (Driver IC) : ST7789 / ST7789V

  • แรงดันไฟฟ้าใช้งาน (Operating Voltage) : 3.3V – 5.0VDC เฉพาะรุ่น 2.0 นิ้ว

  • แรงดันสัญญาณลอจิก (Logic Voltage) : 3.3V (แนะนำ)

  • การเชื่อมต่อ (Interface) : 4-Wire SPI

  • สีการแสดงผล (Color) : RGB 65K Color / 16-bit

  • ทิศทางการมอง: รอบด้าน (Full Viewing Angle)

ข้อมูลบอร์ด (Onboard Resources)

ข้อมูลขนาดสินค้า

ข้อมูลทางเทคนิค (Specification)

ขนาด 1.3 นิ้ว และ 1.54 นิ้ว

  • Resolution: 240 x 240 Pixels

  • Controller: ST7789V

  • Interface: 7-Pin SPI (GND, VCC, SCL, SDA, RES, DC, BLK)

  • Active Area: 23.4 x 23.4 mm (1.3″) / 27.72 x 27.72 mm (1.54″)

ขนาด 2.0 นิ้ว (Non Touch / Touch)

  • Resolution: 240 x 320 Pixels

  • Controller: ST7789V

  • Touch Controller: CST816 (เฉพาะรุ่น Touch) เชื่อมต่อผ่าน I2C

  • Storage: Micro SD Card Slot เชื่อมต่อผ่าน SPI

  • Interface: Multi-pin Header (รองรับทั้งการแสดงผล, SD Card และ Touch)

เปรียบเทียบ (Comparison)

          ในรุ่นขนาด 1.3″ และ 1.54″ จะเน้นความกะทัดรัด เหมาะสำหรับอุปกรณ์สวมใส่หรืออุปกรณ์แสดงผลสถานะขนาดเล็ก ส่วนรุ่น 2.0″ จะมีความโดดเด่นในด้านพื้นที่การแสดงผลที่มากกว่า และถูกออกแบบมาเพื่อการใช้งานที่ซับซ้อนขึ้นด้วยการเพิ่มช่อง SD Card เข้ามา ทำให้สามารถเก็บไฟล์รูปภาพ .bmp เพื่อดึงมาแสดงผลบนหน้าจอได้โดยไม่เปลืองหน่วยความจำของตัวประมวลผลหลัก สำหรับรุ่น Capacitive Touch จะให้ประสบการณ์การใช้งานเหมือนสมาร์ทโฟน เหมาะสำหรับเครื่องมือวัดหรือแผงควบคุมที่ต้องการการโต้ตอบจากผู้ใช้งาน

ตัวอย่างการใช้งาน (Applications)

  • Smart Watch DIY: สร้างนาฬิกาอัจฉริยะที่แสดงผลแจ้งเตือนและวัดอัตราการเต้นของหัวใจ

  • IoT Dashboard: แสดงค่าอุณหภูมิ ความชื้น และกราฟสถานะของระบบ Smart Home

  • Media Player: ใช้รุ่น 2.0″ แสดงภาพถ่ายจาก SD Card หรือสร้างเครื่องเล่น MP3 ขนาดเล็ก

  • Control Panel: รุ่น Touch Screen ใช้ทำหน้าจอควบคุมเครื่องจักรหรือระบบสั่งการในโรงงาน

  • Educational Kits: ใช้เป็นอุปกรณ์เสริมสำหรับการเรียนรู้การเขียนโปรแกรมกราฟิกบนไมโครคอนโทรลเลอร์

ตัวอย่างโปรแกรม (Example Arduino Code)

การตั้งค่าและติดตั้งโปรแกรม Setup Arduino Library

  1. TFT_eSPI
  2.  PNGdec
  3.  JPEGDecoder
  4. TJpg_Decoder
  • ใช้ไลบรารี TFT_eSPI สำหรับควบคุมจอ ST7789

  • ไลบรารีนี้ต้องตั้งค่าขา GPIO ในไฟล์ User_Setup.h ให้ตรงกับบอร์ดก่อนใช้งาน

การใช้งานหน้าจอ TFT LCD 1.3″ 1.54″ 2.0″ สามารถใช้โปรแกรมเดียวกันได้ เนื่องจาก Driver ST7789 เหมือนกัน ทำให้ง่ายต่อการใช้งาน

ตัวอย่างที่ 1 การแสดงผลกราฟิก UI หน้าจอ 1.3" หรือ 1.54" TFT LCD 240x240 Pixel Driver ST7789

1_TFT_LCD_ST7789_Demo

อุปกรณ์ที่ใช้ในโปรเจกต์

  • บอร์ด ESP32 38PIN Massmore

  • TFT LCD 1.3″ 1.54″ 2.0″ (รุ่นใดก็ได้)

Arduino IDE Code

  • อย่าลืมติดตั้ง Library จากไฟล์บน Github 
    https://github.com/Massmore/SKU-1021-TFT-LCD-ST7789
				
					#include <SPI.h>
#include <TFT_eSPI.h>

TFT_eSPI tft = TFT_eSPI();

// --- Color Definitions ---
#define MASSMORE_BLUE   0x041F
#define MASSMORE_PINK   0xF81F
#define MASSMORE_CYAN   0x07FF
#define NEON_GREEN      0x07E0
#define DARK_BG         0x10A2 // Dark Grey
#define ORANGE_RED      0xFA20
#define PURPLE_Haze     0x780F

// --- Global Variables ---
int currentPage = 1;
unsigned long lastPageSwitchTime = 0;
const unsigned long pageDuration = 5000; // 5000ms = 5 วินาที
bool pageInitialized = false; // ตัวแปรเช็กว่าวาด Background หรือยัง

// ตัวแปรสำหรับ Animation หน้า 1
int p1_circleR = 5;
int p1_grow = 1;

// ตัวแปรสำหรับ Animation หน้า 2 (Bouncing Ball)
int p2_ballX = 120, p2_ballY = 120;
int p2_dirX = 3, p2_dirY = 3;
int p2_radius = 8;

// ตัวแปรสำหรับ Animation หน้า 3 (Radar Pulse)
int p3_pulseR = 10;

void setup() {
  tft.begin();
  tft.setRotation(0);
  tft.fillScreen(TFT_BLACK);
  lastPageSwitchTime = millis();
}

void loop() {
  unsigned long currentTime = millis();

  // ตรวจสอบว่าถึงเวลาเปลี่ยนหน้าหรือยัง
  if (currentTime - lastPageSwitchTime > pageDuration) {
    currentPage++;
    if (currentPage > 3) currentPage = 1; // วนกลับไปหน้า 1
    lastPageSwitchTime = currentTime;
    pageInitialized = false; // บอกให้วาด Background ใหม่
    tft.fillScreen(TFT_BLACK); // ล้างหน้าจอ
  }

  // เลือกทำงานตามหน้าปัจจุบัน
  switch (currentPage) {
    case 1:
      if (!pageInitialized) drawPage1_Static();
      runPage1_Anim();
      break;
    case 2:
      if (!pageInitialized) drawPage2_Static();
      runPage2_Anim();
      break;
    case 3:
      if (!pageInitialized) drawPage3_Static();
      runPage3_Anim();
      break;
  }
  
  delay(30); // หน่วงนิดหน่อยเพื่อความลื่นไหล (30-50ms)
}

// ==========================================
// PAGE 1: "Hello Worlds" (ธีมสีฟ้า/ชมพู)
// ==========================================
void drawPage1_Static() {
  tft.fillScreen(TFT_BLACK);
  // กรอบ Card
  tft.drawRoundRect(10, 10, 220, 220, 10, MASSMORE_CYAN);
  tft.drawRoundRect(12, 12, 216, 216, 9, MASSMORE_BLUE);
  // Header
  tft.fillRoundRect(20, 30, 200, 40, 5, MASSMORE_BLUE);
  
  tft.setTextColor(TFT_WHITE, MASSMORE_BLUE);
  tft.setTextDatum(MC_DATUM);
  tft.setTextSize(2);
  tft.drawString("Hello Worlds", 120, 50);

  tft.setTextColor(TFT_YELLOW, TFT_BLACK);
  tft.setTextSize(1);
  tft.setTextFont(4);
  tft.drawString("We are", 120, 130);
  
  tft.setTextColor(MASSMORE_CYAN, TFT_BLACK);
  tft.drawString("Massmore", 120, 160);
  
  pageInitialized = true;
}

void runPage1_Anim() {
  // Animation: วงกลมหายใจ (Breathing Circle)
  tft.drawCircle(120, 200, p1_circleR, TFT_BLACK); // ลบวงเก่า
  
  if (p1_grow) {
    p1_circleR++;
    if (p1_circleR > 18) p1_grow = 0;
  } else {
    p1_circleR--;
    if (p1_circleR < 5) p1_grow = 1;
  }
  tft.drawCircle(120, 200, p1_circleR, MASSMORE_PINK); // วาดวงใหม่
}

// ==========================================
// PAGE 2: "System Ready" (ธีมสีเขียว/Cyber)
// ==========================================
void drawPage2_Static() {
  tft.fillScreen(DARK_BG);
  // เส้นตาราง Grid แบบ Cyber
  for(int i=0; i<240; i+=40) {
    tft.drawFastHLine(0, i, 240, 0x2124); // เส้นแนวนอนสีเทาเข้ม
    tft.drawFastVLine(i, 0, 240, 0x2124); // เส้นแนวตั้ง
  }
  
  // กล่องข้อความตรงกลาง
  tft.fillRect(40, 90, 160, 60, TFT_BLACK);
  tft.drawRect(40, 90, 160, 60, NEON_GREEN);
  
  tft.setTextColor(NEON_GREEN, TFT_BLACK);
  tft.setTextDatum(MC_DATUM);
  tft.setTextFont(4);
  tft.setTextSize(1);
  tft.drawString("SYSTEM", 120, 110);
  tft.drawString("READY...", 120, 135);
  
  pageInitialized = true;
}

void runPage2_Anim() {
  // Animation: ลูกบอลเด้งดึ๋ง (Bouncing Ball)
  
  // 1. ลบลูกบอลเก่า (ใช้สีพื้นหลังทับ)
  // เนื่องจากพื้นหลังมี Grid การลบอาจจะทำให้เส้นหาย (เขียนทับด้วยสีพื้น)
  // แต่เพื่อความง่าย เราจะทับด้วยสีพื้น Dark BG ไปเลย
  tft.fillCircle(p2_ballX, p2_ballY, p2_radius, DARK_BG); 
  
  // 2. คำนวณตำแหน่งใหม่
  p2_ballX += p2_dirX;
  p2_ballY += p2_dirY;
  
  // 3. เช็กการชนขอบ (Bounce)
  if (p2_ballX > 230 || p2_ballX < 10) p2_dirX *= -1;
  if (p2_ballY > 230 || p2_ballY < 10) p2_dirY *= -1;
  
  // 4. วาดลูกบอลใหม่
  tft.fillCircle(p2_ballX, p2_ballY, p2_radius, ORANGE_RED);
}

// ==========================================
// PAGE 3: "Processing" (ธีมสีม่วง/ส้ม)
// ==========================================
void drawPage3_Static() {
  tft.fillScreen(TFT_BLACK);
  
  // วาดวงแหวนรอบนอก
  tft.drawCircle(120, 120, 110, PURPLE_Haze);
  tft.drawCircle(120, 120, 100, PURPLE_Haze);

  tft.setTextColor(TFT_WHITE, TFT_BLACK);
  tft.setTextDatum(MC_DATUM);
  tft.setTextFont(2);
  tft.setTextSize(2);
  tft.drawString("ESP32 Demo", 120, 30);
  
  tft.setTextColor(ORANGE_RED, TFT_BLACK);
  tft.setTextFont(4);
  tft.setTextSize(1);
  tft.drawString("Processing", 120, 210);

  pageInitialized = true;
}

void runPage3_Anim() {
  // Animation: เรดาร์กระจายออก (Pulse Radar) ตรงกลางจอ
  
  // ลบวงเก่า
  tft.drawCircle(120, 120, p3_pulseR, TFT_BLACK);
  tft.drawCircle(120, 120, p3_pulseR - 1, TFT_BLACK); // ลบเส้นหนาหน่อย
  
  // ขยายขนาด
  p3_pulseR += 2;
  
  // ถ้าใหญ่เกินกรอบ ให้เริ่มใหม่จากตรงกลาง
  if (p3_pulseR > 80) p3_pulseR = 10;
  
  // วาดวงใหม่ (เปลี่ยนสีตามขนาดได้ถ้าต้องการ)
  tft.drawCircle(120, 120, p3_pulseR, 0xFFE0); // สีเหลือง
  tft.drawCircle(120, 120, p3_pulseR - 1, 0xFFE0);
}

				
			

ตัวอย่างที่ 2 การแสดงผลกราฟิกแบบ DMA (Direct Memory Access) UI หน้าจอ 1.3" หรือ 1.54" TFT LCD 240x240 Pixel Driver ST7789

2_TFT_LCD_ST7789_DM

อุปกรณ์ที่ใช้ในโปรเจกต์

  • บอร์ด ESP32 38PIN Massmore

  • TFT LCD 1.3″ 1.54″ 2.0″ (รุ่นใดก็ได้)

Arduino IDE Code

  • อย่าลืมติดตั้ง Library จากไฟล์บน Github 
    https://github.com/Massmore/SKU-1021-TFT-LCD-ST7789
				
					// Created by Bodmer 20/04/2021 as an example for:
// https://github.com/Bodmer/TFT_eSPI

// Number of circles to draw
#define CNUMBER 42

// Define the width and height according to the TFT and the
// available memory. The sprites will require:
//     DWIDTH * DHEIGHT * 2 bytes of RAM
// Note: for a 240 * 320 area this is 150 Kbytes!
#define DWIDTH  240
#define DHEIGHT 240

#include <TFT_eSPI.h>

// Library instance
TFT_eSPI    tft = TFT_eSPI();

// Create two sprites for a DMA toggle buffer
TFT_eSprite spr[2] = {TFT_eSprite(&tft), TFT_eSprite(&tft)};

// Pointers to start of Sprites in RAM (these are then "image" pointers)
uint16_t* sprPtr[2];

// Used for fps measuring
uint16_t counter = 0;
int32_t startMillis = millis();
uint16_t interval = 100;
String fps = "xx.xx fps";

// Structure to hold circle plotting parameters
typedef struct circle_t {
  int16_t   cx[CNUMBER] = { 0 }; // x coordinate of centre
  int16_t   cy[CNUMBER] = { 0 }; // y coordinate of centre
  int16_t   cr[CNUMBER] = { 0 }; // radius
  uint16_t col[CNUMBER] = { 0 }; // colour
  int16_t   dx[CNUMBER] = { 0 }; // x movement & direction
  int16_t   dy[CNUMBER] = { 0 }; // y movement & direction
} circle_param;

// Create the structure and get a pointer to it
circle_t *circle = new circle_param;

// #########################################################################
// Setup
// #########################################################################
void setup() {
  Serial.begin(115200);

  tft.init();
  tft.initDMA();
  tft.fillScreen(TFT_BLACK);

  // Create the 2 sprites, each is half the size of the screen
  sprPtr[0] = (uint16_t*)spr[0].createSprite(DWIDTH, DHEIGHT / 2);
  sprPtr[1] = (uint16_t*)spr[1].createSprite(DWIDTH, DHEIGHT / 2);

  // Move the sprite 1 coordinate datum upwards half the screen height
  // so from coordinate point of view it occupies the bottom of screen
  spr[1].setViewport(0, -DHEIGHT / 2, DWIDTH, DHEIGHT);

  // Define text datum for each Sprite
  spr[0].setTextDatum(MC_DATUM);
  spr[1].setTextDatum(MC_DATUM);

  // Seed the random number generator
  randomSeed(analogRead(A0));

  // Initialise circle parameters
  for (uint16_t i = 0; i < CNUMBER; i++) {
    circle->cr[i] = random(12, 24);
    circle->cx[i] = random(circle->cr[i], DWIDTH - circle->cr[i]);
    circle->cy[i] = random(circle->cr[i], DHEIGHT - circle->cr[i]);
    
    circle->col[i] = rainbow(4 * i);
    circle->dx[i] = random(1, 5);
    if (random(2)) circle->dx[i] = -circle->dx[i];
    circle->dy[i] = random(1, 5);
    if (random(2)) circle->dy[i] = -circle->dy[i];
  }

  tft.startWrite(); // TFT chip select held low permanently

  startMillis = millis();
}

// #########################################################################
// Loop
// #########################################################################
void loop() {
  drawUpdate(0); // Update top half
  drawUpdate(1); // Update bottom half

  // Calculate the fps every <interval> iterations.
  counter++;  
  if (counter % interval == 0) {
    long millisSinceUpdate = millis() - startMillis;
    fps = String((interval * 1000.0 / (millisSinceUpdate))) + " fps";
    Serial.println(fps);
    startMillis = millis();
  }
}

// #########################################################################
// Render circles to sprite 0 or 1 and initiate DMA
// #########################################################################
void drawUpdate (bool sel) {
  spr[sel].fillSprite(TFT_BLACK);
  for (uint16_t i = 0; i < CNUMBER; i++) {
    // Draw (Note sprite 1 datum was moved, so coordinates do not need to be adjusted
    spr[sel].fillCircle(circle->cx[i], circle->cy[i], circle->cr[i], circle->col[i]);
    spr[sel].drawCircle(circle->cx[i], circle->cy[i], circle->cr[i], TFT_WHITE);
    spr[sel].setTextColor(TFT_BLACK, circle->col[i]);
    spr[sel].drawNumber(i + 1, 1 + circle->cx[i], circle->cy[i], 2);
  }

  tft.pushImageDMA(0, sel * DHEIGHT / 2, DWIDTH, DHEIGHT / 2, sprPtr[sel]);

  // Update circle positions after bottom half has been drawn
  if (sel) {
    for (uint16_t i = 0; i < CNUMBER; i++) {
      circle->cx[i] += circle->dx[i];
      circle->cy[i] += circle->dy[i];
      if (circle->cx[i] <= circle->cr[i]) {
        circle->cx[i] = circle->cr[i];
        circle->dx[i] = -circle->dx[i];
      }
      else if (circle->cx[i] + circle->cr[i] >= DWIDTH - 1) {
        circle->cx[i] = DWIDTH - circle->cr[i] - 1;
        circle->dx[i] = -circle->dx[i];
      }
      if (circle->cy[i] <= circle->cr[i]) {
        circle->cy[i] = circle->cr[i];
        circle->dy[i] = -circle->dy[i];
      }
      else if (circle->cy[i] + circle->cr[i] >= DHEIGHT - 1) {
        circle->cy[i] = DHEIGHT - circle->cr[i] - 1;
        circle->dy[i] = -circle->dy[i];
      }
    }
  }
}

// #########################################################################
// Return a 16-bit rainbow colour
// #########################################################################
uint16_t rainbow(byte value)
{
  // If 'value' is in the range 0-159 it is converted to a spectrum colour
  // from 0 = red through to 127 = blue to 159 = violet
  // Extending the range to 0-191 adds a further violet to red band

  value = value % 192;

  byte red   = 0; // Red is the top 5 bits of a 16-bit colour value
  byte green = 0; // Green is the middle 6 bits, but only top 5 bits used here
  byte blue  = 0; // Blue is the bottom 5 bits

  byte sector = value >> 5;
  byte amplit = value & 0x1F;

  switch (sector)
  {
    case 0:
      red   = 0x1F;
      green = amplit; // Green ramps up
      blue  = 0;
      break;
    case 1:
      red   = 0x1F - amplit; // Red ramps down
      green = 0x1F;
      blue  = 0;
      break;
    case 2:
      red   = 0;
      green = 0x1F;
      blue  = amplit; // Blue ramps up
      break;
    case 3:
      red   = 0;
      green = 0x1F - amplit; // Green ramps down
      blue  = 0x1F;
      break;
    case 4:
      red   = amplit; // Red ramps up
      green = 0;
      blue  = 0x1F;
      break;
    case 5:
      red   = 0x1F;
      green = 0;
      blue  = 0x1F - amplit; // Blue ramps down
      break;
  }

  return red << 11 | green << 6 | blue;
}
				
			

ตัวอย่างที่ 3 การแสดงผลกราฟิก UI หน้าจอ 2.0" TFT LCD 320x240 Pixel Driver ST7789

3_TFT_LCD_ST7789_PNG

อุปกรณ์ที่ใช้ในโปรเจกต์

  • บอร์ด ESP32 38PIN Massmore

  • TFT LCD 1.3″ 1.54″ 2.0″ (รุ่นใดก็ได้)

Arduino IDE Code

  • อย่าลืมติดตั้ง Library จากไฟล์บน Github 
    https://github.com/Massmore/SKU-1021-TFT-LCD-ST7789
				
					
// This example renders a png file that is stored in a FLASH array
// using the PNGdec library (available via library manager).

// Image files can be converted to arrays using the tool here:
// https://notisrac.github.io/FileToCArray/
// To use this tool:
//   1. Drag and drop file on "Browse..." button
//   2. Tick box "Treat as binary"
//   3. Click "Convert"
//   4. Click "Save as file" and move the header file to sketch folder
//   5. Open the sketch in IDE
//   6. Include the header file containing the array (panda.h in this example)

// Include the PNG decoder library
#include <PNGdec.h>
#include "panda.h" // Image is stored here in an 8-bit array

PNG png; // PNG decoder instance

#define MAX_IMAGE_WIDTH 240 // Adjust for your images

int16_t xpos = 0;
int16_t ypos = 0;

// Include the TFT library https://github.com/Bodmer/TFT_eSPI
#include "SPI.h"
#include <TFT_eSPI.h>              // Hardware-specific library
TFT_eSPI tft = TFT_eSPI();         // Invoke custom library

//====================================================================================
//                                    Setup
//====================================================================================
void setup()
{
  Serial.begin(115200);
  Serial.println("\n\n Using the PNGdec library");

  // Initialise the TFT
  tft.begin();
  tft.fillScreen(TFT_BLACK);

  Serial.println("\r\nInitialisation done.");
}

//====================================================================================
//                                    Loop
//====================================================================================
void loop()
{
  int16_t rc = png.openFLASH((uint8_t *)panda, sizeof(panda), pngDraw);
  if (rc == PNG_SUCCESS) {
    Serial.println("Successfully opened png file");
    Serial.printf("image specs: (%d x %d), %d bpp, pixel type: %d\n", png.getWidth(), png.getHeight(), png.getBpp(), png.getPixelType());
    tft.startWrite();
    uint32_t dt = millis();
    rc = png.decode(NULL, 0);
    Serial.print(millis() - dt); Serial.println("ms");
    tft.endWrite();
    // png.close(); // not needed for memory->memory decode
  }
  delay(10000);
  tft.fillScreen(random(0x10000));
}


//=========================================v==========================================
//                                      pngDraw
//====================================================================================
// This next function will be called during decoding of the png file to
// render each image line to the TFT.  If you use a different TFT library
// you will need to adapt this function to suit.
// Callback function to draw pixels to the display
void pngDraw(PNGDRAW *pDraw) {
  uint16_t lineBuffer[MAX_IMAGE_WIDTH];
  png.getLineAsRGB565(pDraw, lineBuffer, PNG_RGB565_BIG_ENDIAN, 0xffffffff);
  tft.pushImage(xpos, ypos + pDraw->y, pDraw->iWidth, 1, lineBuffer);
}

				
			

อ้างอิง (reference)

Arduino Code

🎉บอร์ด ESP32 38PIN ชิพแท้จาก E...

฿350.00

🔥ชื่อสินค้า: บอร์ดขยาย หุ่นยนต...

฿590.00

แสดงความคิดเห็น