Fórum témák

» Több friss téma
Cikkek » Sebességmérő segédmotoros kerékpárra
Sebességmérő segédmotoros kerékpárra
Szerző: MaSTeRFoXX, idő: Aug 13, 2009, Olvasva: 46563, Oldal olvasási idő: kb. 2 perc
Lapozás: OK   2 / 6

A működtető programról

A programot C-nyelven írtam WinAVR-ben. A működéséről annyit, hogy a főciklusban jeleníti meg a számokat a kijelzőn, és frissíti a képet másodpercenként körülbelül 50-szer. A körülfordulási idő mérése, és a sebesség számolása megszakításokkal történik. Az egyik érdekesség, az a print függvényen belül maga a kiíratás. Mivel a nyáktervet minél egyszerűbbre akartam csinálni (kerülni az átkötéseket), emiatt össze-vissza kellett kavarnom a kijelző kiosztását, aminek az eredménye az a sok tologatás és maszkolás.

Az AVR adottságaiból származik hogy 16bites felbontása van annak a számlálónak, amit idő mérésére használok, így ennél az órajelnél (3.2768MHz) a megmérhető minimális sebesség kb 4.8 km/h, de ez egyáltalán nem probléma, hiszen a gyalog is kb. 5km/h val halad az ember. A kijelezhető maximális sebesség 99.9 km/h, fölötte is működhet, ekkor 10-el kellene osztani, és kikapcsolni a tizedespontot. Még ilyenkor, 90km/h fölött is kb 0.5km/h a felbontás finomsága.

Aki ezt megépíti, valószínűleg érdekelni fogja a konst nevezetű konstans, amit a program elején definiálunk. Ennek az értéke: konst=10*3.6 [m/sec] * kerület [m], a 10-szeres szorzó azért kell, hogy ne kelljen szórakozni a tizedes törtekkel, egyszerűbb ha fel van szorozva, és a kijelzőn tesszük csak ki a tizedes pontot.

Jelenleg a kód Simson S51-re van beállítva, mérőszalaggal mérve, 16"-os első keréknél kb. 172 cm. Aki módosítja, mérje le mérőszalaggal a kerületet, ne a sugárból számoljon mert sokkal pontatlanabb, persze ilyenkor újra kell fordítani a kódot.
Erről itt cikkeztem régebben: >LINK<

A programozásnál, a fusebiteknél kapcsoljuk ki a JTAG interfészt (vegyük ki a pipát a Jtag Interface Enabled-ről), és állítsuk át külső kvarcra az órajelforrást (Ext. Crystal/resonator, High Freq, Startup time 64ms, CKSEL=1111) Ha valamit elrontottunk volna, és nem reagál továbbá az AVR, akkor a kvarcot kiforrasztva és egy 1MHz-es órajelforrást az XTAL1 lábra kötve, újra lehet próbálkozni.

A forráskód

  1. //simson sebességmérő
  2. //Holcsik Tamás -MaSTeRFoXX
  3. //holcsik@freemail.hu
  4. //2009-07-15
  5.  
  6. #include <avr/io.h>
  7. #include <util/delay.h>
  8. #include <avr/pgmspace.h>
  9. #include <avr/interrupt.h>
  10.  
  11. #define konst 62.01 //3.6*kerület*10 (1.7225m)
  12.  
  13. volatile uint16_t sebesseg;
  14. volatile uint8_t dp;
  15.  
  16. const uint8_t digit1_pattern[] PROGMEM=
  17. {
  18.     0xE7, 0x81, 0x6B, 0xCB, 0x8D, 0xCE, 0xEE, 0x83, 0xEF, 0xCF,    
  19. };
  20.  
  21. const uint8_t digit2_pattern[] PROGMEM=
  22. {
  23.     0x77, 0x41, 0x6E, 0x6B, 0x59, 0x3B, 0x3F, 0x61, 0x7F, 0x7B,    
  24. };
  25.  
  26. const uint8_t digit3_pattern[] PROGMEM=
  27. {
  28.     0x6F, 0x03, 0x5D, 0x57, 0x33, 0x76, 0x7E, 0x43, 0x7F, 0x77,    
  29. };
  30.  
  31.  
  32. void print(void)
  33. //kiírja a sebesseg változóból a kijelzőre a számokat
  34. {
  35.     uint8_t d1=0; //az első számjegy
  36.     uint8_t d2=0; //a második számjeg
  37.     uint8_t d3=0; //a harmadik szmjegy
  38.     uint16_t temp=sebesseg;
  39.     if (temp>999) temp=999; //ha a sebesség nagyobb mint 99.9
  40.     //számjegyek szétbontása
  41.     while(temp>=100)
  42.     {    temp-=100;
  43.         d1++;
  44.     }
  45.     while(temp>=10)
  46.     {
  47.         temp-=10;
  48.         d2++;
  49.     }
  50.     d3=temp;
  51.    
  52.     //kiíratás
  53.     d1=pgm_read_word(&digit1_pattern[d1]); //kiolvasni a bitmintákat
  54.     d2=pgm_read_word(&digit2_pattern[d2]);
  55.     d3=pgm_read_word(&digit3_pattern[d3]);
  56.     PORTD=0b01111000&(d3<<3);
  57.     if(dp) PORTD|=(1<<PD7);
  58.     PORTB=((d2>>3)&0b00001111)|((d3<<1)&0b11100000);
  59.     PORTC=0b00000111&d2;
  60.     PORTA=d1;
  61.  
  62. }
  63.  
  64. void refresh()
  65. //A portok állapotát bitszinten meginvertálja, mert a kijelzőt így szabad csak hajtani
  66. {
  67.     PORTD=~PORTD;
  68.     PORTB=~PORTB;
  69.     PORTC=~PORTC;
  70.     PORTA=~PORTA;
  71. }
  72.  
  73. ISR(TIMER1_OVF_vect)
  74. //ez a megszakítás akkor jelentkezik, amikor nullára csökken a sebesség
  75. // és a 16bites számláló túlcsordul, ilyenkor 0-t ír ki sebességnek
  76. {
  77.     cli();
  78.     sebesseg=0;
  79.     TCNT1=0;
  80.     sei();
  81. }
  82.  
  83. //megszakítás, lefutó élnél a bemeneten
  84. ISR(INT0_vect)
  85. {
  86.     cli(); //megszakítások kikapcsolása
  87.     sebesseg=(double)(konst*51200/TCNT1); //51200 = 3276800MHz/64-es osztó
  88.     TCNT1=0; //indítsa újra a számlálót
  89.     sei(); //megszakítások be
  90. }
  91.  
  92. int main(void)
  93. {
  94.     sebesseg=0; //kezdetben legyen nulla
  95.     DDRA=0xFF;
  96.     DDRB=0xEF;
  97.     DDRC=0x0F;
  98.     DDRD=0xF8;
  99.    
  100.     //megszakítások, timerek bekonfigurálása
  101.     MCUCR|=(1<<ISC01); //INT0 lefutó él érzékelés
  102.     GICR|=(1<<INT0); //INT0 megszakítás bekapcsolása
  103.     TIMSK|=(1<<TOIE1); //timer1 megszakítás be
  104.     TCCR1B|=(1<<CS11) |(1<<CS10); //bekapcs, 64-es osztás
  105.    
  106.     dp=1;  //legyen tizedes pont mert 10-el felszorozva számolunk, így sokkal egyszerűbb
  107.     sei(); //megszakítások be
  108.     print(); //írja ki a számokat
  109.  
  110.     while(1)
  111.     {
  112.         _delay_ms(20);
  113.         refresh(); //frissítse a kijelzőt
  114.         _delay_ms(20);
  115.         refresh();
  116.         print(); //rajzolja újra ki a sebességet
  117.     }
  118.  
  119. }


A cikk még nem ért véget, lapozz!
Következő: »»   2 / 6
Értékeléshez bejelentkezés szükséges!
Bejelentkezés

Belépés

Hirdetés
XDT.hu
Az oldalon sütiket használunk a helyes működéshez. Bővebb információt az adatvédelmi szabályzatban olvashatsz. Megértettem