Skocz do zawartości
Turboasm

[Bascom] Obrotomierz + rgb

Pomocna odpowiedź

Mam kod obrotomierza:

$crystal = 4000000

$regfile = "m8def.dat" 

Dim Wynik As Long
Config Lcd = 16 * 2
Config Lcdpin = Pin , Db4 = Portd.2 , Db5 = Portd.3 , Db6 = Portd.4 , Db7 = Portd.6 , E = Portd.1 , Rs = Portd.0
Config Timer1 = Counter , Edge = Rising                   
Cls : Lcd "Obrotomierz" : Wait 1                                                                                                       
Do                                                         
  Timer1 = 0                                              
  Start Timer1                                            
  Wait 1                                                 
  Stop Timer1                                              

  Wynik = Timer1 * 60                                      

  Cls                                                                                                    
  Lcd "P: " ; Wynik ; " obr/min"                           
  Cursor Off                                              
Loop                                                       
End

Pytania:

Chciałbym zmodyfikować program aby w zależności od obrotów zmianiało się wypełnienie impulsów PWM. Czy rolę licznika w programie może pełnić timer2 a Timer1 wykorzystać jako 2 kanałowy PWm ? Jak zrobić aby zmieniał się płynnie kolor diody RGB z niebieskiego na czerwony w zakresie obrotów np. 1000 - 7000 ?

Udostępnij ten post


Link to post
Share on other sites

Może zapytam inaczej. Czy poniższy kod jest poprawny ? Chodzi o to żeby było zapętlone select case żeby na bieżąco zmieniało wypełnienie pwm w zależności od obrotów.

$crystal = 4000000

$regfile = "m8def.dat" 

Dim Wynik As Long
Config Timer2 = Counter , Edge = Rising
Config Pinb.1 = Output
Config Timer1 = Pwm , Prescale = 1 , Compare A Pwm = Clear Down
Cls : Lcd "Obrotomierz" : Wait 1

Do
  Start Timer1
  Timer2 = 0
  Start Timer2
  Wait 1
  Stop Timer2

  Wynik = Timer2 * 60

  Cls
  Lcd "P: " ; Wynik ; " obr/min" 
  Cursor Off

  Select Case Wynik

  Case 0 To 1000: 
  Do
  Pwm1a = 250
  Pwm1b = 0
  Loop

  Case 1001 To 2000: 
  Do
  Pwm1a = 220
  Pwm1b = 35
  Loop

  Case 2001 To 3000: 
  Do
  Pwm1a = 190
  Pwm1b = 70
  Loop

  Case 3001 To 4000: 
  Do
  Pwm1a = 160
  Pwm1b = 105
  Loop

  Case 4001 To 5000: 
  Do
  Pwm1a = 90
  Pwm1b = 180
  Loop

  Case 5001 To 6000: 
  Do
  Pwm1a = 30
  Pwm1b = 210
  Loop

  Case 6001 To 7000: 
  Do
  Pwm1a = 0
  Pwm1b = 250
  Loop

  End Select


Loop
End

Udostępnij ten post


Link to post
Share on other sites

Masz kilka błędów, pod case'ami nie są potrzebne do...loop, wszystko co jest pomiędzy poszczególnymi case'ami się wykona więc wystarczy wpisać:

   Case 5001 To 6000: 
  Pwm1a = 30
  Pwm1b = 210

  Case 6001 To 7000: 
  Pwm1a = 0
  Pwm1b = 250 

Timer2 w medze8 jest ośmiobitowy, co da ci możliwość zliczania do maksymalnie 255 obrotów na sekundę, jeśli się przepełni będziesz miał nieprawidłowy wynik. Mógłbyś to obejść poprzez dodanie dodatkowej zmiennej, która byłaby zwiększana przy przepełnieniu timera2. Wtedy wynik końcowy byłby równy ilości przepełnień razy 256 plus aktualna wartość w timerze2.

Skoro pod case'ami używasz 2 kanałów PWMa to musisz je zdefiniować:

Config Timer1 = Pwm , Prescale = 1 , Compare A Pwm = Clear Down ,Compare B Pwm = Clear Down

definicja pinu jako wyjście przy PWMie nie jest wymagana bez tej linijki też będzie działać:

Config Pinb.1 = Output 
  • Pomogłeś! 1

Udostępnij ten post


Link to post
Share on other sites

Czyli tą zmianną bym musiał zerować po każdym przejściu programu. Jakoś inaczej jeszcze da radę to zrobić ?

Udostępnij ten post


Link to post
Share on other sites
Czyli tą zmianną bym musiał zerować po każdym przejściu programu. Jakoś inaczej jeszcze da radę to zrobić ?

Ale po co kombinować skoro masz podane na tacy gotowe rozwiązanie stosowane np przy dość (tylko dość! :]) dokładnych pomiarach częstotliwości (ilości impulsów na ułamki sekund).

Sprawdź tutaj, jest to całkiem dobrze opisane.

Udostępnij ten post


Link to post
Share on other sites

Witam.

W Twoim kodzie jak widzę wypełnienie zmienia się skokowo.

Jak chcesz, aby zmieniało się płynnie nie potrzebujesz case a odrobiny matematyki.

Maksymalne obroty w twoim wypadku wynoszą 7000 obr/mia a maksymalne wypełnienie PWMa wynosi 256.

Dzieląc 7000 / 256 otrzymamy wynik 27+reszta.

Po wymnożeniu 255*27 oraz 255*28 otrzymamy wyniki 6885 oraz 7140

Załóżmy, że maksymalna prędkość silnika jest mniejsza od 6885

W takim przypadku wpisujemy wypełnienie PWMa:

PWM1a = Wynik/27

PWM1b = 255-(Wynik/27)

Otrzymamy pełynne przejście jednego koloru w drugi.

Jeszcze jedna sprawa natury pomiarowej.

Czy czas próbkowania musisz mieć równy 1 sek?

jak nie, to możesz go skrócić.

Zmieni to jedynie wartość drugiego czynnika w równaniu.

Dla przykładu zmiana czasu do 0,5 sek spowoduje zmianę:

Wynik = Timer1 * 120

Sprawa następna. Do obliczeń PWMa nie musisz przemnażać wyniku. Wystarczy, ze zrobisz to przed wpisaniem wartości do LCD

 Wynik = Timer1
Lcd " :P: " ; Wynik*60 ; " obr/min" 

Takie rozwiązanie pozwoli Ci na zredukowanie wielkości zmiennej Wynik z long nawet do byte.

Spowoduje to m.in przyspieszenie wykonywania kodu ponieważ obliczenia na zmiennych większych niż byte są w procesorach 8bitowych nieefektywne.

  • Lubię! 1

Udostępnij ten post


Link to post
Share on other sites

dzięki za pomoc 🙂 ale pozostaje mi tylko problem który licznik zaprząc do zadania. Czy timer1 do zliczania impulsów czy timer2 ?

Udostępnij ten post


Link to post
Share on other sites

Tak jak pisałem wyżej, timer2 jest 8-mio bitowy więc musiałbyś zliczać przepełnienia tego licznika, timer1 jest 16-sto bitowy więc teoretycznie powinien wystarczyć do zliczania impulsów. Na twoim miejscu użyłbym timera1. Jeśli będzie ci wygodniej projektując płytkę użyć końcówki od timera2 to wtedy poprostu zmienisz kod i będziesz zliczał przepełnienia w zmiennej Byte co da ci dokładnie to samo co użycie 16-sto bitowego licznika.

Udostępnij ten post


Link to post
Share on other sites

Ja bym proponował zostawić zliczanie na Timer1.

Pozostaje problem jak sterować 2 diodami przez jedno wyście Timer2.

W kodzie, który zaproponował Zuk druga dioda zawsze dostaje 255-jasność_diody_1, więc możesz na wyjściu Timer2 zrobić następująco:

1) sterowanie diodą blue bezpośrednio

2) sterowanie diodą red przez negator (np. 74hc04)

Udostępnij ten post


Link to post
Share on other sites

Co do timerów:

7000 obr/min to jest 117 obr/sek.

Skoro zdecydowałeś się na pomiar prędkości przez 1sek

maksymalnie powinieneś otrzymać dokładnie taką wartość (przy 7000 obr/min).

Zauważ, że mając w tarczy 2 otwory otrzymasz maksymalny wynik

dwa razy większy czyli 233 imp/sek.

Nawet w tym przypadku nie zostaje przekroczony zakres zmiennej typu byte,
a uzyskałeś rozdzielczość dwa razy większą.

Taką samą (max 233) rozdzielczość uzyskasz mając tarczę z 4 otworami i czas próbkowania 0,5. a zyskasz większą dynamikę pomiaru.

Z powyższego wynika, że 8 bitowy timer w zupełności wystarcza.

Udostępnij ten post


Link to post
Share on other sites

Jak zrobic żeby program dzialał szybciej ? Zliczam impulsy włącznikiem hallotronowym. Program działa z opóźnieniem.

$regfile = "m8def.dat" 
$crystal = 8000000

Config Lcdpin = Pin , Db4 = Portb.6 , Db5 = Portd.3 , Db6 = Portd.2 , Db7 = Portd.1 , E = Portb.7 , Rs = Portd.7
Config Lcd = 16 * 2

Dim Wynik As Long


Config Timer0 = Counter , Edge = Rising
Config Timer1 = Pwm , Prescale = 1 , Compare A Pwm = Clear Down , Compare B Pwm = Clear Down


Start Timer1

Cls

Do

  Timer0 = 0
  Start Timer0
  Waitms 500
  Stop Timer0

  Wynik = Timer0 * 120
  Cls
  Lcd Wynik ; " obr/min" 
  Cursor Off

  Pwm1a = Wynik / 27
  Pwm1b = 255 - Pwm1a
Loop


End

po prostu program nie może zdążyć za silnikiem. Da sie to w jakiś inny sposób zrealizować ?

Udostępnij ten post


Link to post
Share on other sites

Przepraszam że odkopuje temat ale chciałem wykorzystać ten program i mam z nim problem.

Chodzi o pierwszą wersję kodu.

Skoro podajemy sygnały do zliczania na PD3 to czemu w konfiguracji wyświetlacza jest podane: Db5 = Portd.3

Udostępnij ten post


Link to post
Share on other sites

Dołącz do dyskusji, napisz odpowiedź!

Jeśli masz już konto to zaloguj się teraz, aby opublikować wiadomość jako Ty. Możesz też napisać teraz i zarejestrować się później.
Uwaga: wgrywanie zdjęć i załączników dostępne jest po zalogowaniu!

Gość
Dołącz do dyskusji! Kliknij i zacznij pisać...

×   Wklejony jako tekst z formatowaniem.   Przywróć formatowanie

  Dozwolonych jest tylko 75 emoji.

×   Twój link będzie automatycznie osadzony.   Wyświetlać jako link

×   Twoja poprzednia zawartość została przywrócona.   Wyczyść edytor

×   Nie możesz wkleić zdjęć bezpośrednio. Prześlij lub wstaw obrazy z adresu URL.


×
×
  • Utwórz nowe...