- Kružni dijagram
- Generiranje PWM signala na GPIO pinu za upravljanje servo motorom
- Programiranje PIC16F8771A za robotsku ruku
- Simulacija koda robotskog oružja PIC-a
- Dizajn PCB-a pomoću EasyEDA-e
- Izračunavanje i naručivanje uzoraka putem interneta
- Rad robotske ruke PIC-a
Od proizvodne trake automobilske proizvodne industrije do telehirurških robota u svemiru, robotsko oružje možete pronaći svugdje. Mehanizmi ovih robota slični su ljudskim koji se mogu programirati za slične funkcije i povećane mogućnosti. Mogu se koristiti za brže i preciznije ponavljanje radnji od ljudi ili u surovim uvjetima bez riskiranja ljudskog života. Već smo izgradili Record and Play Robotic Arm koristeći Arduino koji se može obučiti za izvršavanje određenog zadatka i učiniti da se ponavlja zauvijek.
U ovom uputstvu koristit ćemo industrijski standard PIC16F877A 8-bitni mikrokontroler za upravljanje istom robotskom rukom s potenciometrima. Izazov ovog projekta je da PIC16F877A ima samo dva pina sposobna za PWN, ali moramo kontrolirati oko 5 servo motora za našeg robota koji zahtijeva 5 pojedinačnih PWM pinova. Dakle, moramo koristiti GPIO pinove i generirati PWM signale na PIC GPIO pinovima pomoću prekidača s odbrojavanjem. Sada bismo, naravno, mogli nadograditi na bolji mikrokontroler ili upotrijebiti IC za uklanjanje multipleksera kako bismo ovdje puno olakšali stvari. Ali ipak, vrijedi pokušati ovaj projekt za iskustvo učenja.
Mehanička struktura robotske ruke koju koristim u ovom projektu u potpunosti je 3D ispisana za moj prethodni projekt; cjelovite datoteke dizajna i postupak montaže možete pronaći ovdje. Ako nemate 3D printer, također možete izraditi jednostavnu robotsku ruku pomoću kartona kao što je prikazano u poveznici. Pod pretpostavkom da ste se nekako dokopali svoje robotske ruke, idemo u projekt.
Kružni dijagram
Kompletna shema sklopa za ovu robotsku ruku zasnovanu na PIC mikrokontroleru prikazana je u nastavku. Sheme su nacrtane pomoću EasyEDA-e.

Shema sklopa prilično je jednostavna; kompletan projekt napaja 12V adapter. Tih se 12V pretvara u + 5V pomoću dva regulatora napona 7805. Jedan je označen kao + 5V, a drugi kao + 5V (2). Razlog postojanja dva regulatora je taj što kada se servo okreće uvlači puno struje što stvara pad napona. Ovaj pad napona prisiljava PIC da se sam ponovno pokrene, stoga ne možemo raditi i PIC i servo motore na istoj + 5V tračnici. Dakle, onaj označen kao + 5V koristi se za napajanje PIC mikrokontrolera, LCD-a i potenciometra, a zasebni izlaz regulatora koji je označen kao + 5V (2) koristi se za napajanje servo motora.
Pet izlaznih pinova potenciometra koji pružaju promjenjivi napon od 0V do 5V spojeno je na analogne pinove An0 do AN4 PIC-a. Budući da planiramo koristiti tajmere za generiranje PWM-a, servo motori se mogu spojiti na bilo koji GPIO pin. Odabrao sam iglice od RD2 do RD6 za servo motore, ali to može biti bilo koji GPIO po vašem izboru.
Budući da program uključuje puno otklanjanja pogrešaka, LCD zaslon 16x2 također je povezan sa portB PIC-a. Ovo će prikazati radni ciklus servo motora kojima se upravlja. Osim toga, također sam proširio veze za sve GPIO i analogne pinove, za svaki slučaj ako neki senzori budu trebali biti povezani u budućnosti. Konačno, također sam povezao pin programera H1 za izravno programiranje PIC-a pomoću pickit3 pomoću mogućnosti programiranja ICSP.
Generiranje PWM signala na GPIO pinu za upravljanje servo motorom
Jednom kad je sklop spreman, moramo smisliti kako generirati PWN signale na GPIO pinu PIC-a za upravljanje servo motorom. Nešto slično smo već umorili metodom prekida Timer i uspjeli smo. Ovdje ćemo ga nadograditi, pa ako ste novi ovdje, toplo bih vam preporučio da pročitate ovaj prethodni vodič prije nego što nastavite dalje.
Svi hobi servo motori rade na frekvenciji od 50Hz. Što znači da će jedan potpuni pulsni ciklus za servo motor biti 1/50 (F = 1 / T) što je 20 ms. Od ovih kompletnih 20 ms kontrolni signal je samo od 0 do 2 ms, dok je ostatak signala uvijek isključen. Donja slika pokazuje kako vrijeme uključivanja varira samo od 0 do 2 ms za okretanje motora od 0 stupnjeva do 180 stupnjeva od ukupnog trajanja od 20 ms.

Imajući to na umu, program moramo napisati na takav način da PIC očita 0 do 1204 s potenciometra i preslika na 0 do 100 što će biti radni ciklus servo motora. Koristeći ovaj radni ciklus možemo izračunati vrijeme uključivanja servo motora. Tada možemo inicijalizirati prekid timera da se prelije u redovnom intervalu tako da djeluje slično funkciji millis () u Arduinu. Uz to, možemo prebaciti status GPIO pina na visok za željeno trajanje i isključiti ga nakon 20 ms (jedan cjeloviti ciklus), a zatim ponoviti isti postupak. Sad, kad smo razumjeli logiku, krenimo u program.
Programiranje PIC16F8771A za robotsku ruku
Kao i uvijek kompletni program s video zapisom možete pronaći na kraju ove stranice, kôd se također može preuzeti odavde sa svim potrebnim datotekama. U ovom ćemo odjeljku razgovarati o logici koja stoji iza programa. Program koristi ADC modul, modul za mjerenje vremena i LCD modul za kontrolu robotske ruke. Ako niste svjesni kako koristiti ADC značajke ili značajke odbrojavanja vremena ili povezati LCD s PIC-om, možete se vratiti na odgovarajuće poveznice da biste ih naučili. Objašnjenje u nastavku dano je pod pretpostavkom da je čitatelj upoznat s tim pojmovima.
Konfiguracija priključka odbrojavanja vremena
Najvažniji odjeljak koda je postavljanje timera 0 na prekomjerni protok za svako određeno kašnjenje. Formule za izračunavanje ovog kašnjenja mogu se dati kao
Odgoda = ((256-REG_val) * (Prescal * 4)) / Fosc
Korištenjem registra OPTION_REG i TMR0 postavili smo timer 0 da radi s predskalarnom vrijednošću 32, a REG val postavljen na 248. Frekvencija kristala (Fosc) koja se koristi u našem hardveru je 20 MHz. Pomoću ovih vrijednosti kašnjenje se može izračunati kao
Kašnjenje = ((256-248) * (32 * 4)) / (20000000) = 0,0000512 sekundi (ili) = 0,05 ms
Tako smo sada postavili da se tajmer prelijeva na svakih 0,05 ms. Kôd za isto je dan u nastavku
/ ***** Konfiguracija porta za odbrojavanje ****** / OPTION_REG = 0b00000100; // Timer0 s vanjskom frekvencijom i 32 kao predskalarom // Također omogućuje PULL UPs TMR0 = 248; // Učitavanje vremenske vrijednosti za 0,0001s; delayValue može biti između 0-256 samo TMR0IE = 1; // Omogući bit prekida timera u PIE1 registru GIE = 1; // Omogući globalni prekid PEIE = 1; // Omogući periferni prekid / *********** ______ *********** /
Od ukupnog upravljačkog prozora servo motora od 0 ms do 2 ms, njime možemo upravljati s razlučivošću 0,05 ms, što nam omogućuje da imamo (2 / 0,05) 40 različitih položaja motora između 0 stupnjeva i 180 stupnjeva. Ovu vrijednost možete dodatno smanjiti ako bi je vaš MCU mogao podržati kako bi dobio više položaja i preciznu kontrolu.
Rutinska usluga prekida (ISR)
Sada kada imamo timer 0 postavljen na prekomjerni protok za svakih 0,05 ms, imat ćemo postavljenu zastavicu prekida TMR0IF za 0,05 ms. Dakle, unutar funkcije ISR možemo resetirati tu zastavicu i povećati varijablu koja se zove count za jedan. Dakle, sada će se ova varijabla povećavati za 1 za svakih 0,05 ms.
void interrupt timer_isr () { if (TMR0IF == 1) // Oznaka timera pokrenuta je zbog prelijevanja timera -> postavljeno na overflow za svakih 0,05 ms { TMR0 = 248; // Učitaj timer Vrijednost TMR0IF = 0; // Očisti broj zastavica prekida timera ++; // Broji prirast za 1 za svakih 0,05 ms }
Izračunavanje radnog ciklusa i vremena
Dalje moramo izračunati radni ciklus i na vrijeme za svih pet servo motora. Imamo pet servo motora od kojih se svaki koristi za upravljanje pojedinačnim dijelom ruke. Dakle, moramo pročitati ADC vrijednost svih pet i izračunati radni ciklus i na vrijeme za svaku.
Vrijednost ADC-a bit će u rasponu od 0 do 1024, što se može pretvoriti u radni ciklus od 0% do 100% jednostavnim množenjem 0,0976 (100/1024 = 0,0976) na dobivenu vrijednost. Ovaj radni ciklus od 0 do 100% mora se zatim pretvoriti u vrijeme uključivanja. Znamo da pri 100% radnog ciklusa vrijeme uključivanja mora biti 2 ms (za 180 stupnjeva) pa će se množenjem 0,02 (2/100 = 0,02) 0 do 100 radnog ciklusa pretvoriti u 0 do 2 ms. Ali tada je postavljeno da se naš broj varijabli tajmera povećava jednom za svakih 0,05 ms. To znači da će vrijednost brojanja biti 20 (1 / 0,05 = 20) za svakih 1 ms. Dakle, moramo pomnožiti 20 s 0,02 da bismo izračunali točno vrijeme za naš program koji će nam dati vrijednost 0,4 (0,02 * 20 = 0,4). Kôd za isti prikazan je ispod, možete ga ponoviti 5 puta za svih 5 pota koristeći for petlju. Dobivene vrijednosti pohranjuju se u polje T_ON.
za (int broj_pota = 0; broj_pota <= 3; broj_pota ++) { int Pev_val = T_ON; POT_val = (ADC_Read (pot_num)); // Očitavanje vrijednosti POT pomoću ADC Duty_cycle = (POT_val * 0.0976); // Karta 0 do 1024 do 0 do 100 T_ON = Duty_cycle * 0,4; // 20 * 0,02
Odabir motora koji će se okretati
Ne možemo upravljati svih pet motora zajedno, jer će to otežati usporavanje cijelog mikrokontrolera ISR kodom. Dakle, istovremeno moramo okretati samo jedan servo motor. Da biste odabrali koji servo zakretati, mikrokontroler nadgleda vrijeme UKLJUČENJA svih pet servo motora i uspoređuje ga s prethodnim na vrijeme. Ako dođe do promjene vremena UKLJUČENJA, možemo zaključiti da se određeni servo mora premjestiti. Kôd za isti prikazan je u nastavku.
if (T_ON! = Pev_val) { Lcd_Clear (); servo = broj_pota; Lcd_Set_Cursor (2,11); Lcd_Print_String ("S:"); Lcd_Print_Char (servo + '0'); if (broj_pota == 0) {Lcd_Set_Cursor (1,1); Lcd_Print_String ("A:");} inače if (pot_num == 1) {Lcd_Set_Cursor (1,6); Lcd_Print_String ("B:");} inače if (pot_num == 2) {Lcd_Set_Cursor (1,11); Lcd_Print_String ("C:");} inače if (pot_num == 3) {Lcd_Set_Cursor (2,1); Lcd_Print_String ("D:");} inače if (pot_num == 4) {Lcd_Set_Cursor (2,6); Lcd_Print_String ("E:");} char d2 = (dužni_ciklus)% 10; char d1 = (Duty_cycle / 10)% 10; Lcd_Print_Char (d1 + '0'); Lcd_Print_Char (d2 + '0');
Također ispisujemo ciklus rada servo pogona na LCD zaslonu kako bi korisnik mogao znati njegov trenutni položaj. Na temelju promjene vremena UKLJ., Varijabla servoa ažurira se brojevima od 0 do 4 koji predstavljaju pojedinačne motore.
Upravljanje servo motorom unutar ISR-a
Unutar ISR-a imamo broj varijabli koji se povećava za svakih 0,05 ms, to znači da će se za svakih 1 ms varijabla povećavati za 20. Korištenjem ovoga moramo kontrolirati pinove kako bi proizveli PWM signal. Ako je vrijednost brojača manja od vremena uključenja, GPIO tog motora uključuje se pomoću donje crte
PORTD = PORTD - servo_code;
Ovdje niz servo_code sadrži detalje pina svih pet servo motora, a na temelju vrijednosti u varijabli servo, koristit će se kôd za taj određeni servo motor. Tada je logično ILI (-) sa postojećim PORTD bitovima kako ne bismo remetili vrijednosti drugog motora i ažurirali samo ovaj motor. Slično za isključivanje zatiča
PORTD = PORTD & ~ (servo_code);
Obrnili smo vrijednost bita pomoću logičkog inverznog (~) operatora, a zatim smo izveli operaciju AND (&) na PORTD-u kako bismo isključili samo željeni pin dok smo ostale pinove ostavili u prethodnom stanju. Kompletni isječak koda prikazan je u nastavku.
void interrupt timer_isr () { if (TMR0IF == 1) // Oznaka timera aktivirana je zbog prelijevanja timera -> postavljeno na preljev za svakih 0,05 ms { TMR0 = 248; // Učitaj timer Vrijednost TMR0IF = 0; // Očisti broj zastavica prekida timera ++; // Broji prirast za 1 za svakih 0,05 ms -> brojanje će biti 20 za svakih 1 ms (0,05 / 1 = 20)) } int servo_code = {0b01000000, 0b00100000, 0b00010000, 0b00001000, 0b00000100}; if (count> = 20 * 20) count = 0; if (count <= (T_ON)) PORTD = PORTD - servo_code; else PORTD = PORTD & ~ (servo_code); }
Znamo da ukupni ciklus mora trajati 20 ms prije ponovnog uključivanja GPIO pina. Dakle, provjeravamo je li brojanje premašilo 20 ms uspoređujući vrijednost brojanja s 400 (isti izračun kao što je gore spomenuto) i ako da, moramo ponovno inicijalizirati brojanje na nulu.
Simulacija koda robotskog oružja PIC-a
Uvijek je bolje simulirati kod prije nego što ga odnesete na pravi hardver. Stoga sam koristio Proteus da simuliram svoj kôd i potvrdio da radi ispravno. Krug korišten za simulaciju prikazan je u nastavku. Osciloskopom smo provjerili generiraju li se PWM signali prema potrebi. Također možemo provjeriti okreću li se LCD i servo motori kako se očekivalo.

Kao što vidite, LCD prikazuje radni ciklus motora D 07, na temelju vrijednosti lonca koja je 3. motor. Slično ako se pomakne drugi lonac, radni ciklus tog lonca i njegov broj motora prikazat će se na LCD-u. PWM signal prikazan na osciloskopu prikazan je u nastavku.

Ukupno razdoblje ciklusa mjeri se na 22,2 ms pomoću opcije kursora na osciloskopu, što je vrlo blizu željenih 20 ms. Napokon smo sigurni da kôd djeluje, pa da bismo nastavili s krugom, možemo ga lemiti na perf ploču ili koristiti PCB. Neće raditi lako na pločici jer POT uvijek ima problema s lošim vezama.
Dizajn PCB-a pomoću EasyEDA-e
Za dizajn ove robotske ruke PIC odabrali smo mrežni EDA alat nazvan EasyEDA. Već ga dugo koristim i čini mi se vrlo prikladnim zbog velike dostupnosti otiska i jednostavne prirode. Nakon dizajniranja PCB-a, uzorke PCB-a možemo naručiti putem njihovih jeftinih usluga izrade PCB-a. Oni također nude uslugu nabave komponenata gdje imaju veliku zalihu elektroničkih komponenata, a korisnici mogu naručiti njihove potrebne komponente zajedno s narudžbom PCB-a.
Dok dizajnirate svoje sklopove i PCB-ove, također možete učiniti svoj dizajn kruga i PCB-a javnim, tako da ih drugi korisnici mogu kopirati ili uređivati i imati koristi od vašeg rada, također smo za ovaj sklop učinili javnim cijeli raspored krugova i PCB-a, provjerite donja poveznica:
easyeda.com/circuitdigest/pic-development-board-for-robotic-arm
Korištenjem ove veze možete izravno naručiti istu PCB koju koristimo u ovom projektu i koristiti je. Nakon završetka dizajna ploča se može gledati kao 3D model što će biti od velike pomoći u vizualizaciji izgleda ploče nakon izrade. 3D model ploče koji koristimo prikazan je u nastavku. Osim toga, također možete pregledati gornji i donji sloj ploče kako biste provjerili je li klizavi zaslon očekivan.

Izračunavanje i naručivanje uzoraka putem interneta
Nakon dovršetka dizajna ove PIC Robot PCB-a, PCB možete naručiti putem JLCPCB.com. Da biste PCB naručili od JLCPCB, potrebna vam je datoteka Gerber. Da biste preuzeli Gerber datoteke s PCB-a, samo kliknite gumb Generiraj fabričku datoteku na stranici EasyEDA uređivača, a zatim odatle preuzmite datoteku Gerber ili možete kliknuti na Naruči na JLCPCB kako je prikazano na donjoj slici. Ovo će vas preusmjeriti na JLCPCB.com, gdje možete odabrati broj PCB-a koje želite naručiti, koliko slojeva bakra trebate, debljinu PCB-a, težinu bakra, pa čak i boju PCB-a, poput snimke prikazane dolje:

Nakon što odaberete sve opcije, kliknite "Spremi u košaricu", a zatim ćete biti preusmjereni na stranicu na koju možete učitati svoju Gerber datoteku koju smo preuzeli s EasyEDA-e. Prenesite svoju Gerber datoteku i kliknite "Spremi u košaricu". I na kraju kliknite Sigurno plaćanje da biste dovršili narudžbu, a zatim ćete dobiti svoje PCB-ove nekoliko dana kasnije. Oni izrađuju PCB po vrlo niskoj stopi koja iznosi 2 USD. Njihovo vrijeme izrade također je vrlo manje, što je 48 sati s DHL-ovom isporukom od 3-5 dana, u osnovi ćete dobiti svoje PCB-ove u roku od tjedan dana od narudžbe.

Nakon narudžbe PCB-a možete provjeriti napredak u proizvodnji PCB-a s datumom i vremenom. Provjerite je tako da odete na stranicu računa i kliknete "Napredak proizvodnje".

Nakon nekoliko dana naručivanja PCB-a, dobio sam uzorke PCB-a u lijepom pakiranju kao što je prikazano na slikama ispod.


A nakon što sam nabavio ove dijelove, zalemio sam sve potrebne komponente preko PCB-a. Također sam izravno zalemio POT, umjesto da sam koristio spojne žice, jer su ženske i ženske žice koje sam u početku koristio dajući čudne analogne izlazne napone vjerojatno zbog labavih kontakata. Nakon što su sve komponente sastavljene, moja je PCB izgledala otprilike ovako.

Mogli ste primijetiti da je na ovoj ploči samo jedan 7805. To je zato što sam u početku mislio da se mogu izvući samo s regulatorom za napajanje i PIC-a i servo motora, a kasnije sam shvatio da mi trebaju dva. Stoga sam koristio vanjski krug za napajanje servo motora kroz zelene žice koje vidite ovdje.
Ipak, o tome se ne morate puno brinuti jer; Sad sam izvršio promjene na PCB-u. Možete koristiti modificirani PCB i zalemiti oba regulatora na samom brodu.
Rad robotske ruke PIC-a
Nakon svih zamornih radova vrijeme je za isplatu. Zalemite sve komponente na ploči i prenesite program na PIC kontroler. Kompletni kod je naveden u nastavku ili ga možete preuzeti ovdje. Programski konektor koji se nalazi na ploči trebao bi vam pomoći da izravno prenesete program pomoću programa Pickit 3 bez puno muke. Nakon što program prenesete, trebali biste vidjeti LCD zaslon koji prikazuje servo kojim se trenutno upravlja. Da biste saznali više o programiranju PIC mikrokontrolera, samo slijedite prethodni vodič.

Odatle možete jednostavno okrenuti lonac i provjeriti kako servo motori reagiraju na svaki potenciometar. Jednom kad shvatite format, možete kontrolirati robotsku ruku da izvrši bilo koju radnju koja vam je potrebna za izvođenje i zabavu. Kompletni rad projekta možete pronaći u videu dolje povezanom.
To je to, momci se nadaju da ste razumjeli projekt i naučili nešto novo iz njega. Ako imate pitanja, ostavite ih u odjeljku za komentare ili koristite forume za ostale tehničke rasprave.
