====== Jalgpallirobot ======
===== Taust =====
Järgnev õpetus on koostatud TTÜ avatud ülikooli ja MTÜ TTÜ Robotiklubi koostöös eesmärgiga aidata Robotexil osalevaid või seda plaanivaid võistkondi.
Robotex on eesti suurim ja populaarseim võistlus, mis leiab aset igal aastal novembris või detsembris Tallinnas. Võistlusel on ette antud lähteülesanne, mis tavaliselt muutub igal aastal. Täpsemat infot võistluse ja reeglite kohta saab aadressilt http://www.robotex.ee
Käesolev juhend sisaldab täielikku dokumentatsiooni ja praktilisi näpunäiteid ühe Robotex 2010 reeglitele vastava roboti ehitamiseks. Robot on oma ülesehituselt ja võimetelt ette nähtud juuniorite klassis osalemiseks, kus robotitel pole kasutada kalleid ja kiireid mootoreid, pisikesi arvuteid ning kaameraid. Sellesse klassi on oodatud gümnaasiumiõpilased ja robootikaga alles tutvust tegevad huvilised.
Juhendi baasil loodud platvormi eesmärgiks on olla lihtne ning odav esimene katsetus robotite ehitamise vallas. Sellest lähtuvalt kasutatakse laialt saadaolevaid konstruktsioonimaterjale ning elektroonikakomponente. Roboti baaskomponentideks on valitud Kodulabori komplektis sisalduvad moodulid. Kuna kõiki komponente kodulaborites siiski ei leidu, lisanduvad mõningad spetsiifilised osad. Tänu moodularhitektuurile võib iga soovija robotit muuta vastavalt oma äranägemisele.
===== Kontseptsioon =====
Kuna ilma pilditöötluseta ja kallite laserkaugumõõdikuteta on pallide leidmine väljakult tehniliselt üsna keerukas, tuleb minna lihtsama vastupanu teed ja kaugelt avastamise asemel palle aktiivselt ringi sõites otsida. Selleks on roboti algoritmis ette nähtud väljakul edasi-tagasi sõitmine ja pallide juhuslik avastamine.
~~CL~~
[{{ :images:projects:soccer_robot:liikumine_valjakul.png |Liikumine väljakul}}]
~~CL~~
Robot kasutab pallide leidmiseks ultraheli kaugusandurit. Andur on asetatud mõõtma kaugust roboti parema külje peale. Pallide otsimiseks sõidab robot väljaku keskel ühe värava juures teise juurde ja mõõdab pidevalt temast paremale jäävate objektide kaugust. Kui roboti ja seina vahele jääb pall siis kauguse näit väheneb ja robot võtab hoo maha, et vaikselt liikudes pallist mööduda nii, et kaugusanduri näit jälle suureneks. Sedasi saab robot üpris täpselt palli kõrvale sõita.
[{{ :images:projects:soccer_robot:liikumine_palli_otsimine.png |Palli otsimine paremale suunatud ultrahelianduri abil}}]
Edasi on põhimõtteliselt lihtne - robotil tuleks keerata 90 kraadi paremale ja sõita pallini, kuid paraku ei ole palli kõrvale seisma jäämine ja pööre nii täpne, et robot saaks kätte poole meetri kaugusel oleva palli. Selleks on pärast palli avastamist kaks varianti: kohe palli püüdma minek või selle lähemalt otsimine. Kui pall asub robotist kuni 30 cm kaugusel pöörab robot kohe palli poole ja üritab selle kätte saada nii nagu on näidatud ka järgneval skeemil:
[{{ :images:projects:soccer_robot:liikumine_palli_otsimine_kaugus_a.png |Lähedal seisnud palli püüdmine}}]
Kui pall asub kaugemal kui 30 cm siis robot sõidab esmalt edasi veel 10 cm, siis pöördub 90 kraadi paremale ja hakkab otse seina suunas sõites ultrahelianduriga otsima palli mis peaks robotist taaskord paremat kätt olema. Nii kui ultraheliandur näeb lähedal olevat objekti, sõidab robot natuke edasi, pöördub teist korda 90 kraadi paremale ja saab palli üsna nina alt kätte. Seda kauge palli leidmise algoritmi iseloomustab järgnev skeem:
[{{ :images:projects:soccer_robot:liikumine_palli_otsimine_kaugus_b.png |Kaugel seisnud palli püüdmine}}]
Robot saab pallianduri abil aru kas ta on palli kätte saanud või mitte. Palli püüdmiseks on roboti ninas V-kujuline lehter ja selle kohal pöörlev kummist rull mis paneb lehtrisse sattunud palli pöörlema roboti suunas. Palli pööritamine takistab selle minema veeremist roboti liikumise ajal.
Pärast palli kättesaamist hakkab robot otsima vastase väravat kuhu pall toimetada. Värava leidmiseks on väravate kohal infrapuna (IR) majakad mis kiirgavad väljaku suunas RC5 protokolliga signaale, ehk põhimõtteliselt on saatjad justkui telekapuldid. Värava leidmiseks on robotil kahe kanaliga RC5 vastuvõtja millel on kahe infrapuna detektori vahel sein. Kui vastuvõtja on suunatud majaka suunas, kiirgab majakas mõlemasse detektorisse; kui vastuvõtja on majaka suhtes viltu, siis signaal jõuab ainult ühte detektorisse. Vastavalt sellele milline detektor majakat "näeb" saab robot aru värava suunast. Kui suund on õige saab robot otse värava suunas sõita.
[{{ :images:projects:soccer_robot:liikumine_varava_otsimine.png |Värava suuna leidmine RC5 vastuvõtja abil}}]
Roboti ees on ~8 cm kõrgusel infrapuna kaugusandur, mis mõõdab takistuste kaugust. Takistuseks võivad võistlusel olla vastase robot või seinad. Sellesama anduriga saab robot ka aru väravast kuna väravate tagumise seina alumises 10 cm osas on riie millelt infrapuna kiirgus peegeldub. Sõites värava suunas ja jõudes värava seinast ~20 cm kaugusele lõpetatakse palli kinnihoidmine ja lükatakse see väravasse. On oht, et värava suunas sõites võib robot värava seina asemel märgata vastast - selleks ootab robot enne palli lahti laskmist natukese, lootuses, et vastane liigub eest ära.
[{{ :images:projects:soccer_robot:liikumine_kokkuporke_valtimine.png |Takistustest hoidumine ja värava leidmine infrapuna kaugusanduri abil}}]
Löögimehhanism pallide kaugel väravasse löömiseks puudub, kuna see on tehniliselt keerukas ja otseselt pole seda vaja. Pärast palli vastase väravasse lükkamist hakkab robot palle otsima oma värava suunas liikudes.
===== Dokumentatsioon =====
==== Komponentide nimekiri ====
^ Komponent ^ Selgitus ^ Kogus ^
| Veermik | | 1 |
| Alusplaat | Alumiiniumist kere | 1 |
| Haarats | Alumiiniumist raam rulli ja pallianduri jaoks | 1 |
| Mootor | DC | 1 |
| Rull | Palli keerutamiseks | 1 |
| Kummirõngas | Palli keerutamiseks | 2 |
| Kodulabori Kontrollermoodul | Mikrokontrolleriga põhiplaat | 1 |
| Kodulabori Mootorite moodul | H-sillad mootorite juhtimiseks | 1 |
| Kodulabori Andurite moodul | Erinevate andurite ühendamiseks | 1 |
| Kodulabori Kommunikatsioonimoodul | RC5 vastuvõtjaga suhtlemiseks | 1 |
| Ultraheli kaugusandur | Palli leidmiseks | 1 |
| Infrapuna kaugusandur | Takistuste avastamiseks | 1 |
| Kooder | Optokatkesti sammude lugemiseks | 2 |
| Palliandur | Peegeldusandur palli nägemiseks | 1 |
| M3x6 polt | Komponentide kinnitamiseks | 16 |
| M3x10 polt | Koodrite kinnitamiseks | 4 |
| Mutter | Komponentide kinnitamiseks | 20 |
| Seib | Komponentide kinnitamiseks | 4 |
==== Konstruktsioon====
{{:images:projects:soccer_robot:jalgpalliroboti_osad.jpg?560|Jalgpalliroboti osad}}
Jalgpalliroboti keskseks osaks on Pololu RP5 lintidega veermik sellele kinnitatava alusplaadiga. Alusplaadi külge kinnitatakse omakorda rullimehhanism, elektroonikamoodulid, andurid, koodrid, jms. Jalgpalliroboti konstruktsiooni väljatöötamisel on lähtutud sellest, et robot oleks võimalikult kompaktne, lihtne ja käepäraste vahenditega ehitatav. Materjalide ja erinevate detailide valikul on arvestatud nende kättesaadavusega.
===Veermik===
[{{ :images:projects:soccer_robot:alusplatvorm_pololu_rp5.jpg?250|Pololu RP5 veermik}}]
Alusplatvormina kasutatakse Pololu RP5 lintidega veermikku. Veermikuga on kaasas kaks alalisvoolumootorit, kummagi lindi jaoks üks. Nende abil suudab veermik liikuda kiirusega kuni 15 cm/s. Lindid tagavad platvormile hea manööverdamisvõime. Lisaks on platvormiga kaasas ka patareihoidik 6 AA suuruses patarei jaoks. Platvormi mõõtmed on 180 mm x 140 mm x 60 mm. Augud alusplaadi kinnitamiseks on platvormil algselt juba olemas, kuid need tuleb siiski veel keermestada. Rohkem informatsiooni veermiku ja selle tellimise kohta saab järgnevalt aadressilt: http://www.pololu.com/catalog/product/1060
===Alusplaat===
[{{ :images:projects:soccer_robot:montage:01_alusplaat.jpg?250|Alusplaat}}]
Alusplaat seob omavahel jalgpalliroboti kõiki detaile. Erinevate komponentide kinnitamiseks on alusplaadile puuritud vajalikud augud. Kõik komponendid on seejuures kinnitatud M3 polte ja mutreid kasutades. Alusplaat ise kinnitatakse veermiku külge nelja poldi abil. Lisaks poldiaukudele on alusplaadil auk patareihoidiku lihtsamaks väljavõtmiseks ning kaks auku koodrite kaablite jaoks. Alusplaadile tuleb teha ka kaks painutust (vt pilti). Alusplaadi materjali valikul tuleb arvestada sellega, et materjali oleks võimalik painutada.
~~CL~~
===Rullimehhanism===
[{{ :images:projects:soccer_robot:montage:10_haarats_rull_kumm.jpg?250|Rullimehhanism}}]
Rullimehhanism koosneb haaratsist, rullist, rulli kummirõngastest, rulli käitavast alalisvoolumootorist ja hingest, mille abil mehhanism alusplaadi külge kinnitatakse. Haaratsile kinnitatakse ka kahepoolse teibiga optiline andur. Alalisvoolumootorina kasutatakse Kodulabori Micro motors L149.6.10 reduktoriga mootorit.
~~CL~~
==Haarats==
[{{ :images:projects:soccer_robot:haarats.png?250|Haarats}}]
Haarats seob omavahel rullimehhanismi kõiki komponente. Haaratsi külge kinnitatakse alalisvoolumootor, optiline andur ning hing. Lisaks sellele on haaratsi üheks põhiülesandeks golfipalli fikseerimine rulli ette. Haarats on konstrueeritud nii, et golfipalli sattumisel haaratsi ette suunatakse see rulli pindade poole. Haaratsi antud ehitus takistab ka golfipalli minema veeremist roboti pööramisel. Kuna haaratsile tuleb teha mitmeid painutusi, peab materjali valikul sellega arvestama.
~~CL~~
==Rull==
[{{ :images:projects:soccer_robot:rull_kummid.jpg?250|Rull ja kummirõngad}}]
Rulli tööpõhimõte seisneb palli sellisel viisil pöörlema panemises, et see kogu aeg roboti poole veereks . Rulli diameeter on 20 mm ja laius 50 mm. Rulli ühte otsa on puuritud auk mootori võlli jaoks ning sellega risti on puuritud ja keermestatud teine auk, mille kaudu poldi abil rull võlli külge fikseeritakse.
==Kummirõngad==
Rullile kinnitatakse kaks kummirõngad siseläbimõõduga 19 mm ja välisläbimõõduga 30 mm, kummide laius on 15 mm. Kummidevaheline kaugus rullil on 10 mm. Kummid tagavad parema kontakti rulli ja golfipalli vahel ja seega golfipalli parema püsimise rulli ees.
~~CL~~
===Andurite kinnitus===
[{{ :images:projects:soccer_robot:andurite_kinnitus.png?250|IR andur, RC5 vastuvõtja kinnitusega}}]
Infrapuna kaugusanduri ning RC5 vastuvõtja kinnitamiseks on lihtne U-kujulise profiiliga kinnitus. Kinnitusele on puuritud augud infrapuna kaugusanduri ja kinnituse enda alusplaadi külge kinnitamiseks. RC5 vastuvõtja fikseerimiseks kasutatakse kahepoolset teipi. Kuna tehakse painutusi, peab sellega ka kinnituse materjali valikul.
~~CL~~
===Kodulabori moodulid===
[{{ :images:projects:soccer_robot:montage:16_kodulabori_moodulid.jpg?250|Kodulabori moodulid puksidel}}]
Patareihoidiku väljavõtmise võimaldamiseks on Kodulabori moodulid paigaldatud alusplaadile puksidega. Alusplaadil on moodulite kinnitamiseks puuritud vastavad augud. Moodulid paiknevad kihiliselt ning on omavahel kergesti ühendatavad.
~~CL~~
==== Elekter ====
=== Kodulabori moodulid ===
Roboti ehitamiseks kasutatakse Kodulabori täiskomplekti, mis sisaldab järgnevaid mooduleid (eraldi plaate):
* AVR ATmega128 arendusplaat (kontroller)
* Kasutajaliides ehk sisend-väljundmoodul (nupud, valgusdioodid, 2 x LCD väljund, 7-segment-indikaator)
* Mootorite moodul
* Andurite moodul
Moodulite pikema kirjelduse koos pistikute piikide täpse kirjeldusega leiab leheküljelt
[[http://home.roboticlab.eu/et/hardware/homelab]]
Järgneval pildil on toodud lihtsustatud ülevaade andurite jms ühendamisest.
{{:images:projects:soccer_robot:moodulite_uehendused.png|}}
=== Toiteahel ===
Robotil vajab toitepinget nii kontrolleri moodul kui ka mootorite moodul. Mõlemad kasutavad energiaallikana sama akupatareid. Kasutatakse kaheks hargnevat juhet. MOotorite mooduli toitepistiku ühendamise õpetus on lehel
[[http://home.roboticlab.eu/et/hardware/homelab/motor]]
NB! Standardse akupatarei fikseeritud pinge tõttu peab kontrolleri plaadil lühistama dioodsilla. Silla funktsioon plaadil on pöörata toitepinge polaarsus alati ühte pidi. See tähendab, et silda kasutades pole toitepinge polaarsus tähtis. Paraku jääb sillal u 1,5V pingelangu, mis on lubamatult palju.
{{:images:projects:soccer_robot:silla_luehistamine.jpg|}}
Lühistades silla on toitepinge õige polaarsus tähtis! Pistiku keskmine piik on positiivne ja välime äär negatiivne.
=== Koodrid ===
[{{ :images:projects:soccer_robot:optokatkesti_elitr8102.jpg?200|Optokatkesti}}]
Roboti veermikul on mõlema lindi ülekandes 2 aukudega hammasratast. Asetades optokatkesti niimoodi hammasratta kohale, et see jääb optokatkesti pilu vahele saab optokatkestiga registreerida hammasrattas olevaid auke. Kui optokatkesti vahele jääb auk, siis optokatkesti ühes otsas oleva valgusdioodi valgus kiirgab teises otsas oleva fototransistori peale ja viimane hakkab voolu juhtima. Lugedes pöörlevas hammasrattas olevaid auke saab selle info põhjal välja arvutada läbi teepikkuse. Originaalis on mõlemas veermiku hammasrattas üks auk, kuid sinna tuleb sümmeetriliselt juurde puurida 2 auku, et koodri täpsust parandada. Sedasi saab lindi läbitud teepikkust mõõta ligikaudu 1 cm täpsusega.
Koodrid on ühendatud Kodulabori Mootorite mooduli "encoder" pistikupesas. Vasaku poole kooder on ülemises, parema poole kooder alumises pesas. Koodrite impulside lugemiseks kasutatakse tarkvara Kodulabori teegi koodrite moodulit.
=== RC5 vastuvõtja ===
[{{ :images:projects:soccer_robot:ir_rx_iso.png?200|RC5 vastuvõtja}}]
Robotexil on väravate kohale paigutatud infrapuna signaali saatjad, mis edastavad Philips’i RC5 protokolli abil kanaleid 1 kuni 4. Nende signaalide vastuvõtmiseks on tehtud eraldiseisev moodul. Vastuvõtumoodul ühendatakse kodulabori kommunikatsioonimooduliga kaabliga, mille ühendusskeem on välja toodud plokkskeemis. Samas on välja toodud info vastuvõtja olulisemate komponentide kohta.
Vastuvõtumoodulile on paigutatud kaks signaali vastuvõtjat/demoduleerijat. Tänu sellele on võimalik paika panna roboti asend väravate suhtes.
Vastuvõtja saadab 4800 bps kiirusel välja 1-baidiseid UART sõnumeid, milles sisaldub infrapunavastuvõtja indeks ning vastuvõetud kanal. Väljasaadetavate UART sõnumite kirjeldused on välja toodud allpool olevates tabelites:
**Vastuvõtja indeksiga 0 (vasakpoolne)** [{{ :images:projects:soccer_robot:rc5_plokkskeem.png?150|RC5 vastuvõtja plokkskeem}}]
^ Kanal ^ Kaheksandiksüsteemis(HEX) ^ Kahendsüsteemis(BIN) ^
| 1 | 0x01 | 0b00000001 |
| 2 | 0x02 | 0b00000010 |
| 3 | 0x03 | 0b00000011 |
| 4 | 0x04 | 0b00000100 |
**Vastuvõtja indeksiga 1 (parempoolne)**
^ Kanal ^ Kaheksandiksüsteemis(HEX) ^ Kahendsüsteemis(BIN) ^
| 1 | 0x11 | 0b00010001 |
| 2 | 0x12 | 0b00010010 |
| 3 | 0x13 | 0b00010011 |
| 4 | 0x14 | 0b00010100 |
RC5 vastuvõtja skeemi ja trükkplaadi pildid. Skeemi ja trükplaadi failid, tarkvara ning komponentide nimistu paiknevad lehekülje alumises osas, alajaotuses "Failid".
[{{:images:projects:soccer_robot:rc5_vastuvotja_skeem.png?200|RC5 vastuvõtja skeem}}][{{:images:projects:soccer_robot:rc5_vastuvotja_plaat.png?200|RC5 vastuvõtja trükkplaat}}]
=== Palliandur ===
Palli tuvastamiseks rulliku all kasutatakse infrapuna peegeldusandurit. Saatajalt peegeldunud kiirgus jõuab vastuvõtjasse ja selle kiirguse intensiivsuse järgi saab määrata objekti kauguse. Intensiivsus sõltub lisaks kaugusele ka objekti pinna värvist ja siledusest. Robotexi ülesande golfipall on alati ühesugune ja seega vastab igale intensiivuse tasemele kindel kaugus andurist.
[{{ :images:projects:soccer_robot:pallianduri_skeem.jpg?200|Pallianduri skeem}}]
Kuna võistlusel on alati palju välklampe, kaameraid, valgusteid jms infrapunakiirguse allikaid, siis kasutatakse moduleeritud signaali, st saatja kiirgab teatud sagedusel ja vastuvõtja reageerib ainult sellel sagedusel olevale signaalile. Kõik selle teeb ära üks integraallülitus - Hamamatsu S4282-51. Ainsaks väliseks komponendiks on infrapunakiirgur (diood) ning tundlikkust reguleeriv takisti jadamisi dioodiga.
Pallianduri skeem on näidatud pildil. U1 on Hamamatsu S4282-51 andur. Kondensaator C1 silub toitepinge kõikumist. Kuna IP-diood võtab üsna palju voolu, siis selle sisse-välja lülitamise hetketel muutub voolutugevus anduri juhtmetes. Juhtmete induktiivsuse tõttu ei saa muutus toimuda hetkeliselt ja kondensaator täidab lühiajalise energiaallika osa. Kondensaatori parameetrid pole kriitilised. Peaasi, et nimipinge ületab 5V ja mahtuvus 1uF või rohkem.
Takisti R1 määrab anduri tundlikkuse. Ilma takistita oleks anduri reageermiskaugus u 5cm (sõltub ka IP-dioodi valikust). Takisti valimine käib katse-eksituse meetodil (vahemik 0 - 30 oomi).
[{{ :images:projects:soccer_robot:peegeldusandur.jpg?200|Peegeldusandur}}]
Dioodi valimisel tuleb lähtuda S4282-51 andmelehel märgitud lainepikkusest (800nm), kus andur on kõige tundlikum. Dioodi kiirgusnurk peaks olema võimalikult väike, et palliandur näeks ainult otse ette. Suure nurgaga dioodi puhul võib andur reageerida juba siis, kui pall pole täpselt otse anduri ees. Dioodi kiirgusnurk 11 kraadi ja alla selle tagab hea tulemuse.
Pistik JP1:
- Signaal, madal kui andur tuvastab palli
- Toide +5V
- Maa (0V)
==== Programm ====
Roboti tarkvara on kirjutatud AVR Studios C keeles. Tarkvara kasutab kodulabori teeki ja AVR-GCC kompilaatorit mis tuleb kaasa WinAVR-iga. Programm on jagatud funktsioonide järgi mitmeks failiks - näiteks on sõitmise funktsioonide ja andurite näitude lugemiseks erinevad failid. Põhifailis asub //main// funktsioon mis käivitab kõik juhtimis- ja tagasiside protsessid. Roboti algoritm asub samas failis olevas suures olekutabelis.
Programm on üles ehitatud tavapärase olekumasina eeskujul, kuid et kood liiga pikaks ei läheks ning kogu algoritm ühes kohas koos oleks, kasutatakse sisendite kontrolliks ja väljundite juhtimiseks ühtset suurt tabelit. Selleks, et algoritmis saaks kiirelt ja mugavalt lugeda andurite näite, juhtida mootoreid ja kuvada infot, on kõik muud protsessid toimima pandud katkestuste pealt. Katkestuste pealt töötades ei sega mõõtmis- ja juhtimisprotsessid algoritmi tööd ja vastupidi - need toimuvad paralleelselt.
Tabeli struktuur on järgmine:
* Sisendid
* Olek
* Taimer
* Vasak enkooder
* Parem enkooder
* Nupud
* Infrapuna kaugusandur
* Ultraheli kaugusandur
* Palliandur
* Oma värava suund
* Vastase värava suund
* Väljundid
* Uus olek
* Taimer
* Platvorm
* Pallihoidmise rullik
* 7-segmendiline indikaator
* Punane LED
* Ultraheli kaugusanduri väärtuse meelde jätmise lipuke
Tabeli ridade pikkuse vähendamiseks ning määramata sisendite/väljundite võimaldamiseks kasutatakse tabelis makrokäsklusi. Järgnevalt on kasutatavad käsklused lahti seletatud.
^ Käsklus ^ Seletus ^
| EQ(n) | Sisend peab olema n-ga võrdne |
| NE(n) | Sisend ei tohi olla n-ga võrdne |
| GT(n) | Sisend peab olema suurem n-st |
| LT(n) | Sisend peab olema väiksem n-st |
| BM(n) | Kontrollitakse n-ndat bitti sisendis |
| CSM(n) | Sisendi väärtus peab olema suurem või võrdne n ja eelmise meelde jäetud ultraheliandurist saadud kauguse summaga |
| CSB(n) | Sisendi väärtus peab olema suurem või võrdne n ja eelmise meelde jäetud ultraheliandurist saadud kauguse vahega |
|||
| DRV(l, r) | Seab vasaku mootori kiiruseks l ja parema mootori kiiruseks r. Arvud -100...100, kus 0 on peatatud olek ning negatiivne arv tähistab sama kiirust vastassuunas. |
| STA(n) | Seab uue oleku n |
| TMR(n) | Seab taimeri uueks väärtuseks n |
| ROL(0/1) | Lülitab pallihoidmise rulliku välja/sisse |
| LED(0/1) | Lülitab LED'i välja/sisse |
| SEG(0-9) | Seab 7-segmendilise indikaatori näidatava väärtuse 0-9 |
//
// Input-output logic list
// This table does all the "thinking"
//
logic_step logic_list[] =
{
// INPUT OUTPUT
// STATE TIMER CODEL CODER BUTTN IRRED USONI BALLS OWN OPPO STATE TIMER CHASSIS ROLLER SEGMNT LEDRED US M+
{ EQ( 1), 0, 0, 0, BM(1), 0, 0, 0, 0, 0, STA( 2), 0, 0, 0, 0, LED(1), 0 }, // Start command
{ 0, 0, 0, 0, BM(4), 0, 0, 0, 0, 0, STA( 1), 0, DRV( 0, 0), ROL(0), SEG(0), LED(0), 0 }, // Stop command
// --- Drive to the center ------------------------------------------------------------------------------------------------------------------------------------------
{ EQ( 2), 0, 0, 0, 0, 0, 0, 0, 0, 0, STA( 3), 0, DRV(-100, 100), 0, 0, 0, true },
{ EQ( 3), 0, 0, GT(18), 0, 0, 0, 0, 0, 0, STA( 4), 0, DRV( 100, 100), 0, 0, 0, 0 },
{ EQ( 4), 0, CSB(1000), CSB(1000), 0, 0, 0, 0, 0, 0, STA( 5), 0, DRV( 100,-100), 0, 0, 0, 0 },
{ EQ( 5), 0, GT(18), 0, 0, 0, 0, 0, 0, 0, STA( 10), 0, DRV( 0, 0), 0, 0, 0, 0 },
// --- Start searching ----------------------------------------------------------------------------------------------------------------------------------------------
{ EQ( 10), 0, 0, 0, 0, 0, 0, 0, 0, 0, STA( 11), 0, DRV( 100, 100), ROL(0), SEG(1), 0, 0 },
{ EQ( 11), 0, 0, 0, 0, 0, 0, EQ(1), 0, 0, STA( 90), 0, 0, 0, 0, 0, 0 }, // Found a random ball
{ EQ( 11), 0, 0, 0, 0, 0, LT( 600), 0, 0, 0, STA( 20), 0, DRV( 0, 0), 0, 0, 0, 0 }, // Sudden closer distance on the right, investigate
{ EQ( 11), 0, 0, 0, 0, LT( 200), 0, 0, 0, 0, STA(100), 0, DRV( 0, 0), 0, 0, 0, 0 }, // Something's in the way, turn around
// --- Precise search -----------------------------------------------------------------------------------------------------------------------------------------------
{ EQ( 20), 0, 0, 0, 0, 0, 0, 0, 0, 0, STA( 21), TMR(5000), DRV( 50, 50), 0, SEG(2), 0, 0 },
{ EQ( 21), 0, 0, 0, 0, 0, 0, EQ(1), 0, 0, STA( 90), 0, 0, 0, 0, 0, 0 }, // Found a random ball
{ EQ( 21), 0, 0, 0, 0, LT( 200), 0, 0, 0, 0, STA(100), 0, DRV( 0, 0), 0, 0, 0, 0 }, // Something's in the way, turn around
{ EQ( 21), EQ( 0), 0, 0, 0, 0, LT( 600), 0, 0, 0, STA( 22), 0, DRV( 0, 0), 0, 0, 0, 0 }, // Suspected ball seems to be a wall instead
{ EQ( 21), EQ( 0), 0, 0, 0, 0, GT( 599), 0, 0, 0, STA( 10), 0, 0, 0, 0, 0, 0 }, // Didn't recognize a ball, return to search
{ EQ( 21), LT(4500), 0, 0, 0, 0, GT( 599), 0, 0, 0, STA( 30), 0, DRV( 0, 0), 0, 0, 0, true }, // Identified a ball, go get it
{ EQ( 22), 0, 0, 0, 0, 0, 0, 0, 0, 0, STA( 23), 0, DRV(-100, 100), 0, 0, 0, true }, // Try to get away from the wall
{ EQ( 23), 0, 0, GT(18), 0, 0, 0, 0, 0, 0, STA( 24), 0, DRV( 100, 100), 0, 0, 0, 0 },
{ EQ( 24), 0, CSB(750), CSB(750), 0, 0, 0, 0, 0, 0, STA( 25), 0, DRV( 100,-100), 0, 0, 0, 0 },
{ EQ( 25), 0, GT(18), 0, 0, 0, 0, 0, 0, 0, STA( 10), 0, DRV( 0, 0), 0, 0, 0, 0 }, // Resume search
// --- Turn to ball -------------------------------------------------------------------------------------------------------------------------------------------------
{ EQ( 30), 0, 0, 0, 0, 0, 0, 0, 0, 0, STA( 31), 0, DRV( 100, 100), ROL(1), SEG(3), 0, 0 },
{ EQ( 31), 0, 0, 0, 0, 0, 0, EQ(1), 0, 0, STA( 90), 0, 0, 0, 0, 0, 0 }, // Found a random ball
{ EQ( 31), 0, GT(MTS(150)), GT(MTS(150)), 0, 0, 0, 0, 0, 0, STA( 32), 0, DRV( 100,-100), 0, 0, 0, 0 }, // Turn right
{ EQ( 32), 0, GT(18), 0, 0, 0, 0, 0, 0, 0, STA( 33), 0, DRV( 75, 75), 0, 0, 0, 0 }, // Start driving towards the wall
{ EQ( 33), 0, 0, 0, 0, LT( 150), 0, 0, 0, 0, STA( 40), 0, DRV(-100, 100), ROL(0), 0, 0, 0 }, // Wall too close, turn around and get back to the center
{ EQ( 33), 0, 0, 0, 0, 0, LT( 300), 0, 0, 0, STA( 34), 0, DRV( 100, 100), 0, 0, 0, true }, // Spotted the ball
{ EQ( 34), 0, GT(MTS( 50)), GT(MTS( 50)), 0, 0, 0, 0, 0, 0, STA( 35), 0, DRV( 100,-100), 0, 0, 0, 0 }, // Turn towards the ball
{ EQ( 35), 0, GT(18), 0, 0, 0, 0, 0, 0, 0, STA( 36), 0, DRV( 90, 90), 0, 0, 0, 0 },
{ EQ( 36), 0, CSM(50), CSM(50), 0, 0, 0, EQ(1), 0, 0, STA( 90), 0, 0, 0, 0, 0, 0 }, // Caught the ball
{ EQ( 36), 0, CSM(50), CSM(50), 0, 0, 0, EQ(0), 0, 0, STA( 45), 0, DRV( 0, 0), 0, 0, 0, 0 }, // Didn't get the ball
{ EQ( 40), 0, 0, GT(34), 0, 0, 0, 0, 0, 0, STA( 41), 0, DRV( 100, 100), 0, 0, 0, 0 },
{ EQ( 41), 0, GT(MTS(700)), GT(MTS(700)), 0, 0, 0, 0, 0, 0, STA( 42), 0, DRV( 100,-100), 0, 0, 0, 0 },
{ EQ( 42), 0, GT(18), 0, 0, 0, 0, 0, 0, 0, STA( 10), 0, DRV( 0, 0), 0, 0, 0, 0 }, // Resume search
{ EQ( 45), 0, 0, 0, 0, 0, LT( 801), 0, 0, 0, STA( 46), 0, DRV( 100,-100), 0, 0, 0, 0 }, // Drive back to the center
{ EQ( 45), 0, 0, 0, 0, 0, GT( 800), 0, 0, 0, STA( 47), 0, DRV( 100,-100), 0, 0, 0, true },
{ EQ( 46), 0, GT(18), 0, 0, 0, 0, 0, 0, 0, STA( 49), 0, DRV( 100,-100), 0, 0, 0, 0 },
{ EQ( 47), 0, GT(18), 0, 0, 0, 0, 0, 0, 0, STA( 48), 0, DRV( 100, 100), 0, 0, 0, 0 },
{ EQ( 48), 0, CSB(800), CSB(800), 0, 0, 0, 0, 0, 0, STA( 46), 0, DRV( 100,-100), 0, 0, 0, 0 },
{ EQ( 49), 0, GT(18), 0, 0, 0, 0, 0, 0, 0, STA( 10), 0, DRV( 0, 0), 0, 0, 0, 0 }, // Return to search
// --- Locate the goal ----------------------------------------------------------------------------------------------------------------------------------------------
{ EQ( 90), 0, 0, 0, 0, 0, 0, 0, 0, 0, STA( 91), 0, DRV( 50, 50), ROL(1), SEG(4), 0, 0 },
{ EQ( 91), 0, GT(MTS( 50)), GT(MTS( 50)), 0, 0, 0, 0, 0, 0, STA( 92), TMR(1000), DRV( -70, 70), 0, 0, 0, 0 },
{ EQ( 92), 0, 0, 0, 0, 0, 0, 0, 0, LT(0), 0, 0, DRV( -70, 70), 0, 0, 0, 0 }, // Goal to the left
{ EQ( 92), 0, 0, 0, 0, 0, 0, 0, 0, GT(0), 0, 0, DRV( 70, -70), 0, 0, 0, 0 }, // Goal to the right
{ EQ( 92), EQ( 0), 0, 0, 0, 0, 0, 0, 0, EQ(0), STA( 95), 0, DRV( 100, 100), 0, 0, 0, 0 }, // Goal straight ahead
// --- Score the goal -----------------------------------------------------------------------------------------------------------------------------------------------
{ EQ( 95), 0, 0, 0, 0, 0, 0, 0, 0, 0, STA( 96), 0, DRV( 100, 100), 0, SEG(5), 0, 0 },
{ EQ( 96), 0, 0, 0, 0, LT( 300), 0, 0, 0, 0, STA(100), 0, DRV( 0, 0), ROL(0), 0, 0, 0 }, // Goal scored, turn around
// --- Turn around --------------------------------------------------------------------------------------------------------------------------------------------------
{ EQ(100), 0, 0, 0, 0, 0, 0, 0, 0, 0, STA(101), 0, DRV(-100, 100), 0, SEG(6), 0, 0 },
{ EQ(101), 0, GT(34), 0, 0, 0, 0, 0, 0, 0, STA( 10), 0, DRV( 0, 0), 0, 0, 0, 0 }
};
Järgnevalt on toodud roboti //main// funktsioon kus käivitatakse kõik katkestustel toimuvad protsessid ja täidetakse põhialgoritmi vastavalt olekutabelist loetud väärtustele. Selles funktsioonis asub lõputu tsükkel, mis kontrollib igal läbimisel kõigis tabeli ridades olevaid sisendeid. Kui mõne tabelirea kõigis määratud sisendites on vastav väärtus, siis täidetakse samas reas kirjeldatud väljundite väärtused. Näiteks roboti käivitamiseks nupust on tabeli alguses rida, mille ainsateks sisendtingimusteks on see, et robot on peatatud ning vastavat nuppu on vajutatud. Kui need tingimused on täidetud, määratakse olekuks "2" ning robot hakkab palliotsimisprotsessiga pihta.
Enne tabeli ridade kontrollimist loetakse puhvritest kõigi andurite väärtused ning uuendatakse ka LCD ekraanil olevat infot. Et vähendada ekraani uuendamisega kaasnevat viidet on uuendamine jagatud kuue tsükli vahel, millest igas tsüklis uuendatakse erineva anduri väärtust ekraanil.
//
// Main program.
//
int main(void)
{
unsigned char i;
unsigned short timer;
unsigned short encoder_left;
unsigned short encoder_right;
unsigned short buttons;
unsigned short infrared;
unsigned short ultrasonic;
unsigned short ball;
signed char own_goal;
signed char target_goal;
// Initial state
unsigned short state = 1;
// LCD counter
unsigned short lcdcount = 0;
// Initialize hardware.
init();
// Loop forever
while (true)
{
// Read sensor values
chassis_get_steps(&encoder_left, &encoder_right);
timer = timeout_get_counter();
buttons = sensors_buttons();
infrared = sensors_infrared_distance();
ultrasonic = sensors_ultrasonic_distance();
ball = sensors_is_ball();
own_goal = beacon_locate_own_goal();
target_goal = beacon_locate_opponent_goal();
// Display ultrasonic distance.
switch (lcdcount % 6)
{
case 0:
lcd_alpha_write_stringf_to(0, 0, "U%04d ", ultrasonic);
break;
case 1:
lcd_alpha_write_stringf_to(0, 1, "I%04d ", infrared);
break;
case 2:
lcd_alpha_write_stringf_to(6, 0, "M%03d ", own_goal);
break;
case 3:
lcd_alpha_write_stringf_to(6, 1, "O%03d ", target_goal);
break;
case 4:
lcd_alpha_write_stringf_to(12, 0, "L%03d ", encoder_left);
break;
case 5:
lcd_alpha_write_stringf_to(12, 1, "R%03d ", encoder_right);
break;
}
lcdcount++;
pin_set_to(led_green, !ball);
//pin_toggle(led_green);
// Decide state
for (i = 0; i < NUM_LOGIC_LIST_ITEMS; i++)
{
// Check input conditions match
if (input_check_value(logic_list[i].input_state, state) &&
input_check_value(logic_list[i].input_timer, timer) &&
input_check_value(logic_list[i].input_encoder_left, encoder_left) &&
input_check_value(logic_list[i].input_encoder_right, encoder_right) &&
input_check_value(logic_list[i].input_buttons, buttons) &&
input_check_value(logic_list[i].input_infrared, infrared) &&
input_check_value(logic_list[i].input_ultrasonic, ultrasonic) &&
input_check_value(logic_list[i].input_ball_sensor, ball) &&
input_check_value(logic_list[i].input_own_goal, own_goal) &&
input_check_value(logic_list[i].input_opponent_goal, target_goal))
{
// Set new state ?
if (logic_list[i].output_state)
{
state = logic_list[i].output_state & 0x7FFF;
}
// Set timer
if (logic_list[i].output_timer)
{
timeout_start(logic_list[i].output_timer & 0x7FFF);
}
// Drive ?
if (logic_list[i].output_drive)
{
chassis_tank_drive((signed char)((logic_list[i].output_drive >> 8) & 0xFF),
(signed char)( logic_list[i].output_drive & 0xFF));
}
// Use roller ?
if (logic_list[i].output_roller)
{
chassis_use_roller(logic_list[i].output_roller & 0x01);
}
// Use red LED ?
if (logic_list[i].output_led_red)
{
pin_set_to(led_red, !(logic_list[i].output_led_red & 0x01));
}
// Use 7-segment display
if (logic_list[i].output_segment)
{
segment_display_write(logic_list[i].output_segment & 0xFF);
}
// Remember current ultrasonic reading
if (logic_list[i].remember_usonic)
{
usonic_memory = ultrasonic;
}
// Got match
break;
}
}
}
}
===== Montaaž =====
{{:images:projects:soccer_robot:montage:koik_osad.jpg?400|Jalgpalliroboti kõik osad}}
**Esimese sammuna** kinnitatakse alusplaadile koodrid. Selleks läheb vaja:
* 4 M3x10 polti
* 8 mutrit
Kõigepealt kinnitatakse poldid mutritega alusplaadi külge, seejärel paigutatakse koodrid poltidele ning kinnitatakse need mutritega. Sel viisil tagatakse, et optokatkesti on piisavalt lähedal hammasrattale ja suudab registreerida hammasrattas olevaid auke.
[{{:images:projects:soccer_robot:montage:01_alusplaat.jpg?200|1a. Alusplaat}}][{{:images:projects:soccer_robot:montage:02_koodrid.jpg?200|1b. Koodrite kinnitamine alusplaadile}}]
~~CL~~
Koodrite täpsuse parandamiseks on hammasrattale sümmeetriliselt juurde puuritud 2 auku.
~~CL~~
[{{:images:projects:soccer_robot:montage:03_koodrid_hammasrattad.jpg?200|1c. Augud hammasrattas koodri jaoks}}]
~~CL~~
**Teise sammuna** kinnitatakse alusplaadi külge ultraheli kaugusandur. Selleks läheb vaja:
* 2 10 mm kõrgust puksi (M3 keere).
* 2 M3 polti (väikse peaga)
* 2 mutrit
[{{:images:projects:soccer_robot:montage:04_ultraheli.jpg?200|2. Ultraheli kaugusanduri kinnitamine}}]
~~CL~~
**Kolmandana** pannakse kokku rullimehhanism. Rullimehhanismi kokkupanekuks on vaja:
* 6 M3x6 polti, 2 mootori kinnitamiseks haaratsi külge, 2 hinge kinnitamiseks haaratsi külge, 2 hinge kinnitamiseks alusplaadi külge.
* 4 seibi, 2 mootori kinnitamisel ja 2 hinge kinnitamisel haaratsi külge.
* 4 mutrit
* kahepoolne teip
~~CL~~
Esmalt kinnitatakse hing haaratsi külge. Haaratsi ja hinge vahel kasutatakse seibe, tagades sel viisil hinge vaba liikumise. Hilisem kinnitamine on raskendatud, kuna rull jääks ette.
[{{:images:projects:soccer_robot:montage:05_haarats_hing.jpg?200|3a. Hinge kinnitamine haaratsi külge}}]
~~CL~~
Järgmise sammuna kinnitatakse haaratsi külge mootor (3b). Peale seda kinnitatakse kahepoolse teibi abil haaratsi külge optiline palliandur (3c).
~~CL~~
[{{:images:projects:soccer_robot:montage:06_haarats_mootor.jpg?200|3b. Mootori kinnitamine haaratsi külge}}]
[{{:images:projects:soccer_robot:montage:08_haarats_palliandur.jpg?200|3c. Optilise anduri kinnitamine}}]
~~CL~~
Nüüd kinnitatakse mootorivõlli otsa rull, mis fikseeritakse võllile poldiga (3d). Seejärel pannakse rullile peale kummirõngad (3e). Rullimehhanism on nüüd kokku pandud.
~~CL~~
[{{:images:projects:soccer_robot:montage:09_haarats_rull.jpg?200|3d. Rulli kinnitamine võllile}}]
[{{:images:projects:soccer_robot:montage:10_haarats_rull_kumm.jpg?200|3e. Kummirõngaste paigaldamine rullile}}]
~~CL~~
Lõpuks kinnitatakse rullimehhanism alusplaadi külge.
~~CL~~
[{{:images:projects:soccer_robot:montage:11_alusplaat_haarats_2.jpg?200|3f. Rullimehhanismi kinnitamine alusplaadi külge}}]
~~CL~~
**Neljanda sammuna** paigaldatakse alusplaadi külge andurite kinnitus koos infrapuna kaugusanduriga ja puksid, millele Kodulabori moodulid paigaldatakse. RC5 vastuvõtja paigaldatakse alles peale alusplaadi kinnitamist veermiku külge, kuna enneaegsel paigaldamisel saab ligipääs kruvikeerajaga raskendatud olema.
Kinnituse ja pukside paigaldamiseks läheb vaja:
* 2 M3x6 polti, andurite kinnituse paigaldamiseks
* 4 20 mm kõrgust puksi (M3 keere).
* 6 mutrit.
[{{:images:projects:soccer_robot:montage:12_alusplaat_infrapuna_2.jpg?200|4a. Andurite kinnituse paigaldamine alusplaadile}}]
[{{:images:projects:soccer_robot:montage:13_alusplaat_kodulabori_puksid.jpg?200|4b. Pukside kinnitamine}}]
~~CL~~
**Viies samm** on alusplaadi kinnitamine veermikule ja RC5 vastuvõtja paigaldamine andurite kinnitusele. Selleks läheb vaja:
* 4 M3x6 polti.
* Kahepoolne teip.
~~CL~~
[{{:images:projects:soccer_robot:montage:14_platvorm_alusplaat.jpg?200|5a. Alusplaadi kinnitamine platvormile.}}]
[{{:images:projects:soccer_robot:montage:15_alusplaat_rc5.jpg?200|5b. RC5 vastuvõtja paigaldamine.}}]
~~CL~~
**Kuuendana** kinnitatakse puksidele Kodulabori moodulid. Kinnitamiseks on vaja:
* 4 M3x6 polti.
~~CL~~
[{{:images:projects:soccer_robot:montage:16_kodulabori_moodulid.jpg?200|6. Kodulabori moodulite kinnitamine puksidele}}]
~~CL~~
**Seitsmenda** sammuna ühendatakse roboti elektroonikaosade vahel kõik juhtmed. Alustada võiks toite harukaablist mis jagab Kontrollermoodulisse minema toite kaheks millest teine pistik tuleb ühendada Mootoite mooduliga.
[{{:images:projects:soccer_robot:montage:17_kodulabor_toitepistik.jpg?200|7a. Toitepistikute ühendamine mootori ja kontrolleri moodulile}}]
~~CL~~
RC5 vastuvõtja tuleb ühendada Kommunikatsioonimooduli välisesses EXT_UART pesasse:
[{{:images:projects:soccer_robot:montage:18_kodulabor_rc5_kaabel.jpg?200|7b. RC5 vastuvõtja ühendamine}}]
~~CL~~
Roomiku kaks mootorit tuleb ühendada Mootoritemooduli DC3 ja DC4 pesadesse. Koodrid lähevad sinnasamasse kõrvale ENC1 ja ENC2 pesadesse:
[{{:images:projects:soccer_robot:montage:19_kodulabor_mootorid_koodrid.jpg?200|7c. Roomikute mootorite ja koodrite ühendamine}}]
~~CL~~
Edasi tuleks ühendada ultraheli- ja infrapuna kaugusandurid ning palliandur. Infrapuna kaugusanduri ja pallianduri jaoks on tarbis servode pikenduskaablit. Täpsemalt on pesad näidatud piltidel:
[{{:images:projects:soccer_robot:montage:20_kodulabor_infrapuna_ultraheli_kaabel.jpg?200|7d. Ultraheli- ja infrapunaanduri ühendamine. Ultraheli toide ja signaal käivad eraldi pistikutesse}}]
[{{:images:projects:soccer_robot:montage:21_kodulabor_palliandur_kaabel.jpg?200|7e. Pallianduri ühendamine}}]
~~CL~~
Viimasena on jäänud ühendada LCD kus kuvatakse programmi töö ajal kõiki andurite näitusid:
[{{:images:projects:soccer_robot:montage:23_robot_kaablivitsad.jpg?200|7f. Kõik moodulid omal kohal}}]
~~CL~~
**Kaheksas** ja viimane etapp on robotisse akude või patareide laadimine ning selle tööle panek. Akud käivad spetsiaalsesse alusplatvormiga kaasatulevasse rakisesse. Ühendades toitekaabli ja akuploki läheb robot tööle ja sinna saab peale laadida programmi.
[{{:images:projects:soccer_robot:montage:24_patareipakk.jpg?200|8a. Akupatarei paigaldamine}}]
[{{:images:projects:soccer_robot:montage:25_patareide_yhendamine.jpg?200|8b. Roboti pingestamine}}]
~~CL~~
[{{ :images:projects:soccer_robot:montage:26_robot_valmis_pingestatud.jpg?400 |Töövalmis robot}}]
===== Video =====
{{youtube>large:KFhU-NHMZfo}}
===== Soovitused =====
* Rull teha võimalikult lai, et paremini palle kätte saada. Samas tuleb siis ka palliandur ümber teha nii, et LED ja vastuvõtja on haaratsi otses suunatud üksteise vastu ja nad jälgivad kas nende vahele satub pall.
* Alusplaadi, rullimehhanismi haaratsi ja andurite kinnituse tegemiseks on soovitatav kasutada materjali, mille painutamisega ei oleks probleeme ning mille puhul ei oleks ohtu, et see painutamisel murdub või paindekohast praguneb. Prototüübi valmistamisel kasutatati 1 mm paksust alumiiniumi, mis antud detailide tegemiseks suurepäraselt sobis.
* Alusplaadi, rullimehhanismi haarasti ja andurite kinnituse tegemiseks on soovitatav kasutada CNC-tööpinki. Sellega tagatakse detailide valmistamisel võimalikult väike eksimisvõimalus (nt avade puurimisel).
* Programmi kirjutada meetod vastase robotist möödumiseks. Samas eeldab see rohkem andureid, näiteks peegeldusandurit allpool väljaku taset oleva väravapõhja tuvastamiseks.
===== Failid =====
{{ :images:projects:soccer_robot:robot_2.jpg?200|Jalgpallirobot}}
* {{:images:projects:soccer_robot:joonised_mudel.rar|Mudelid ja joonised}}
* {{:images:projects:soccer_robot:soccer_robot_software.zip|Funktsioonidega programm}}
* {{:images:projects:soccer_robot:soccer_robot_table_based.zip|Tabelitega programm}}
* {{:images:projects:soccer_robot:skeem.zip|RC5 vastuvõtja skeemi ja trükkplaadi joonised}}
* {{:images:projects:soccer_robot:tarkvara.zip|RC5 vastuvõtja tarkvara}}
* {{:images:projects:soccer_robot:rc5_komponendid.rar| RC5 vastuvõtja komponentide nimistu}}
~~CL~~
© TTÜ, MTÜ TTÜ Robotiklubi
~~DISCUSSION~~