from machine import Pin, Timer
led = Pin('LED', Pin.OUT)
timer = Timer()
def blink(timer):
led.toggle()
timer.init(freq=2.5, mode=Timer.PERIODIC, callback=blink)
===== Komunikace po UART =====
Cílem dílčí úlohy je poslat prostřednictvím rozhraní UART informaci o tom, jakou rychlostí se má rozsvítit LED na desce Raspberry Pi Pico. Nejprve si ale můžeme vyzkoušet samotnou komunikaci, tj. např. odesílání znaků z mikrokontroléru a jejich příjem na straně PC.
==== Aplikace na Raspberry Pi ====
Třída [[https://docs.micropython.org/en/latest/library/machine.UART.html|machine.UART]] je určena pro vytvoření fyzického UART rozhraní pomocí dvojice RX/TX pinů. Pokud bychom ji chtěli využít, potřeboval bychom na druhé straně obdobné zařízení, např. jiné Pico. Pokud bychom chtěli takto komunikovat s PC, je potřeba konvertor UART-USB, např. s FTDI čipem (např. [[https://dratek.cz/arduino/1158-eses-cp2102-usb-ttl-prevodnik.html|tento]]).
Lze však využít toho, že USB rozhraní Raspberry Pi funguje jako sériové rozhraní s rychlostí 115200 kb/s. A data z desky Pico lze tedy poslat příjemci na PC např. pomocí funkce ''print()''.
from machine import Pin, Timer
import sys
led = Pin('LED', Pin.OUT)
while True:
# x = input()
x = sys.stdin.read(1)
if x == 'a':
led.toggle()
print("UART: {}".format(x))
==== Aplikace na PC ====
Pro UART komunikaci mezi embedded zařízením a PC použijeme knihovnu [[https://pypi.org/project/pyserial/|PySerial]]. Připojení proběhne vytvoření instance třídy, parametry konstruktoru jsou název sériového portu a rychlost komunikace. Je celkem vhodné ošetřit připojení pro případ, že spojení nelze uskutečnit. V následujícím kódo je zařízení připojeno k portu ''COMXXX'' (za XXX dosaďte podle potřeby) a komunikuje rychlostí 115200 baudů.
import serial
try:
ser = serial.Serial('COMXXX', 115200)
ser.flushInput()
except:
print("unable to open COM port")
Se zařízením je možné komunikovat na úrovni bytů nebo znaků. Pokud zařízení posílá data ve formě znaků (tj. posílá byty s významem ASCII kódů), lze data přijmout třeba takto:
data = ser.readline().decode()
print(data)
Pokud je z hlediska aplikace výhodnější používat byty ve s významem čísla (např. v rozsahu 0-255), je možné přijmout a dekódovat takto:
byte = ser.read()
decoded_bytes = int.from_bytes(byte, byteorder = 'little')
Argumentem metody ''read()'' je počet bytů, které jsou najednou přečteny. Lze tedy např. předpokládat, že embedded zařízení posílá dva byty současně a tyto dva byty buď mohou reprezentovat číslo typu ''short'', nebo dva samostatné byty ''a'' a ''b'', které je třeba dekódovat:
byte = ser.read(2)
decoded_bytes = int.from_bytes(byte, byteorder = 'little')
a = decoded_bytes & 255;
b = (decoded_bytes >> 8) & 255;
import serial
try:
ser = serial.Serial('COM7', 115200)
ser.flushInput()
# while True:
ser.write(b'a')
data = ser.readline().decode()
print(data)
except:
print("unable to open COM port")
===== Zadání 3. miniprojektu =====
Rozšiřte aplikaci vytvořenou v rámci předchozích dvou miniprojektů o komunikaci s Raspberry Pi Pico prostřednictvím UART rozhraní.
==== Možné řešení ====
Následující systém je minimalistickou variantou aplikace, která umožňuje měnit stav LED na RPi Pico pomocí formuláře ve webovém rozhraní.
from machine import Pin, Timer
import sys
led = Pin('LED', Pin.OUT)
while True:
# x = input()
x = sys.stdin.read(1)
if x == 'a':
led.toggle()
print(led.value())
=== Kód pro Flask server ===
import serial
from flask import Flask, request, render_template
app = Flask(__name__)
@app.route('/', methods=['GET', 'POST'])
def main():
x = request.form.get('zmena')
ret = -1
if x is not None:
ser = serial.Serial('COM7', 115200)
ser.flushInput()
ser.write(b'a')
ret = int(ser.readline().decode())
ser.close()
return render_template('index.html', data=ret)
if __name__ == '__main__':
app.run(debug=True)
=== HTML šablona ===
Pico LED
{% if data == -1 %}
LED: neznámý stav
{% elif data == 0 %}
LED: nesvítí
{% elif data == 1 %}
LED: svítí
{% endif %}