Základy v MicroPythonu

Krok za krokem od prvního blikání LEDky až po vlastní mini hru. Žádné předchozí zkušenosti s Pythonem nepotřebujete – jdeme polopaticky.

Co je MicroPython #

MicroPython je odlehčená verze Pythonu navržená přímo pro mikrokontroléry. Píšete v ní stejným jazykem, jako kdybyste programovali na počítači, ale váš kód běží přímo v Picopadu. Když ho připojíte přes USB, můžete s ním v reálném čase komunikovat – napíšete řádek, stisknete Enter a Picopad ho hned vykoná.

Picopad podporuje tři způsoby programování. Tabulka pomůže vybrat:

Jazyk Pro koho Tempo
MicroPython Začátečníci i hobby projekty. Jednoduchá syntaxe, okamžité výsledky. Pomalejší, ale na hry a senzory bohatě stačí.
CircuitPython Velmi podobný MicroPythonu, ale s knihovnami od Adafruitu. Srovnatelný s MicroPythonem.
C / C++ Pokročilí, kteří chtějí maximální výkon (např. emulátory). Nejrychlejší, ale složitější nastavení projektu.

V tomhle tutoriálu jdeme cestou MicroPythonu. Jakmile zvládnete základy, přechod na C nebo CircuitPython je už jen otázka chuti.

Co budete potřebovat: sestavený Picopad, USB kabel typu Micro-USB, počítač s Windows / macOS / Linuxem a editor Thonny (zdarma). Stažení a instalaci probereme v další kapitole.

Instalace firmware #

Než budete moct psát programy v MicroPythonu, musíte do Picopadu nahrát MicroPython firmware. Je to jednorázová operace – nahrané jednou, drží se v zařízení a přepisuje se jen tehdy, když chcete jiný jazyk.

Postup je v samostatném návodu: Jak nainstalovat MicroPython →

Tip: Picopad používá čistý oficiální MicroPython z micropython.org – žádný speciální Pajenicko build. Picopad Wifi i Picopad Pro mají modul Raspberry Pi Pico W, takže pro oba aktuální modely se stahuje stejný build RPI_PICO_W.

První program – Hello Picopad #

Když máte MicroPython nahraný, je čas něco napsat. Použijeme editor Thonny, který je zdarma a má MicroPython podporu zabudovanou.

1) Nainstalujte Thonny

Stáhněte si Thonny z thonny.org a nainstalujte. Při prvním spuštění vyberte v dialogu „Initial settings" volbu Standard.

2) Připojte Picopad a vyberte interpreter

Připojte Picopad přes USB (vypnutý zapněte). V Thonny otevřete menu Run → Configure interpreter… a v záložce Interpreter vyberte:

  • Interpreter: MicroPython (Raspberry Pi Pico)
  • Port: ten, kde se Picopad zobrazuje (např. /dev/cu.usbmodem... na macOS, COM3 na Windows)

Po potvrzení uvidíte dole v okně Shell řádek MicroPython v1.xx ... a >>>. To je REPL – interaktivní konzole MicroPythonu. Můžete do něj psát a Picopad vám hned odpoví.

3) První řádek v REPLu

Klikněte do okna Shell a napište:

print("Ahoj, Picopade!")

Po Enteru se hned pod tím zobrazí odpověď:

Ahoj, Picopade!

Gratulujeme – právě jste na Picopadu spustili první program. REPL je super na rychlé experimenty, ale jakmile odpojíte USB, vše se ztratí. Pro programy, které mají běžet samostatně, použijeme soubor main.py.

4) Blikání LEDkou (soubor main.py)

V Thonny otevřete nový soubor (File → New) a napište:

from machine import Pin
from time import sleep

led = Pin(22, Pin.OUT)

while True:
    led.value(0)   # rozsvítí (LED je aktivní v low)
    sleep(0.5)
    led.value(1)   # zhasne
    sleep(0.5)

Soubor uložte přímo do Picopadu jako main.py: File → Save as…, vyberte Raspberry Pi Pico a název main.py.

Stiskněte zelené tlačítko Run (nebo F5). Žlutá uživatelská LED na horní hraně Picopadu začne blikat – jednou za sekundu.

Proč 0 znamená rozsvítit? Uživatelská LED je zapojená tak, že svítí, když je její pin v logické nule (LOW). To je běžný hardwarový trik – v dalších kapitolách vysvětlíme.

5) Co dál

Soubor main.py se spustí pokaždé, když Picopad zapnete. Můžete USB odpojit, zapnout Picopad samostatně – LEDka bude blikat. Tím končí „Hello world" část tutoriálu. V dalších kapitolách budeme stavět na tomto základu: ovládání displeje, čtení tlačítek, hraní zvuků a další.

Anatomie Picopadu #

Než se vrhneme na jednotlivé HW prvky, podívejme se, co je kde. Diagram níže je vyrenderovaný přímo z výrobního schématu Picopadu, takže pozice tlačítek a LEDek jsou přesně tam, kde je najdete na své konzoli.

Picopad – přední strana s popisky tlačítek a LED
Přední strana Picopadu – D-pad, tlačítka A/B/X/Y a stavové LEDky

Mapa GPIO pinů

Picopad používá Raspberry Pi Pico jako mozek. Tady je přehled, který Pico pin (GPIO číslo) je s čím propojený. V kódu se na ně budete odkazovat právě pomocí těchto čísel.

Funkce GPIO Poznámka
Displej (SPI 0)SCK=18, MOSI=19+ CS=21, DC=17, RES=20, podsvícení=16
D-pad ↑ ↓ ← →UP=4, DOWN=5, LEFT=3, RIGHT=2Vstup s pull-up, sepnuté = LOW
Tlačítka A B X YA=7, B=6, X=9, Y=8Stejně jako D-pad, sepnuté = LOW
Uživatelská LED22Aktivní v LOW (svítí, když je 0)
Bzučák / reproduktor15Ovládá se přes PWM
microSD karta (SPI 1)SCK=10, MOSI=11, MISO=12, CS=13Samostatná SPI sběrnice
Měření baterie (VSYS)ADC 3 (pin 29)Detail v kapitole Baterie

Externí konektor J2

Na boku Picopadu je 12pinový konektor, kterým se dají připojovat senzory a moduly (např. teplotní čidlo, ultrazvukový dálkoměr, fotorezistor). Vyvedené piny:

  • Napájení: 3.3 V, GND, BAT (přímo z baterie), ADC_VREF, AGND
  • Digitální / komunikace: GPIO 0, GPIO 1 (lze použít jako UART, I2C nebo obecně), GPIO 14
  • Analogové vstupy: GPIO 26 (ADC0), GPIO 27 (ADC1), GPIO 28 (ADC2)

Tip: v kapitole „Externí konektor" si ukážeme konkrétní příklad – přečtení hodnoty z fotorezistoru přes ADC a zobrazení na displeji.

Displej #

Picopad má 2palcový barevný IPS displej 320 × 240 pixelů s ovladačem ST7789. Ovládá se přes SPI sběrnici. MicroPython sám displej řídit neumí, potřebujeme k tomu knihovnu (driver) a font.

1) Stáhněte si knihovnu z GitHubu

Pajeníčko má knihovnu i fonty na GitHubu: Pajenicko/Picopad → micropython/lib. Stáhněte celou složku lib. Měli byste mít:

lib/
├── st7789.py
└── fonts/
    ├── fonts_vga1_16x32.py
    └── fonts_vga2_8x8.py

2) Nahrajte knihovnu na Picopad

V Thonny otevřete View → Files. Levý panel ukazuje váš počítač, pravý Picopad. Najděte na disku staženou složku lib, klikněte na ni pravým a zvolte Upload to /. Po chvilce uvidíte složku lib i v pravém panelu.

Ověření: v Thonny shellu napište import os; os.listdir(). Mezi soubory by měla být složka lib.

3) Inicializace displeje

Aby displej fungoval, musíme mu říct, na kterých GPIO pinech je připojený a jak komunikovat. Tenhle blok kódu uvidíte ve většině programů – je to standardní úvod:

from machine import Pin, SPI
from fonts import fonts_vga1_16x32
import st7789

spi = SPI(0, 62500000, sck=Pin(18), mosi=Pin(19), polarity=1, phase=1)
display = st7789.ST7789(
    spi, 320, 240,
    reset=Pin(20, Pin.OUT),
    dc=Pin(17, Pin.OUT),
    cs=Pin(21, Pin.OUT),
    backlight=Pin(16, Pin.OUT),
    rotation=1,
)

4) První text na displeji

Vyplňte celý displej černou a napište text:

display.fill(0x0000)                                       # černé pozadí
display.text(fonts_vga1_16x32, "Ahoj, Picopade!",
             20, 100, 0xFFE0, 0x0000)                       # žlutý text

Parametry funkce text: font, řetězec, x, y, barva textu, barva pozadí. Souřadnice (0, 0) je v levém horním rohu, x roste doprava, y dolů.

5) Barvy v RGB565

Displej používá 16bitové barvy ve formátu RGB565. V kódu je píšeme jako šestnáctkové číslo. Tady je rychlá cheat sheet:

BarvaRGB565
Černá0x0000
Bílá0xFFFF
Červená0xF800
Zelená0x07E0
Modrá0x001F
Žlutá0xFFE0
Azurová0x07FF

6) Co zkusit dál

  • display.fill_rect(x, y, w, h, color) – vyplněný obdélník
  • display.pixel(x, y, color) – jeden pixel
  • display.line(x1, y1, x2, y2, color) – čára
  • Zkuste menší font fonts_vga2_8x8 – víc textu se vejde

Tlačítka #

Picopad má 8 herních tlačítek: 4 šipky (D-pad) a 4 akční (A, B, X, Y). Všechna fungují stejně – jsou připojená k GPIO pinům s vnitřním pull-up rezistorem. To znamená:

  • Když je tlačítko nestisknuté, pin je v logické 1 (HIGH).
  • Když ho stisknete, propojí se na zem a pin spadne na 0 (LOW).

V kódu se tedy ptáme „je hodnota pinu 0?" a podle toho víme, že je tlačítko stisknuté.

Definice tlačítek

from machine import Pin

buttons = {
    "LEFT":  Pin(3, Pin.IN, Pin.PULL_UP),
    "RIGHT": Pin(2, Pin.IN, Pin.PULL_UP),
    "UP":    Pin(4, Pin.IN, Pin.PULL_UP),
    "DOWN":  Pin(5, Pin.IN, Pin.PULL_UP),
    "A":     Pin(7, Pin.IN, Pin.PULL_UP),
    "B":     Pin(6, Pin.IN, Pin.PULL_UP),
    "X":     Pin(9, Pin.IN, Pin.PULL_UP),
    "Y":     Pin(8, Pin.IN, Pin.PULL_UP),
}

Vypsat stisknuté tlačítko na displej

Spojíme tlačítka s tím, co jsme se naučili o displeji. Při každém průběhu smyčky zkontrolujeme všechna tlačítka a pokud je nějaké stisknuté, zobrazíme jeho jméno:

from machine import Pin, SPI
from fonts import fonts_vga1_16x32
from time import sleep
import st7789

# Inicializace displeje (zkráceno – viz kapitola Displej)
spi = SPI(0, 62500000, sck=Pin(18), mosi=Pin(19), polarity=1, phase=1)
display = st7789.ST7789(spi, 320, 240,
    reset=Pin(20, Pin.OUT), dc=Pin(17, Pin.OUT),
    cs=Pin(21, Pin.OUT), backlight=Pin(16, Pin.OUT),
    rotation=1)

buttons = {
    "LEFT":  Pin(3, Pin.IN, Pin.PULL_UP),
    "RIGHT": Pin(2, Pin.IN, Pin.PULL_UP),
    "UP":    Pin(4, Pin.IN, Pin.PULL_UP),
    "DOWN":  Pin(5, Pin.IN, Pin.PULL_UP),
    "A":     Pin(7, Pin.IN, Pin.PULL_UP),
    "B":     Pin(6, Pin.IN, Pin.PULL_UP),
    "X":     Pin(9, Pin.IN, Pin.PULL_UP),
    "Y":     Pin(8, Pin.IN, Pin.PULL_UP),
}

display.fill(0x0000)
display.text(fonts_vga1_16x32, "Stiskni tlacitko",
             40, 100, 0x07FF, 0x0000)

last = ""
while True:
    pressed = ""
    for name, btn in buttons.items():
        if btn.value() == 0:
            pressed = name
            break
    if pressed != last:
        display.fill(0x0000)
        if pressed:
            display.text(fonts_vga1_16x32, pressed,
                         100, 100, 0xFFFF, 0x0000)
        else:
            display.text(fonts_vga1_16x32, "Stiskni tlacitko",
                         40, 100, 0x07FF, 0x0000)
        last = pressed
    sleep(0.05)

Trik s proměnnou last zajistí, že displej nepřekreslujeme pořád dokola – jen když se změní stav. Tím i pohyb na displeji vypadá plynule.

Co je „debounce"? Mechanická tlačítka při stisku několikrát rychle „cinknou" (zákmity). Pro hru s odezvou 50 ms (jako tady) to nevadí. Kdybyste počítali stisky, narazíte na to – v takovém případě stačí přidat krátké zpoždění po detekci stisku, nebo testovat dvakrát po sobě.

Uživatelská LED #

Žlutá LEDka (popisek USR na horní hraně Picopadu) je připojená na GPIO 22. Slouží jako stavový indikátor – můžete ji použít pro jakékoliv signalizace (bliká při čekání, svítí když probíhá akce…).

Aktivní v LOW – proč 0 znamená svítí

LEDka je na desce zapojená mezi 3,3 V a GPIO pin. Aby svítila, musí proud téct směrem do pinu, takže pin musí být na 0 V (LOW). Když je pin v 1 (HIGH = 3,3 V), na LEDce není napětí a LEDka je zhasnutá.

V kódu si to pamatujte takhle: led.value(0) = svítí, led.value(1) = zhaslá. Stejnou logiku používá většina vestavěných LED u mikrokontrolérů.

Blikání

from machine import Pin
from time import sleep

led = Pin(22, Pin.OUT)
led.value(1)  # začneme zhasnutě

while True:
    led.value(0)   # rozsvítit
    sleep(0.5)
    led.value(1)   # zhasnout
    sleep(0.5)

Plynulé stmívání přes PWM

Místo „svítí / nesvítí" můžeme regulovat jas pomocí PWM (rychlé pulzování). Tady je „dechový" efekt – LEDka pomalu rozsvítí a zase zhasne:

from machine import Pin, PWM
from time import sleep

led = PWM(Pin(22))
led.freq(1000)   # 1 kHz – oko nevnímá jako blikání

while True:
    # rozsvítit (jas roste)
    for jas in range(0, 65536, 500):
        led.duty_u16(65535 - jas)   # active-low: vyšší duty = míň světla
        sleep(0.005)
    # zhasnout (jas klesá)
    for jas in range(65535, 0, -500):
        led.duty_u16(65535 - jas)
        sleep(0.005)

duty_u16 přijímá hodnotu 0–65535. Kvůli zapojení v low logice musíme hodnotu obrátit (65535 - jas), aby vyšší jas znamenal jasnější LED.

LED + tlačítko

A teď to spojíme: stisk tlačítka A LEDku přepne (stiskneš → svítí, stiskneš znovu → zhasne).

from machine import Pin
from time import sleep

led = Pin(22, Pin.OUT)
led.value(1)
button_a = Pin(7, Pin.IN, Pin.PULL_UP)

svitit = False
while True:
    if button_a.value() == 0:
        svitit = not svitit
        led.value(0 if svitit else 1)
        sleep(0.2)   # jednoduchý debounce

microSD karta #

Picopad má slot na microSD kartu na zadní straně. Karta visí na samostatné SPI sběrnici (SPI 1), takže nekonkuruje displeji – můžete v aplikaci pracovat s obojím najednou. Hodí se na ukládání skóre, log souborů, obrázků nebo herních dat.

1) Stáhněte si SDCard knihovnu

MicroPython má oficiální driver v micropython-lib. Stáhněte soubor sdcard.py a nahrajte ho do složky lib na Picopadu (stejně jako jste dělali u st7789.py).

2) Připojení karty

from machine import Pin, SPI
import sdcard
import os

# microSD na SPI 1
spi = SPI(1, baudrate=1_000_000,
          sck=Pin(10), mosi=Pin(11), miso=Pin(12))
sd = sdcard.SDCard(spi, Pin(13))

os.mount(sd, "/sd")
print(os.listdir("/sd"))

Po os.mount se karta tváří jako další složka v souborovém systému Picopadu (cesta /sd). Můžete v ní číst a zapisovat běžnými Pythoními operacemi.

3) Zápis a čtení souboru

# zapsat
with open("/sd/skore.txt", "w") as f:
    f.write("nejlepsi: 1240\n")

# přečíst zpátky
with open("/sd/skore.txt") as f:
    print(f.read())

4) Vypsat obsah karty na displej

# (předpokládáme, že display už je inicializovaný)
display.fill(0x0000)
y = 10
for name in os.listdir("/sd"):
    display.text(fonts_vga2_8x8, name[:38], 10, y, 0xFFFF, 0x0000)
    y += 12
    if y > 230:
        break

Před vyjmutím karty volejte os.umount("/sd"), jinak hrozí, že se neuložená data ztratí.

Bzučák a zvuk #

Reproduktor Picopadu je řízený přes PWM (rychlé pulzování) z GPIO 15. Frekvence pulzů určuje výšku tónu, šířka pulzu hlasitost. Není to vysoce kvalitní zvuk, ale na herní pípnutí, melodie a zvukové efekty stačí.

Funkce pro hraní tónu

from machine import Pin, PWM
from time import sleep

buzzer = PWM(Pin(15))

def tone(freq, duration_s, gap_s=0.05):
    """Zahraj tón o dané frekvenci a délce."""
    buzzer.duty_u16(int(65535 * 0.05))   # cca 5 % – tichý, ale slyšitelný
    buzzer.freq(freq)
    sleep(duration_s)
    buzzer.duty_u16(0)
    sleep(gap_s)

Volání buzzer.duty_u16(0) tón vypne. Krátká pauza gap_s mezi tóny je užitečná – jinak by se sousední tóny slily.

Frekvence not

NotaFrekvence (Hz)
C4 (střední C)262
D4294
E4330
F4349
G4392
A4 (komorní A)440
H4 (B)494
C5523

O oktávu výš = frekvence × 2, o oktávu níž = / 2.

Krátká melodie

# Začátek "Ódy na radost"
melodie = [
    (330, 0.4), (330, 0.4), (349, 0.4), (392, 0.4),
    (392, 0.4), (349, 0.4), (330, 0.4), (294, 0.4),
    (262, 0.4), (262, 0.4), (294, 0.4), (330, 0.4),
    (330, 0.6), (294, 0.2), (294, 0.6),
]

for freq, dur in melodie:
    tone(freq, dur)
buzzer.deinit()

Tlačítka jako klávesy

Stiskem tlačítek hrajeme různé noty – jednoduchý hudební nástroj:

from machine import Pin, PWM
from time import sleep

buzzer = PWM(Pin(15))
buzzer.duty_u16(0)

klavesy = {
    Pin(3, Pin.IN, Pin.PULL_UP): 262,   # LEFT  → C
    Pin(4, Pin.IN, Pin.PULL_UP): 330,   # UP    → E
    Pin(5, Pin.IN, Pin.PULL_UP): 392,   # DOWN  → G
    Pin(2, Pin.IN, Pin.PULL_UP): 523,   # RIGHT → C (oktáva)
}

while True:
    hraje = False
    for btn, freq in klavesy.items():
        if btn.value() == 0:
            buzzer.duty_u16(int(65535 * 0.05))
            buzzer.freq(freq)
            hraje = True
            break
    if not hraje:
        buzzer.duty_u16(0)
    sleep(0.02)

Picopad Pro: nabízí 3.5mm sluchátkový jack a vylepšený zesilovač – pro hraní cestou ve vlaku ideální, hlasitost na sluchátkách je pohodlná a okolí neruší. Hardwarový mute spínač zase utne reproduktor jedním cvaknutím, aniž byste museli sahat do kódu.

Měření baterie #

Picopad jede z Li-ion baterie (500 mAh u Picopad Wifi, 600 mAh u Picopad Pro). Pico W umí změřit své napájecí napětí (VSYS) přes vnitřní ADC a z něj se dá odhadnout, jak je baterie nabitá. Plně nabitý článek má cca 4,2 V, vybitý 3,2 V. V kódu vrátíme aktuální napětí na pinu 29 (ADC kanál 3).

Funkce vsys()

U Pico W je pin 29 sdílený s WiFi modulem, takže před měřením WiFi dočasně vypneme a po změření zase obnovíme. Tato funkce funguje na obou aktuálních modelech (Wifi i Pro), protože oba mají Pico W:

from machine import Pin, ADC
import network

def vsys():
    wlan = network.WLAN(network.STA_IF)
    wifi_byla_zapnuta = wlan.active()
    try:
        wlan.active(False)
        Pin(25, mode=Pin.OUT, pull=Pin.PULL_DOWN).high()
        Pin(29, Pin.IN)
        adc = ADC(3)
        # dělič napětí na desce dělí 1:3, ADC referenční 3.3 V
        napeti = adc.read_u16() * 3 * 3.3 / 65535
        napeti += 0.311   # kompenzace úbytku na ochranné diodě
        return napeti
    finally:
        Pin(29, Pin.ALT, pull=Pin.PULL_DOWN, alt=7)
        wlan.active(wifi_byla_zapnuta)

print(f"VSYS = {vsys():.2f} V")

Stav baterie na displeji

from time import sleep

while True:
    v = vsys()
    procenta = max(0, min(100, int((v - 3.2) / (4.2 - 3.2) * 100)))
    display.fill(0x0000)
    display.text(fonts_vga1_16x32, f"{v:.2f} V",  60, 80,  0xFFE0, 0x0000)
    display.text(fonts_vga1_16x32, f"{procenta} %", 60, 130, 0xFFFF, 0x0000)
    sleep(2)

Pozor na linearizaci: převod „napětí → procenta" je hodně přibližný. Lithium baterie totiž vybíjení neklesá lineárně. Pro hru to stačí, ale pro precizní indikaci se používají složitější tabulky.

Externí konektor #

Konektor J2 na boku Picopadu otevírá dveře k vlastním rozšířením. Pajeníčko má v nabídce hotové moduly (teplotní čidlo DS18B20, ultrazvukový dálkoměr HC-SR04, fotorezistor GL5516), ale klidně si můžete připojit cokoliv – senzor pohybu, OLED displej, RFID čtečku.

Připomenutí pinů z kapitoly Anatomie:

  • Napájení: 3.3 V, GND, BAT, ADC_VREF, AGND
  • Digitální: GPIO 0, GPIO 1, GPIO 14
  • Analog (ADC): GPIO 26 (ADC0), GPIO 27 (ADC1), GPIO 28 (ADC2)

Příklad: fotorezistor (světelný senzor)

Fotorezistor mění odpor podle množství dopadajícího světla. Jeden konec připojíme na 3.3 V, druhý na ADC pin a přes pull-down rezistor (~10 kΩ) na GND. ADC pak čte napětí, které stoupá s intenzitou světla.

from machine import Pin, ADC
from time import sleep

photoresistor = ADC(Pin(26))   # GPIO 26 = ADC0 na konektoru J2

while True:
    surovy = photoresistor.read_u16()      # 0 - 65535
    procenta = surovy * 100 // 65535
    print(f"Svetlo: {procenta}%")
    sleep(0.2)

Sloupcový indikátor na displeji

Prahová hodnota visí na světelných podmínkách. Místo čísel si nakresleme „svíčku" – sloupec, jehož výška odpovídá intenzitě:

# (display je inicializovaný)
display.fill(0x0000)
display.text(fonts_vga1_16x32, "Foto senzor", 70, 20, 0x07FF, 0x0000)

while True:
    surovy = photoresistor.read_u16()
    vyska = int(surovy / 65535 * 180)        # 0 - 180 px

    # vymazat starý sloupec
    display.fill_rect(140, 50, 40, 180, 0x0000)
    # vykreslit nový (od zdola)
    display.fill_rect(140, 50 + 180 - vyska, 40, vyska, 0xFFE0)
    sleep(0.05)

Hotové moduly od Pajenicka

Pajeníčko prodává tři přizpůsobené moduly s konektorem, který se cvakne na J2. Příklad kódu pro každý je v repozitáři Picopadu:

Picopad Pro – další konektory: kromě klasického J2 má Pro PICOBUS rozšiřující konektor pro „cvakací" karty (např. další tlačítka, gamepady, RTC moduly) a samostatný I2C konektor kompatibilní se standardem Stemma/Qwiic – do něj zapojíte stovky hotových senzorů a OLED displejů od Adafruitu, Sparkfunu a komunity bez pájení.

WiFi #

Picopad Wifi i Picopad Pro mají modul Raspberry Pi Pico W, takže máte k dispozici 2.4 GHz WiFi 802.11n a Bluetooth 5.2 v ceně.

Sanity check

Modul network je k dispozici jen na Pico W. U aktuálních Picopadů (Wifi i Pro) by měl tedy projít:

try:
    import network
    print("Pico W - WiFi je k dispozici")
except ImportError:
    print("Pico bez wifi - tahle kapitola neni pro vas")

Sken dostupných sítí

import network

wlan = network.WLAN(network.STA_IF)
wlan.active(True)

site = wlan.scan()
for s in site:
    ssid = s[0].decode("utf-8", "replace")
    rssi = s[3]
    print(f"{ssid:30s}  signal: {rssi} dBm")

Připojení k síti

import network
from time import sleep

SSID = "MojeSit"
HESLO = "tajneheslo"

wlan = network.WLAN(network.STA_IF)
wlan.active(True)
wlan.connect(SSID, HESLO)

# počkat až se připojí (max 15 s)
for _ in range(30):
    if wlan.isconnected():
        break
    sleep(0.5)

if wlan.isconnected():
    ip, mask, gw, dns = wlan.ifconfig()
    print(f"Pripojeno! IP: {ip}")
else:
    print("Nepodarilo se pripojit")

HTTP požadavek a zobrazení na displeji

Zkusíme stáhnout aktuální čas z veřejné API a vypsat ho na displej:

import urequests

# zařízení musí být před tímhle připojené k WiFi
r = urequests.get("https://worldtimeapi.org/api/timezone/Europe/Prague")
data = r.json()
r.close()

cas = data["datetime"][11:19]   # vyřízneme HH:MM:SS
display.fill(0x0000)
display.text(fonts_vga1_16x32, "Prazsky cas:", 50, 70, 0x07FF, 0x0000)
display.text(fonts_vga1_16x32, cas, 100, 120, 0xFFE0, 0x0000)

HTTPS upozornění: urequests v základním MicroPythonu neověřuje certifikáty. Pro hobby projekty to nevadí, pro produkční využití zvažte ověření MAC nebo využití jiné knihovny.

Bluetooth je samostatná velká kapitola sama o sobě – knihovna aioble, BLE GATT, atd. Pokud o ni je zájem, dejte vědět a doplníme.

Mini projekt – test reakce #

Spojíme všechno, co jsme se naučili. Postavíme jednoduchou hru, která měří reakční čas:

  1. Hra ukáže instrukci a čeká na stisk A.
  2. Po stisku počká náhodnou dobu (1–4 sekundy).
  3. Najednou displej zezelená, zazní pípnutí – „GO!"
  4. Hráč co nejrychleji stiskne A.
  5. Hra spočítá milisekundy mezi GO a stiskem a zobrazí je.
  6. Pokud hráč stiskne před GO, je to falešný start.

Hra dohromady použije: displej, tlačítka, bzučák, časovače a generátor náhodných čísel. Tady je celý kód, který stačí uložit jako main.py a spustit:

from machine import Pin, SPI, PWM
from fonts import fonts_vga1_16x32, fonts_vga2_8x8
from time import sleep, ticks_ms, ticks_diff
import st7789
import random

# --- HW init ---
spi = SPI(0, 62500000, sck=Pin(18), mosi=Pin(19), polarity=1, phase=1)
display = st7789.ST7789(spi, 320, 240,
    reset=Pin(20, Pin.OUT), dc=Pin(17, Pin.OUT),
    cs=Pin(21, Pin.OUT), backlight=Pin(16, Pin.OUT),
    rotation=1)

button_a = Pin(7, Pin.IN, Pin.PULL_UP)
buzzer = PWM(Pin(15))
buzzer.duty_u16(0)

# --- Pomocné funkce ---
def text_center(font, text, y, fg, bg):
    """Vykreslí text vodorovně na střed."""
    sirka = len(text) * font.WIDTH
    x = (320 - sirka) // 2
    display.text(font, text, x, y, fg, bg)

def pip(freq, ms):
    buzzer.duty_u16(int(65535 * 0.05))
    buzzer.freq(freq)
    sleep(ms / 1000)
    buzzer.duty_u16(0)

# --- Herní smyčka ---
def cekej_na_stisk():
    while button_a.value() != 0:
        sleep(0.01)
    while button_a.value() == 0:   # počkat až pustí
        sleep(0.01)

while True:
    # Úvodní obrazovka
    display.fill(0x0000)
    text_center(fonts_vga1_16x32, "TEST REAKCE", 60, 0x07FF, 0x0000)
    text_center(fonts_vga2_8x8, "Stiskni A pro start", 110, 0xFFFF, 0x0000)
    cekej_na_stisk()

    # Připrav se
    display.fill(0x0000)
    text_center(fonts_vga1_16x32, "Pripravit...", 100, 0xFFE0, 0x0000)

    # Náhodné čekání 1–4 s, kontrolovat falešný start
    cekani_ms = random.randint(1000, 4000)
    start = ticks_ms()
    falesny = False
    while ticks_diff(ticks_ms(), start) < cekani_ms:
        if button_a.value() == 0:
            falesny = True
            break
        sleep(0.005)

    if falesny:
        display.fill(0xF800)   # červená = chyba
        text_center(fonts_vga1_16x32, "FALESNY START!", 100, 0xFFFF, 0xF800)
        pip(200, 400)
        sleep(2)
        continue

    # GO!
    display.fill(0x07E0)       # zelená
    text_center(fonts_vga1_16x32, "GO!", 100, 0x0000, 0x07E0)
    pip(880, 80)
    go_cas = ticks_ms()

    # Měření reakce
    while button_a.value() != 0:
        sleep(0.001)
    reakce = ticks_diff(ticks_ms(), go_cas)

    # Výsledek
    display.fill(0x0000)
    text_center(fonts_vga1_16x32, f"{reakce} ms", 80, 0xFFE0, 0x0000)
    if reakce < 250:
        zprava = "Bleskovy reflex!"
    elif reakce < 400:
        zprava = "Slusna reakce."
    else:
        zprava = "Zkus to znovu."
    text_center(fonts_vga2_8x8, zprava, 130, 0xFFFF, 0x0000)
    text_center(fonts_vga2_8x8, "Stiskni A pro dalsi kolo", 200, 0x07FF, 0x0000)
    sleep(0.5)        # mini cooldown, ať se nezačne hned
    cekej_na_stisk()

Co dál vylepšit: ukládat best score na microSD kartu, přidat odpočet 3-2-1 před GO, podporovat víc hráčů (střídání ABXY), nebo přidat „úroveň obtížnosti" měnící délku náhodného čekání.

Kam dál #

Probrali jsme všechno, co Picopad nabízí: displej, tlačítka, LEDku, zvuk, SD kartu, baterii, externí konektor i WiFi. Pokud vás MicroPython chytil, tady jsou nápady, kam pokračovat.

Oficiální dokumentace

Pajeníčko moduly a další hardware

Když chcete víc výkonu

MicroPython je super na rychlé prototypy a hry s pixel art grafikou. Když narazíte na limit (komplikovaný emulátor, plynulý 3D, real-time audio), přejděte na C SDK:

Inspirace z komunity

Co všechno se s Picopadem dá udělat – stávající projekty od komunity najdete na stránce Komunita: emulátor GameBoy, ZX Spectrum 48k, port DOOMa, MakeCode Arcade patcher, vlastní kryt v 3D tisku, vylepšené tlačítka.

Zpětná vazba

Tenhle tutoriál žije díky vám. Pokud jste narazili na chybu, máte nápad na další kapitolu, nebo jste si postavili něco bezvadného a chcete to ukázat – ozvěte se přes Pajeníčko nebo na GitHub repo. Šťastné programování!