5. Lüliti ühendamine ja LED-i vilgutamine vastavalt lüliti asendile: IF/ELSE tingimuse kasutamine
<- eelmine peatükk
järgmine peatükk ->
5.0. Seos eelmiste peatükkidega
Eelmises tunnis rakendasime for-tsüklit LED-i vilkumise juhtimiseks. Õppisime üles seadma vooluringi kahele LED-ile—LED pikema „jala“ ühendasime pluss-viigu (juhtme) külge ning lühema „jala“ ühendasime miinus-viigu (juhtme) ( GND) külge. Teame, et LED läbipõlemise vältimiseks on oluline kasutada takistit. Oskame kasutada muutujaid ja teame, millisest kolmest osast koosneb tüüpiline Arduino programm.
5.1. Eesmärk ja selgitused
Vooluahela koostamine saab olema sarnane vooluahela koostamisega kolmandas ja neljandas peatükis. Ent selles tunnis seame LED-i sisaldava vooluahela juhtimiseks üles ka vajaliku teise vooluahela—lüliti kasutamiseks.
Selle peatüki läbimise järel õpilane oskab:
- kasutada IF/ELSE tingimuste seadmist programmi kirjutamisel ning see annab võimaluse rakendada LED juhtimist surunupp-lüliti abil.
- Kusjuures me meelega ei räägi „LED sisse-välja lülitamisest“ vaid rõhutame „LED juhtimist“.
Lüliti nupule vajutamisega me ei „süüta“ LED-i nagu lampi toa valgustamiseks. Lüliti nupule vajutamisega käivitame IF-alla kirjutatud programmiosa—elektrilise impulsiga. Kusjuures programmiosaks, mis käivitub, võiks näiteks olla ka sellesama LED-i teistmoodi vilkumise muster—me lülita midagi „välja“ või „sisse“. Lülitile vajutus registreerib erinevuse lülitile mittevajutamisest—selle tagajärjel toimuva aga määrame programmi teksti abil meie ise.
- Saame näiteks programmeerida meie nupule-vajutuse (st sisend, INPUT) peale LED vilkuma (väljund, OUTPUT)—ja selleks kasutada ka eelmisel tunnil õpitud FOR tsüklit.
- Saame näiteks ilma nupuvajutuseta oleku (samuti väljund, INPUT) peale programmeerida sama LED ilma vilkumiseta valgustatuks. Põhiline on mõista, et lüliti on sisendi (INPUT) andmise võimalus. Sellele peatükile järgnevates peatükkides saame lüliti asemel näiteks kasutada mingit andurit sisuliselt „lüliti rollis“.
Õpime IF/ELSE tingimuse andmist:
näiteks kui (IF) surunupp-lüliti on alla vajutatud asendis (sisend ei ole null), siis täida korraldus LED särama panna;
muul juhul (ELSE—ja selleks saab olla vaid nupule mitte-vajutamine—st sisend on null) tuleb täita midagi muud—näiteks on LED säramine defineeritud käsklusega LOW.
- Viienda tunni lõppedes õpilane mõistab, et suudab lülitiga mitte lihtsalt vooluahelat sisse-välja lülitada vaid elektrilise impulsiga aktiviseerida enda poolt Arduinole programmis kirjutatud käskluse.
Surunupp-lüliti muutub millekski sarnaseks sensoriga: roboti sensori kohta oli meil juba juttu esimeses tunnis roboti osade teemal. Lülitamine ei olegi enam lülitamine?
Viienda tunni järel on õpilasel
- tekkinud vajadus eksperimenteerida, ta on tunnetanud seda, mis on INPUT ja mis on OUTPUT
- kinnistatud oskused ümber käia for-tsükliga;
- oskus programmis if-tingimusi kasutada.
5.2. Töövahendid on paljuski samad, mis kolmandaks tunniks (1-9), ent lisame neile juurde surunupp-lüliti (10)
5.3. Tegevused
5.3.1. Alustame Arduino juurde vooluahela ehitamisest
Alustuseks ehitame eelmise peatükiga üsna sarnase lihtsa vooluahela: ühe LED-iga. Vaata kõrval olevat skeemi.
Anname siia juurde LED vilgutamiseks ka programmi. Laadige see Arduinosse ning uurige:
Kas vilgub kaks korda—HIGH kestab 500 millisekundit ja LOW kestab üks sekund (1000 millisekundit) ning siis ootab ilma vilkumata (LOW) kolm sekundit (3000 millisekundit)?
int ROHELINE_viik = 6; int roheLEDhigh = 500; int roheLEDlow = 1000; void setup() { pinMode(ROHELINE_pin, OUTPUT); //Tähelepanu! } void loop() { for (int j=1; j<=2; j=j+1){ digitalWrite(ROHELINE_viik, HIGH); delay(roheLEDhigh); digitalWrite(ROHELINE_viik, LOW); delay(roheLEDlow); } delay (3000); }
Juhime LED-i tööd programmiga, kusjuures võime mõelda, et viimane delay(3000) on nagu „lüliti“ eest—kolmeks sekundiks on LED „välja lülitatud“—st Arduino poolt ei anta LED-ile toidet vastavalt meie kirjutatud programmile.
Võite katsetamiseks muuta programmis muutujaid, see võimaldab korrata eelmisel tunnil õpitut.
5.3.2. Lüliti lisamine
Ent näiteks me ei taha, et iga kord oleks vahe mingi LED oleku (HIGH) ning sellele järgneva oleku (LOW) vahel vaid ja ainult see arv millisekundeid, mille me oleme pidanud programmis ette määrama (eelnenud programmis antud muutujatega roheLEDhigh ja roheLEDlow ning tundub, et seetõttu justkui kiiresti korrektselt muudetav.
Soovime midagi paindlikumat—me ei saa ju igakordselt programmi ümber kirjutada või antud juhul minna kahte muutujat (roheLEDhigh ja roheLEDlow) muutma, kui soovime mingit protsessi ad hoc esile kutsuda või peatada.
Tahame mingit kontrollivõimalust, mis oleks paindlikum:
- Robot peab ju alluma inimese korraldusele kiirelt.
Seega lahenduseks sobiks hästi midagi, mis võimaldab Arduinole (st „robotile“) midagi „otse“ öelda—näiteks vajaduse korral suruda millelegi, mis ütleks robotile, et „toimi viisil B“ ja kui me enam ei suru, siis robot teaks, et ta peab näiteks taas jätkama „esialgsel toimimisviisil A“.
Anname robotile sisendi, mille alusel robot toimib vastavalt talle varem laetud programmile. Sisend on programmis INPUT.
OUTPUT—LED…
Juhime tähelepanu üleval toodud programmi tekstis olevale rohelisele LEDile. Me anname rohelisele LED-ile infot—ent seda LED-i toitev viik on seejuures väljundit (OUTPUT) edastavaks viiguks.
Toome meie üheainsa rohelise LED-iga vooluringi kohta ka skeemi:
…siia on vaja ka INPUT-lülitit
Kuhugi siia oleks niisiis vaja riistvaraliselt „istutada“ ka INPUT—milleks võtame näpuga all hoides elektrit läbi laskva nupu.
Idee on, et seni kuni pressime lüliti nuppu—st anname sisendit sisendi-viiguile (mis oleks INPUT!)—on meil Arduinole antud signaal tegutseda: teha midagi LED-iga. (NB! Suvaline lüliti ei pruugi sobida igasse rolli, seega on oluline mõelda, et millist kasutame.1)
- Niisiis vajame veel ühte vooluahelat, milles voolu olemasolu ütleks Arduinole, et vaja on lubada vool vastavalt programmile ka LED-i toitvasse vooluringi (või—kui programmeerime teisiti, siis näiteks mitte lubada).
- Ja voolu puudumisele selles vooluahelas saame anda ka mingi tähenduse programmis—tehakse midagi muud.
Meie skeem muutub seega keerukamaks. Vajame veel ühte vooluringi ja teeme skeemi—ent mis on järgneval pildil oleval skeemi probleemiks?
Kas mahakriipsutatud osa justkui sarnane lühisele? Ja kas see üldse annab sisendit?
Õige vastus on, et selline skeem nupule vajutuse korral lühistab ja seega on oht rikkuda Arduinot. Nii ei tohi teha!
1 Erinevatest lülititest Arduino kontekstis vaata võimaluse korral ka eesti keeles välja antud raamatust Arduino projektid alustajale (Raivo Sell, Kaupo Raid, Robolabor.ee kirjastus, 2017) leheküljel 23 toodud tabelit. Mõtle, mis moodi erinevad lülitid aitavad täita erinevaid impulsi andmise eesmärke.
5.3.3. Arutluskäik
A) Mis oleks veel vaja lisada või ümber teha?
- Kas peame muutma lüliti INPUT -iks? St viima lülitist veel ühe juhtme viiku, mille määrame INPUT viiguks?
- Kas peaksime lühise vältimiseks panema enne Groundi (GND) takisti?
- St kui oleme pressimas lülitit, siis takisti toime tõttu ei oleks voolu GND kaudu, vaid vool oleks 5V toite ja mingi meie poolt INPUT viiguks valitud viigu vahel? Ja siis saaksime seda voolu tarvitada INPUT-i lugemiseks?
B) Järgmisel skeemil leiad vastuse. Uuri, mida tuleb veel lisada esimesele vooluringile.
Skeemil ette näidatu kommentaariks:
- Kui me ei suru lülitit, siis toimib vool 5V ja GND vahel. Programmis näeme, et vastav pinge oleks kaetud ELSE osaga.
- Peame asetama GND suunale takisti selleks, et kui surume lülitit, siis toimiks sisendit andev pinge viigul nr 10—ilma takistit kasutamata leiaks vool endale kergema tee—GND kaudu ning me ei saaks mõõta sisendviigul pinge tõusu.
int ROHELINE_pin = 6; // PIN nr 6 oli meil OUTPUT-iks int roheLEDin = 500; int roheLEDout = 1000; //PIN 10 aga on vajalik defineerida INPUT-iks: //loome vastava integer (int) andmetüübi (täisarv): int LYLITI = 10; //ja anname LYLITI-le vaikeväärtuseks nulli--kui me ei pressi //seda, siis ei toimu midagi: int LYLITIvaikimisi = 0; void setup() { pinMode(ROHELINE_pin, OUTPUT); // siia lisame ka pinMode LYLITI jaoks: pinMode on INPUT, //sest juhime sellega--see on sisend-info jaoks: pinMode (LYLITI, INPUT); } void loop() { //siin peame kõigepealt lugema, mis //toimub lülitiga vabas vaikimisi asendis: LYLITIvaikimisi = digitalRead (LYLITI); //ja seejärel huvitab meid, kas lüliti on või ei ole vabas //"vaikimisi" asendis: // st meid huvitab see hetk, //millal vaikeväärtus ei ole (!=) null... //seega: if (LYLITIvaikimisi != 0) { // ja kui (IF!) ei ole null, siis //on antud lause tõene ja käivitab järgneva ahela: for (int j=1; j<=2; j=j+1){ digitalWrite(ROHELINE_pin, HIGH); delay(roheLEDin); digitalWrite(ROHELINE_pin, LOW); delay(roheLEDout); } delay (3000); } // aga kui on hoopis midagi muud (ELSE): //st nuppu ei hoita all-asendis, siis //programmeerime LED seisundisse LOW: else { digitalWrite (LYLITI, LOW); } }
Seega ega me väga palju oma programmi ei täiustanudki.
Võrrelge selles tunnis läbi tehtud programme ja muutke neid. Tehke märkmeid.
5.4. Kui klassis ei jõua, siis jätame järgneva küsimuse koduseks ülesandeks:
Võiksime endale tõestada, et me ei olegi midagi „lülitanud“ lülitamise tavalises mõistes, sest selle surunupp lülitiga me vaid ainult anname INPUT-i. St et kui nupp on „välja lülitatud“—toimib vaid vool Arduino GND ja V5 viikude vahel: viik number 10 ei ole kaasatud ja seega toimib meie poolt programmile ette kirjutatud else-tingimus. Ja else järgi kirjutatut saame me ka ise muuta, näiteks lisada else korral täiendava LED-i signaali.
Näiteks: pange else osas mingi muud värvi täiendav LED kiirelt vilkuma (nii HIGH kui LOW puhul delay näiteks 100).
Saate selleks ülesandeks vajaliku programmilõigu kopeerida eespool toodud programmilõigust. Tõsi, väikesed kohendused võivad olla vajalikud: tehke vajalikuks osutuvad muudatused.
5.4.1. Kui kõik plaanitu juba tunnis tehtud sai, siis palun tehke koduse ülesandena ise mingeid muudatusi: fantaseerige!
Oluline on, et A) ikka kogu programm ja riistvara-skeem töötab ning B) olete muudatused ka omapoolse selgitusega varustanud. Kirjutage oma selgitus ka programmi teksti: et programm seda kogemata „omal käel uurima“ ei hakkaks (veateade!), siis varustage iga oma kommentaar märgiga // või märkidega /* ja */. Ja jälgige, et olete kasutanud sulge, semikoolonit ning loogelisi sulge korrektselt arvutiprogrammile arusaadavate reeglite järgi.
Tunnis kasutatud programmitekste ümber tehes Te testite ja programmeerite: Te kasutate IF, ELSE lauseid ja FOR-tsüklit; see on päris hea saavutus: sellega annab juba päris palju huvitavat teha.
Kui aga tund ei õnnestunud—õpilased ei saanud aru ühe vooluahela abil teise vooluahela juhtimisest, mõistetest sisend ja väljund—input ja output, siis peaks kaaluma tunni kordamist. Ja see ei ole ka paha mõte, sest nii kinnistub ka eelnenud materjal. Kas mäletate, mis pidi ja kuhu tuli ühendada „kahe jalaga“ LED? Ja miks see nii teha tuli?
Kordamiseks annab hea võimaluse ka see, et järgmine tund, mis on RGB-LED-iga mängimine, võib osutuda mõneti intuitiivsemaks kui kahe vooluringi ning IF-ELSE abil input-ouput rakendamine.