1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 | #include <SPI.h> #include <Adafruit_GFX.h> #include <Adafruit_ST7789.h> #define TFT_MOSI 19 // SDA (SPI MOSI) #define TFT_SCLK 18 // SCL (SPI SCK) #define TFT_CS 5 #define TFT_DC 16 #define TFT_RST 23 Adafruit_ST7789 tft = Adafruit_ST7789(TFT_CS, TFT_DC, TFT_RST); static inline uint16_t RGB565(uint8_t r, uint8_t g, uint8_t b) { return ((r & 0xF8) << 8) | ((g & 0xFC) << 3) | (b >> 3); } // 畫口鼻白毛區(固定底圖) void drawMuzzleBase(int cx, int cy) { uint16_t furLight = RGB565(235, 228, 210); uint16_t shadow = RGB565(160, 150, 135); tft.fillScreen(ST77XX_BLACK); // 白毛區 tft.fillCircle(cx - 55, cy + 10, 55, furLight); tft.fillCircle(cx + 55, cy + 10, 55, furLight); tft.fillRoundRect(cx - 90, cy - 25, 180, 110, 28, furLight); // 下巴陰影 tft.fillRoundRect(cx - 85, cy + 60, 170, 22, 12, shadow); tft.fillRoundRect(cx - 40, cy + 55, 80, 10, 5, RGB565(120,110,100)); // 鬍鬚點 uint16_t dotDark = RGB565(70, 70, 70); int dotY1 = cy + 6; int dotY2 = cy + 26; for (int k = 0; k < 3; k++) { tft.fillCircle(cx - 55 - k * 12, dotY1 + k * 2, 2, dotDark); tft.fillCircle(cx - 55 - k * 12, dotY2 + k * 2, 2, dotDark); tft.fillCircle(cx + 55 + k * 12, dotY1 + k * 2, 2, dotDark); tft.fillCircle(cx + 55 + k * 12, dotY2 + k * 2, 2, dotDark); } } // 畫「閉合」虎嘴 void drawMouthClosed(int cx, int cy) { uint16_t lineDark = RGB565(40, 40, 40); // 人中線 tft.drawLine(cx, cy - 5, cx, cy + 20, lineDark); tft.drawLine(cx - 1, cy - 5, cx - 1, cy + 20, RGB565(80,80,80)); // 上唇弧線 int mouthY = cy + 18; for (int i = 0; i < 34; i++) { int xL = cx - i; int yL = mouthY + (i * i) / 95; tft.drawPixel(xL, yL, lineDark); tft.drawPixel(xL, yL + 1, lineDark); int xR = cx + i; int yR = mouthY + (i * i) / 95; tft.drawPixel(xR, yR, lineDark); tft.drawPixel(xR, yR + 1, lineDark); } // 嘴角加深 tft.fillCircle(cx - 36, mouthY + 12, 3, lineDark); tft.fillCircle(cx + 36, mouthY + 12, 3, lineDark); // 嘴中間小暗線 tft.fillRoundRect(cx - 10, mouthY + 20, 20, 4, 2, RGB565(90,80,70)); } // 畫「張開」虎嘴 void drawMouthOpen(int cx, int cy) { uint16_t lineDark = RGB565(40, 40, 40); uint16_t mouthIn = RGB565(15, 15, 15); // 口腔黑 uint16_t tongue = RGB565(210, 120, 120); // 舌頭粉 // 人中線(到上唇) tft.drawLine(cx, cy - 5, cx, cy + 10, lineDark); tft.drawLine(cx - 1, cy - 5, cx - 1, cy + 10, RGB565(80,80,80)); // 上唇弧線(稍微更彎一點) int mouthY = cy + 16; for (int i = 0; i < 36; i++) { int bend = (i * i) / 85; int xL = cx - i; int yL = mouthY + bend; tft.drawPixel(xL, yL, lineDark); tft.drawPixel(xL, yL + 1, lineDark); int xR = cx + i; int yR = mouthY + bend; tft.drawPixel(xR, yR, lineDark); tft.drawPixel(xR, yR + 1, lineDark); } // 嘴角 tft.fillCircle(cx - 38, mouthY + 14, 3, lineDark); tft.fillCircle(cx + 38, mouthY + 14, 3, lineDark); // 口腔(張開的洞) // 用圓角矩形 + 下半圓做出比較像嘴巴的形狀 int w = 90, h = 45; int x = cx - w/2; int y = cy + 28; tft.fillRoundRect(x, y, w, h, 18, mouthIn); tft.fillCircle(cx, y + h, 22, mouthIn); // 下唇線(口腔上緣加一條暗線) tft.drawRoundRect(x, y, w, h, 18, RGB565(60,50,45)); // 舌頭 tft.fillRoundRect(cx - 22, y + 18, 44, 20, 10, tongue); tft.fillCircle(cx, y + 36, 14, tongue); } void drawTigerMouthFrame(bool open) { int cx = tft.width() / 2; int cy = tft.height() / 2; drawMuzzleBase(cx, cy); if (open) drawMouthOpen(cx, cy); else drawMouthClosed(cx, cy); } void setup() { SPI.begin(TFT_SCLK, -1, TFT_MOSI, TFT_CS); tft.init(240, 320); // 若你確定是 170x320 再改成 tft.init(170, 320) tft.setRotation(1); drawTigerMouthFrame(false); // 先閉合 } void loop() { // 2 秒後張開 delay(2000); drawTigerMouthFrame(true); // 2 秒後閉合 delay(2000); drawTigerMouthFrame(false); } |
「智慧生活科技專業社群」由 Nantou.py 使用者社群與國立虎尾科技大學電機資訊學院共同維護,匯集關注Python、人工智慧、物聯網與智慧生活應用的教師、學生及實務工作者。本社群以「科技融入生活、教學連結場域、知識促進共好」為核心,分享Python程式設計、AI協作學習、AIoT、網際網路與雲端服務、智慧農業、福祉科技、永續發展及USR社會實踐等內容,並將技術導入課堂、社區與真實生活場域。部分文章運用生成式AI協助資料整理、內容架構、程式範例與文字潤飾,文章主題、場域經驗、內容查核及最終修訂則由作者與社群成員負責。我們期待透過人與AI協作,讓科技成為改善生活、連結世代、支持地方與實踐永續的力量。
2026年2月12日 星期四
[OTTO GO]動畫測試-張閉嘴
訂閱:
張貼留言 (Atom)
沒有留言:
張貼留言