Při vytváření složitějších projektů s micro:bitem se nám bude hodit si postavit dálkový ovladač dle svých potřeb a představ. Tato lekce je ukázkou, jaké máme možnosti si ovladač postavit s micro:bitem.
název: D1 Dálkový ovladač
kategorie: D zkušení programátoři
ref.číslo: D1
projekt: kurz micro:bit
verze: 01, 2017-11-07
autor: Ivo Obr, Lanškroun
Předpokládáme, že máme zařízení s micro:bitem, které chceme dálkově ovládat. V dalším budeme tomuto zařízení říkat přijímač, vlastnímu ovladači pak ovladač. Komunikace bude pomocí rádiového přenosu. Tato lekce je sice konkrétním návodem, ale umožní Vám porozumět tématu a upravit si svůj vlastní ovladač podle Vašich potřeb.
Nejdříve si řekneme, co od ovladače budeme očekávat. (v dalších lekcích připravuji návod na stavbu vozítka ovládaného micro:bitem, s ovladačem, který je v této lekci)
- komunikace mezi ovladačem a přijímačem bezdrátově
- klávesnice 4×4 (16 tlačítek: 1,2,3,4,5,6,7,8,9,0,A,B,C,D,*,#), odesílání stisknutého znaku
- odesílání hodnoty náklonu micro:bitu v ose X a oseY
- možnost přepínat mezi 4 nastavenými kanály (pro eliminaci rušení)
- odesílání signálu HEART BEAT (že ovladač je připojen)
- indikace připojení přijímače (pomocí signálu HEART BEAT z přijímače)
Co budeme ke stavbě ovladače potřebovat :
- 2 ks micro:bit (ovladač, přijímač)
- 1 ks EDGE konektor s kolíky
- 1 ks membránová klávesnice 4×4
- 1 ks žlutá LED dioda
- 1 ks RGB LED dioda
- spojovací dráty (male-female)
- 4 ks odpor 160 ohmů 0,25W
- nainstalovaný sériový monitor Tera Term (viz lekce B18) na PC
Začneme tím, že si vyzkoušíme funkčnost našeho rádiového přenosu mezi micro:bity a funkčnost sériového monitoru. Pokud máte realizovanou lekci B18, tak by to mělo fungovat na první zapojení.
Program pro ovladač :
from microbit import *
import radio
display.scroll("A")
radio.config(length=32, group=48, power=7)
radio.on()
radio.send("OVLADAC")
while True:
radio.send("HEART BEAT")
sleep(1000)
Abychom si nepopletli micro:bity, na začátku se na displeji micro:bitu ovladače vypíše “A”, na displeji micro:bitu přijímače “B”. Oproti standardním hodnotám rádia je nastaveno group=48 a power=7 a délka přenosu 32. Každou vteřinu bude ovladač odesílat text “HEART BEAT”.
Program pro přijímač :
from microbit import *
import radio
display.scroll("B")
uart.init(9600)
uart.write("PRIJIMAC \n \r")
prijem = ""
radio.config(length=32, group=48, power=7)
radio.on()
uart.write("RADIO ON \n \r")
while True:
prijem = radio.receive()
if not(prijem is None):
uart.write(prijem)
uart.write("\n \r")
Po zapnutí micro:bitů a správném nastavení sériového monitoru by se měl na sériovém monitoru opakovat text “HEART BEAT”. (pokud ne, zkuste na ovladači i na přijímači tlačítko reset).
Pro ovladač použijeme membránovou klávesnici 4×4, která pro ovládání dostatečný počet tlačítek a je jednoduchá. Skládá se ze dvou vrstev, jedna vrstva má spojena tlačítka v řádcích, druhá vrstva ve sloupcích. Jestliže stiskneme některé tlačítko, pak se v průsečíku řádku a sloupce vytvoří vodivé spojení (dojde ke kontaktu vrstev).
Obrázek ukazuje princip této klávesnice. Jak program zjistí, která klávesa je stisknutá? Budeme postupně nastavovat v jednotlivých sloupcích digitálně hodnotu 1 (3V). Pokud v prvním sloupci nastavíme digitálně 1 (v ostatních sloupcích je digitálně 0), pak budeme číst hodnotu v jednotlivých řádcích. Pokud máme stisknutou například klávesu “7”, pak je ve třetím řádku na vodiči z klávesnice digitálně 1, v ostatních řádcích je 0. Ze souřadnice sloupce a řádku určíme, jaká klávesa je stisknuta.
(Náš program je postaven na vyhodnocení stisku jen jedné klávesy současně, pokud stiskne klávesy dvě najednou, pak bude vyhodnocena klávesa s vyšším pořadím.)
Pokud nebude žádná klávesa stisknuta, pak jsme nenašli žádný řádek s logickou hodnotou 1. Testování stisknuté klávesy je v programu nastaveno na interval 200ms, to je 5x za vteřinu. Držíme-li klávesu trvale, pak je znak vyhodnocen, jako bychom stiskli klávesu 5x za vteřinu.
Na obrázku jsou uvedeny čísla pinů na micro:bitu, ke kterým připojíme vývody z klávesnice. Sloupce jsou postupně od pinu 16 do pinu 13, řádky pak od pinu 9 do pinu 6. Kód pro test klávesnice je :
# OSAZENI KLAVESNICE
klavesnice = ['1', '2', '3', 'A',
'4', '5', '6', 'B',
'7', '8', '9', 'C',
'*', '0', '#', 'D']
iznak = None
def klavesa():
global iznak
iznak = None
i = 0
for sloupec in [pin16, pin15, pin14, pin13]:
sloupec.write_digital(1)
j = 0
for radek in [pin9, pin8, pin7, pin6]:
if radek.read_digital():
iznak = (i * 4) + j
j += 1
sloupec.write_digital(0)
i += 1
Každý znak, který je zjištěn je pak odesílán rádiem. Klávesy “A”, “B”, “C” a “D” jsem vyhradil pro přepínání kmitočtů a skupin rádiového přenosu. Na ovladači, pokud bychom se rušili s nějakým jiným rádiovým vysíláním, můžeme přepnout na jiný kanál a jinou skupinu. Také můžeme ovládat nezávisle dvě (tři nebo čtyři) zařízení jedním ovladačem. Znaky (“A”, “B”, “C” a “D”) se také odesílají ještě než dojde k přepnutí kanálu, aby se přijímač na druhé straně přepnul také na správné parametry vysílání (pokud ovládáme jedno zařízení).
V programu je sledován čas a po uplynutí 200ms dojde k testu klávesnice :
def klavesy44():
global CAS_KLAVESY
global INT_KLAVESY
global iznak
if (running_time() - CAS_KLAVESY) >= INT_KLAVESY:
klavesa()
if not(iznak is None):
znak = klavesnice[iznak]
radio.send(znak)
if (znak in ['A', 'B', 'C', 'D']):
zap_radio(znak)
CAS_KLAVESY = running_time()
iznak = None
Zapínání rádia se provede funkcí “zap_radio(znak)”, kde znak je hodnota “A” nebo “B” nebo “C” nebo “D” přečtená z klávesnice.
# PARAMETRY RADIA
A_CHANNEL = 51
A_GROUP = 201
B_CHANNEL = 61
B_GROUP = 211
C_CHANNEL = 71
C_GROUP = 221
D_CHANNEL = 81
D_GROUP = 231
def zap_radio(kanal):
pin11.write_digital(0)
pin12.write_digital(0)
radio.off()
if (kanal == 'A'):
radio.config(length=32, channel=A_CHANNEL, group=A_GROUP, power=7)
if (kanal == 'B'):
radio.config(length=32, channel=B_CHANNEL, group=B_GROUP, power=7)
pin11.write_digital(1)
if (kanal == 'C'):
radio.config(length=32, channel=C_CHANNEL, group=C_GROUP, power=7)
pin12.write_digital(1)
if (kanal == 'D'):
radio.config(length=32, channel=D_CHANNEL, group=D_GROUP, power=7)
pin11.write_digital(1)
pin12.write_digital(1)
radio.on()
Vysílací kanály a skupiny je možno upravit, vždy je ale třeba, aby stejné hodnoty byly i na přijímači. RGB LED diodu (červená- pin11, zelená – pin12) zapojíme do pinů 11 a 12 na microbitu přes omezovací odpor 160 ohmů. LED dioda svítí dle nastaveného kanálu takto :
A – nesvítí
B – červená
C – zelená
D – žlutá
Všechny časové intervaly jsou uvedeny v kódu :
# CASOVE INTERVALY CAS_KLAVESY = running_time() INT_KLAVESY = 200 CAS_GYRO = running_time() INT_GYRO = 97 CAS_HBS = running_time() INT_HBS = 1000 CAS_HBR = running_time() INT_HBR = 3000
Hodnoty z gyroskopu jsou přenášeny v časovém intervalu INT_GYRO = 97. Jedná se o souřadnice v ose X (náklon micro:bitu vpravo-vlevo) a v ose Y(náklon micro:bitu dopředu-dozadu). Hodnoty jsou přenášeny samostatně jako dva řetězce znaků. Před těmito řetězci je poslán znak “S”, aby přijímač měl informaci, že budou následovat dva řetězce znaků (X a Y).
def gyro():
global CAS_GYRO
global INT_GYRO
if (running_time() - CAS_GYRO) >= INT_GYRO:
radio.send('S')
radio.send(str(accelerometer.get_x()))
radio.send(str(accelerometer.get_y()))
CAS_GYRO = running_time()
Zbývá nám ještě signál HEART BEAT, který nám monitoruje spojení mezi ovladačem a přijímačem. Ovladač každou vteřinou vysílá na rádio znak “H”, který může být identifikován na přijímači jako že je spojení v pořádku. Také naopak přijímá signál z přijímače (ovládaného zařízení). Pokud signál z přijímače chodí, je toto indikováno LED diodou připojenou přes omezovací odpor na pin5. Takže pokud tato dioda svítí, je spojení ovladače a přijímače OK. Pokud po dobu 3 vteřin nepřijde signál (znak “H”) z přijímače, pak je tento stav vyhodnocen jako ztráta spojení a LED dioda zhasne. (Na pin5 je digital 0).
def HB():
global CAS_HBR
global INT_HBR
global CAS_HBS
global INT_HBS
# HEART BEAT SEND
if (running_time() - CAS_HBS) >= INT_HBS:
radio.send('H')
if (running_time() - CAS_HBR) >= INT_HBR:
radio.send('?')
pin5.write_digital(0) # indikace LED HB off
CAS_HBS = running_time()
# HEART BEAT RECEIVE
prijem = radio.receive()
if not(prijem is None):
if (prijem == 'H'):
CAS_HBR = running_time()
pin5.write_digital(1) # indikace LED HB on
Poznámka:
Pokud připojíte piny klávesnice a LED diod jinak než podle tohoto návodu, je možné, že Vám program ovladače nebude fungovat.

Celý program ovladače a přijímače najdete na konci této lekce. Nejdříve si vyzkoušíme, jak to funguje. Nahrajeme oba programy do micro:bitů. Pokud jsme pracovali pozorně, funguje vše na první zapojení.
K vlastní mechanické realizaci jsem použil elektrikářskou krabičku 80x80x28mm. Tato lekce není návodem na konkrétní mechanickou stavbu.
Někdo si vytiskne krabičku na 3D tiskárně, někdo slepí z tvrdého kartonu.
LED diody a omezovací odpory a spojové dráty jsem připájel k destičce pro jednorázovou montáž viz obrázek. Celkový pohled na ovladač takto zhotovený je na posledním obrázku.

Pokud budete chtít experimentovat a měnit funkce ovladače, doporučuji nastavit si delší časy pro “X” a “Y”, aby jste dokázali sledovat komunikaci mezi ovladačem a přijímačem na sériovém monitoru.
A nakonec oba programy.
Program pro ovladač:
from microbit import *
import radio
# PARAMETRY RADIA
A_CHANNEL = 51
A_GROUP = 201
B_CHANNEL = 61
B_GROUP = 211
C_CHANNEL = 71
C_GROUP = 221
D_CHANNEL = 81
D_GROUP = 231
# CASOVE INTERVALY
CAS_KLAVESY = running_time()
INT_KLAVESY = 200
CAS_GYRO = running_time()
INT_GYRO = 97
CAS_HBS = running_time()
INT_HBS = 1000
CAS_HBR = running_time()
INT_HBR = 3000
# OSAZENI KLAVESNICE
klavesnice = ['1', '2', '3', 'A',
'4', '5', '6', 'B',
'7', '8', '9', 'C',
'*', '0', '#', 'D']
iznak = None
def klavesa():
global iznak
iznak = None
i = 0
for radek in [pin16, pin15, pin14, pin13]:
radek.write_digital(1)
j = 0
for sloupec in [pin9, pin8, pin7, pin6]:
if sloupec.read_digital():
iznak = (i * 4) + j
j += 1
radek.write_digital(0)
i += 1
def zap_radio(kanal):
pin11.write_digital(0)
pin12.write_digital(0)
radio.off()
if (kanal == 'A'):
radio.config(length=32, channel=A_CHANNEL, group=A_GROUP, power=7)
if (kanal == 'B'):
radio.config(length=32, channel=B_CHANNEL, group=B_GROUP, power=7)
pin11.write_digital(1)
if (kanal == 'C'):
radio.config(length=32, channel=C_CHANNEL, group=C_GROUP, power=7)
pin12.write_digital(1)
if (kanal == 'D'):
radio.config(length=32, channel=D_CHANNEL, group=D_GROUP, power=7)
pin11.write_digital(1)
pin12.write_digital(1)
radio.on()
display.scroll("A")
zap_radio('A')
while True:
# KLAVESY
if (running_time() - CAS_KLAVESY) >= INT_KLAVESY:
klavesa()
if not(iznak is None):
znak = klavesnice[iznak]
radio.send(znak)
if (znak in ['A', 'B', 'C', 'D']):
zap_radio(znak)
CAS_KLAVESY = running_time()
iznak = None
# GYRO
if (running_time() - CAS_GYRO) >= INT_GYRO:
radio.send('S')
radio.send(str(accelerometer.get_x()))
radio.send(str(accelerometer.get_y()))
CAS_GYRO = running_time()
# HEART BEAT SEND
if (running_time() - CAS_HBS) >= INT_HBS:
radio.send('H')
if (running_time() - CAS_HBR) >= INT_HBR:
radio.send('?')
pin5.write_digital(0) # indikace LED HB off
CAS_HBS = running_time()
# HEART BEAT RECEIVE
prijem = radio.receive()
if not(prijem is None):
if (prijem == 'H'):
CAS_HBR = running_time()
pin5.write_digital(1) # indikace LED HB on
Program pro přijímač (je na Vás, jak s tím naložíte, asi by něco podobného mělo být součástí Vašeho ovládaného zařízení):
from microbit import *
import radio
# PARAMETRY RADIA
A_CHANNEL = 51
A_GROUP = 201
B_CHANNEL = 61
B_GROUP = 211
C_CHANNEL = 71
C_GROUP = 221
D_CHANNEL = 81
D_GROUP = 231
# CASOVE INTERVALY
CAS_HBS = running_time()
INT_HBS = 1000
CAS_HBR = running_time()
INT_HBR = 3000
def zap_radio(kanal):
radio.off()
if (kanal == 'A'):
radio.config(length=16, channel=A_CHANNEL, group=A_GROUP, power=7)
if (kanal == 'B'):
radio.config(length=16, channel=B_CHANNEL, group=B_GROUP, power=7)
if (kanal == 'C'):
radio.config(length=16, channel=C_CHANNEL, group=C_GROUP, power=7)
if (kanal == 'D'):
radio.config(length=16, channel=D_CHANNEL, group=D_GROUP, power=7)
radio.on()
display.scroll("B")
uart.init(115200)
uart.write("PRIJIMAC \n \r")
prijem = ""
radio.config(length=32, channel=A_CHANNEL, group=A_GROUP, power=7)
zap_radio('A')
uart.write("RADIO ON \n \r")
while True:
prijem = radio.receive()
if not(prijem is None):
uart.write(prijem)
uart.write("\n \r")
if (prijem == 'S'):
X = radio.receive()
while (X is None):
X = radio.receive()
uart.write(X)
uart.write(' ')
Y = radio.receive()
while (Y is None):
Y = radio.receive()
uart.write(Y)
uart.write("\n \r")
if (prijem in ['A', 'B', 'C', 'D']):
uart.write("KANAL ")
uart.write(prijem)
uart.write("\n \r")
zap_radio(prijem)
if (prijem == 'H'): # prisel signal HEART BEAT od prijimace
CAS_HBR = running_time()
# HEART BEAT SEND
if (running_time() - CAS_HBS) >= INT_HBS:
radio.send('H')
if (running_time() - CAS_HBR) >= INT_HBR:
uart.write("NENI OVLADAC \n \r")
CAS_HBS = running_time()

Pingback: Aplikace D2 Vozítko s ovladačem – Microla