Community project

Mam Taki Sprzet 40 Szt Zestaw Kabli Do

ESP32
Photo of Mam Taki Sprzet 40 Szt Zestaw Kabli Do
Generated with AI

maciekptasior

Last updated September 2, 2026

This project builds a weather station display using an ESP32 microcontroller and a 1.69" TFT LCD screen. The display connects to Wi-Fi to fetch live weather data, showing conditions and forecasts on a colorful 240×280 pixel screen with custom segment-based number rendering.

The guide provides a complete parts list from the 40-piece cable kit, a wiring diagram showing all eight connections between the ESP32 and ST7789V3 display, step-by-step assembly instructions, and ready-to-use firmware that handles SPI communication, Wi-Fi connectivity, JSON weather parsing, and real-time clock synchronization.

Wiring diagram

Wiring diagram for Mam Taki Sprzet 40 Szt Zestaw Kabli Do

Gather all the parts

QtyComponent
1

TFT LCD 1.69″ 240×280 ST7789V3, SPI, 8-pin

1.69 in, 240×280

Mały kolorowy ekran, który pokazuje godzinę i aktualną pogodę pobraną przez Wi‑Fi.

Assemble it in 5 steps

1. Odłącz zasilanie i ustaw płytki

Odłącz USB‑C od ESP32. Wepnij ESP32 przez środkową szczelinę płytki stykowej, a ekran `tft_169` ustaw obok. Upewnij się, że każdy metalowy pin trafia do osobnego rzędu otworów.

  • Napisy przy pinach ekranu są małe; użyj światła z telefonu, aby odczytać je dokładnie.
  • Jeśli ekran ma nieprzylutowany pasek pinów, przylutuj go przed włożeniem do płytki.
  • Nie wkładaj ani nie przekładaj przewodów, gdy ESP32 jest podłączone przez USB — zwarcie może uszkodzić płytkę lub kabel.

2. Zrób dwie wspólne szyny zasilania

Wybierz boczną szynę z czerwonym znakiem plus jako szynę 3,3 V. Połącz pin 3V3 ESP32 z dowolnym otworem tej szyny czerwonym przewodem (zasilanie). Wybierz sąsiednią szynę z niebieskim znakiem minus i połącz ją z dowolnym pinem GND ESP32 czarnym przewodem (wspólny powrót prądu). Wszystkie otwory na jednej nieprzerwanej części długiej szyny są ze sobą połączone.

  • Znak plus na płytce nie oznacza automatycznie 5 V: po tym połączeniu jest to bezpieczna szyna 3,3 V.
  • Jeżeli długa szyna jest przerwana w połowie, użyj tylko jednej jej połowy albo połącz obie połówki krótkim przewodem.
  • Nie łącz szyny użytej dla ekranu z VIN ani 5V — 5 V może uszkodzić ekran.

3. Podłącz zasilanie i światło ekranu

Z czerwonej szyny 3,3 V poprowadź jeden przewód do pinu VCC ekranu `tft_169` (zasilanie) i drugi przewód do pinu BLK, BL lub LED ekranu (włącza podświetlenie). Z czarnej szyny GND poprowadź przewód do pinu GND ekranu (wspólny powrót prądu). Oba czerwone przewody mogą być wpięte w dwa różne otwory tej samej długiej szyny.

  • Nie potrzebujesz dwóch pinów 3V3 na ESP32: płytka stykowa rozdziela jeden pin 3V3 na VCC i BLK.
  • Jeżeli nie masz miejsca w tym samym otworze, użyj innego wolnego otworu tej samej szyny.
  • Nie zamieniaj VCC z GND — zamienione zasilanie może uszkodzić ekran.
  • Nie podłączaj BLK do GND, ponieważ ekran pozostanie ciemny.

4. Podłącz pięć przewodów obrazu

Połącz `tft_169` SCL lub SCK z D18 ESP32 (zegar danych), SDA lub MOSI z D23 (dane obrazu), CS z D4 (wybór ekranu), DC z D25 (sterowanie ekranem) oraz RES lub RST z D26 (reset ekranu).

  • SCL na tym ekranie może być opisany jako SCK, a SDA jako MOSI — to te same przewody w tym projekcie.
  • Szukaj na ESP32 oznaczeń D18, D23, D4, D25 i D26; liczba po literze D odpowiada numerowi GPIO.
  • Nie używaj D35 do żadnego z tych pięciu przewodów — ten pin potrafi tylko odbierać sygnał, a ekran potrzebuje sygnałów wysyłanych z ESP32.
  • Włożenie przewodu o jeden rząd obok może pozostawić ekran czarny mimo poprawnego programu.

5. Uruchom zegar i połącz Wi-Fi

Sprawdź jeszcze raz osiem nazw pinów ekranu, potem podłącz ESP32 przewodem USB‑C. Naciśnij Deploy w Schematik. Przy pierwszym uruchomieniu połącz telefon lub komputer z siecią Wi‑Fi „Zegar-ESP32”, otwórz stronę ustawień i podaj dane swojej domowej sieci. Zegar pobierze czas oraz pogodę dla Warszawy.

  • Jeżeli strona ustawień nie otworzy się sama, po połączeniu z siecią „Zegar-ESP32” wpisz w przeglądarce 192.168.4.1.
  • Dane pogody są odświeżane co około 10 minut.
  • Podawaj hasło tylko na stronie ustawień otwartej po połączeniu z własną siecią „Zegar-ESP32”.

Review all connections

1. Connections between "tft_169" and "ESP32"

Functiontft_169ESP32
powerVCC3V3
groundGNDGND
spiSCLGPIO 18
spiSDAGPIO 23
digitalCSGPIO 4
powerBLK3V3
digitalDCGPIO 25
digitalRESGPIO 26

Deploy the firmware

#include <Arduino.h>
#include <SPI.h>
#include <WiFi.h>
#include <WiFiManager.h>
#include <HTTPClient.h>
#include <ArduinoJson.h>
#include <time.h>

#define TFT_CS 4
#define TFT_DC 25
#define TFT_RST 26
#define TFT_MOSI 23


// Forward declarations
void segment(int x,int y,int n,int s,uint16_t c);
void number(const String &v,int x,int y,int s,uint16_t c);
void header();
void drawWeather();
void getWeather();
void clockUpdate();

constexpr int TFT_SCLK = 18;
constexpr uint16_t NAVY = 0x0861, SKY = 0x5DDF, PALE = 0xE73C, WHITE = 0xFFFF, YELLOW = 0xFFE0, RED = 0xF800;
constexpr unsigned long WEATHER_INTERVAL_MS = 600000UL;

class ST7789Direct {
 public:
  void begin() {
    pinMode(TFT_CS, OUTPUT); pinMode(TFT_DC, OUTPUT); pinMode(TFT_RST, OUTPUT);
    SPI.begin(TFT_SCLK, -1, TFT_MOSI, TFT_CS);
    digitalWrite(TFT_CS, HIGH); digitalWrite(TFT_RST, LOW); delay(20); digitalWrite(TFT_RST, HIGH); delay(120);
    cmd(0x01); delay(150); cmd(0x11); delay(120); cmdData(0x3A, 0x55); cmdData(0x36, 0x00);
    const uint8_t porch[] = {0x0C, 0x0C, 0x00, 0x33, 0x33};
    const uint8_t power[] = {0xA4, 0xA1};
    cmdData(0xB2, porch, sizeof(porch));
    cmdData(0xB7, 0x35); cmdData(0xBB, 0x19); cmdData(0xC0, 0x2C); cmdData(0xC2, 0x01);
    cmdData(0xC3, 0x12); cmdData(0xC4, 0x20); cmdData(0xC6, 0x0F); cmdData(0xD0, power, sizeof(power));
    cmd(0x21); cmd(0x29); delay(20); fill(0, 0, 240, 280, NAVY);
  }
  void fill(int x, int y, int w, int h, uint16_t c) {
    if (x < 0) { w += x; x = 0; } if (y < 0) { h += y; y = 0; }
    if (x + w > 240) w = 240 - x; if (y + h > 280) h = 280 - y; if (w <= 0 || h <= 0) return;
    uint8_t d[4]; d[0]=x>>8; d[1]=x; d[2]=(x+w-1)>>8; d[3]=x+w-1; cmdData(0x2A,d,4);
    d[0]=y>>8; d[1]=y; d[2]=(y+h-1)>>8; d[3]=y+h-1; cmdData(0x2B,d,4); cmd(0x2C);
    digitalWrite(TFT_DC,HIGH); digitalWrite(TFT_CS,LOW); SPI.beginTransaction(SPISettings(40000000, MSBFIRST, SPI_MODE0));
    uint8_t hi=c>>8, lo=c; for (uint32_t i=0;i<(uint32_t)w*h;i++) { SPI.transfer(hi); SPI.transfer(lo); }
    SPI.endTransaction(); digitalWrite(TFT_CS,HIGH);
  }
 private:
  void cmd(uint8_t c) { digitalWrite(TFT_DC,LOW); digitalWrite(TFT_CS,LOW); SPI.beginTransaction(SPISettings(40000000,MSBFIRST,SPI_MODE0)); SPI.transfer(c); SPI.endTransaction(); digitalWrite(TFT_CS,HIGH); }
  void cmdData(uint8_t c,uint8_t v) { cmdData(c,&v,1); }
  void cmdData(uint8_t c,const uint8_t *p,uint8_t n) { cmd(c); digitalWrite(TFT_DC,HIGH); digitalWrite(TFT_CS,LOW); SPI.beginTransaction(SPISettings(40000000,MSBFIRST,SPI_MODE0)); while(n--) SPI.transfer(*p++); SPI.endTransaction(); digitalWrite(TFT_CS,HIGH); }
};
ST7789Direct tft;

const uint8_t segs[] = {0x3F,0x06,0x5B,0x4F,0x66,0x6D,0x7D,0x07,0x7F,0x6F};
void segment(int x,int y,int n,int s,uint16_t c) { uint8_t m=segs[n]; int w=3*s, l=10*s; if(m&1)tft.fill(x+w,y,l,w,c); if(m&2)tft.fill(x+w+l,y+w,w,l,c); if(m&4)tft.fill(x+w+l,y+2*w+l,w,l,c); if(m&8)tft.fill(x+w,y+2*(w+l),l,w,c); if(m&16)tft.fill(x,y+2*w+l,w,l,c); if(m&32)tft.fill(x,y+w,w,l,c); if(m&64)tft.fill(x+w,y+w+l,l,w,c); }
void number(const String &v,int x,int y,int s,uint16_t c) { for (unsigned i=0;i<v.length();i++) { char q=v[i]; if(q>='0'&&q<='9') segment(x,y,q-'0',s,c); else if(q==':') { tft.fill(x+3*s,y+8*s,3*s,3*s,c); tft.fill(x+3*s,y+17*s,3*s,3*s,c); } else if(q=='.') tft.fill(x+3*s,y+25*s,3*s,3*s,c); else if(q=='-') tft.fill(x,y+13*s,10*s,3*s,c); x+=17*s; } }
void header() { tft.fill(0,0,240,280,NAVY); tft.fill(0,0,240,40,SKY); tft.fill(14,157,212,2,SKY); tft.fill(14,233,212,2,SKY); }
String weather = "--.-"; int weatherCode = -1; unsigned long lastWeather=0; String lastTime;
void drawWeather() { tft.fill(0,164,240,64,NAVY); number(weather,18,170,2,YELLOW); if(weatherCode==0) { tft.fill(175,178,32,32,YELLOW); } else if(weatherCode>=51) { tft.fill(165,182,50,16,PALE); for(int x=170;x<215;x+=12)tft.fill(x,204,3,12,SKY); } else { tft.fill(165,184,52,22,PALE); } }
void getWeather() { if(WiFi.status()!=WL_CONNECTED)return; HTTPClient h; h.begin("http://api.open-meteo.com/v1/forecast?latitude=52.2297&longitude=21.0122&current=temperature_2m,weather_code"); int r=h.GET(); if(r==HTTP_CODE_OK){JsonDocument d; if(!deserializeJson(d,h.getStream())) { weather=String((float)(d["current"]["temperature_2m"]|0.0),1); weatherCode=d["current"]["weather_code"]|-1; drawWeather(); }} h.end(); }
void clockUpdate() { struct tm tm; if(!getLocalTime(&tm,50)) return; char b[6]; strftime(b,sizeof b,"%H:%M",&tm); String now(b); if(now!=lastTime){lastTime=now; tft.fill(0,48,240,102,NAVY); number(now,18,67,3,WHITE);} }
void setup() { Serial.begin(115200); tft.begin(); header(); WiFiManager wm; wm.setConfigPortalTimeout(180); wm.autoConnect("Zegar-ESP32"); configTzTime("CET-1CEST,M3.5.0,M10.5.0/3","pool.ntp.org","time.nist.gov"); clockUpdate(); getWeather(); lastWeather=millis(); }
void loop() { clockUpdate(); unsigned long n=millis(); if(n-lastWeather>=WEATHER_INTERVAL_MS){lastWeather=n;getWeather();} delay(50); }

Remix this project

Make it yours in one click

Open a full copy of this project in your own Schematik workspace — diagram, code, parts, and assembly steps included. Swap the sensor, add features, or redesign the whole thing with AI. The author's original stays untouched.

Open in Schematik