Programowy PWM


Witam
Od wczoraj mam problem z programowym PWM, moze mi ktoś podpowiedzieć co robię nie tak?

Config Timer2 = Timer , Prescale = 8
Enable Timer2 : On Timer2 Software_pwm
Const Timer2_load = 130

Do
 
If Sw1 = 0 And Zmienna = 0 Then Rozdol = 1
If Sw1 = 0 And Zmienna = 1 Then Zgasgora = 1
'If Sw2 = 0 And Zmienna = 1 Then Zgasdol = 1
'If Sw2 = 0 And Zmienna = 0 Then Rozgora = 1
 
 
      If Rozdol = 1 Then
    Zmienna = 1
  If Poziom(1) < 100 Then Incr Poziom(1)
  If Poziom(1) > 20 And Poziom(2) < 100 Then Incr Poziom(2)
  If Poziom(2) > 20 And Poziom(3) < 100 Then Incr Poziom(3)
  If Poziom(3) > 20 And Poziom(4) < 100 Then Incr Poziom(4)
  If Poziom(4) > 20 And Poziom(5) < 100 Then Incr Poziom(5)
  If Poziom(5) > 20 And Poziom(6) < 100 Then Incr Poziom(6)
  If Poziom(6) > 20 And Poziom(7) < 100 Then Incr Poziom(7)
  If Poziom(7) > 20 And Poziom(8) < 100 Then Incr Poziom(8)
  If Poziom(8) > 20 And Poziom(9) < 100 Then Incr Poziom(9)
  If Poziom(9) > 20 And Poziom(10) < 100 Then Incr Poziom(10)
  If Poziom(10) > 20 And Poziom(11) < 100 Then Incr Poziom(11)
  If Poziom(11) > 20 And Poziom(12) < 100 Then Incr Poziom(12)
  If Poziom(12) > 20 And Poziom(13) < 100 Then Incr Poziom(13)
  If Poziom(13) > 20 And Poziom(14) < 100 Then Incr Poziom(14)
  If Poziom(14) > 20 And Poziom(15) < 100 Then Incr Poziom(15)
'  If Poziom(15) > 20 And Poziom(16) < 100 Then Incr Poziom(16)
'  If Poziom(16) > 20 And Poziom(17) < 100 Then Incr Poziom(17)
  If Poziom(15) = 100 Then Rozdol = 0
 
         End If
 
 Loop
 
'******* KONIEC ********
Software_pwm:
Timer2 = Timer2_load
 
 Incr Licznik
 If Licznik = 100 Then Licznik = 0
 
 If Licznik < Poziom(1) Then Set D1 Else Reset D1
 If Licznik < Poziom(2) Then Set D2 Else Reset D2
 If Licznik < Poziom(3) Then Set D3 Else Reset D3
 If Licznik < Poziom(4) Then Set D4 Else Reset D4
 If Licznik < Poziom(5) Then Set D5 Else Reset D5
 If Licznik < Poziom(6) Then Set D6 Else Reset D6
 If Licznik < Poziom(7) Then Set D7 Else Reset D7
 If Licznik < Poziom(8) Then Set D8 Else Reset D8
 If Licznik < Poziom(9) Then Set D9 Else Reset D9
 If Licznik < Poziom(10) Then Set D10 Else Reset D10
 If Licznik < Poziom(11) Then Set D11 Else Reset D11
 If Licznik < Poziom(12) Then Set D12 Else Reset D12
 If Licznik < Poziom(13) Then Set D13 Else Reset D13
 If Licznik < Poziom(14) Then Set D14 Else Reset D14
 If Licznik < Poziom(15) Then Set D15 Else Reset D15
 Return

To akurat działa

 Poziom(15) = 25
 Poziom(1) = 30




Portret użytkownika mirley

Re:

Jak ustwisz na sztywno przed do loop wartości zmiennych poziom to pojawia się odpowiednie wypełnienie?

Nie podoba mi się że nie ma żadnej flagi taktującej te przyciski i mam obawy że się to w ułamku sekundy przekęeci.... Dodaj chociaz w ramach testu waita w do loop np waitms 50 itp

-

UWAGA! Możliwy jest zakup zaprogramowanych uC i zestawów elementów itp. do niektórych projektów. O dostępność proszę pytać via email. Konkretne oferty pojawiają się w cenniku.

Portret użytkownika gosc

Nie wlaczylem przerwania. A

Nie wlaczylem przerwania. A po wpisaniu na sztywno mruga poszczególne dioda

Portret użytkownika mirley

PWM

Nie zwróciłem na to uwagi, myślałem że to tylko fragmenty kodu

-

UWAGA! Możliwy jest zakup zaprogramowanych uC i zestawów elementów itp. do niektórych projektów. O dostępność proszę pytać via email. Konkretne oferty pojawiają się w cenniku.

Portret użytkownika demsy1

Mam jeszcze problem ze

Mój fragment kodu

'************* Konfiguracja uC *****************
'***********************************************
$regfile = "m16def.dat"
$crystal = 8000000
 
 
Ddra = &B00000000 : Porta = &BX1111XXX
Ddrb = &B11111111 : Portb = &B00000000
Ddrc = &B00111111 : Portc = &B11000000
Ddrd = &B11111111 : Portd = &B00000000
 
Dim Licznik As Byte
Dim W As Word
Dim Poziom(15) As Byte
Dim Zmienna As Byte
Dim Rozdol As Byte
Dim Rozgora As Byte
Dim Zgasdol As Byte
Dim Zgasgora As Byte
Dim F25m As Bit
Dim F100m As Bit
Dim Sw1_licz As Byte
Dim Animacja As Bit
Dim Dziel As Byte
 
'Config Adc = Single , Prescaler = Auto , Reference = Avcc
'Start Adc
 
 
Config Timer0 = Timer , Prescale = 1
Enable Timer0 : On Timer0 Prztimer0
Enable Interrupts
 
 
D1 Alias Portb.2 : D2 Alias Portb.3 : D3 Alias Portb.4 : D4 Alias Portb.5
D5 Alias Portb.6 : D6 Alias Portb.7 : D7 Alias Portd.0 : D8 Alias Portd.1
D9 Alias Portd.2 : D10 Alias Portd.3 : D11 Alias Portd.4 : D12 Alias Portd.5
D13 Alias Portd.6 : D14 Alias Portd.7 : D15 Alias Portc.0 : ' D16 Alias Portc.1
'D17 Alias Portc.2 : D18 Alias Portc.3 : D19 Alias Portc.4 : D20 Alias Portc.5
'D21 Alias Portc.6 : D22 Alias Portc.7
 
 
 
Sw1 Alias Pina.6
Sw2 Alias Pina.5
Sw3 Alias Pina.4
 
 
 
 
Do
  If F25m = 1 Then
    F25m = 0
 
    'obsługa przycisku 1
    If Sw1 = 0 Then
      Incr Sw1_licz
      If Sw1_licz = 100 Then
        Sw1_licz = 0
        Animacja = 0
      End If
    Else
      Sw1_licz = 95
    End If
 
 
End If
 
 
 
  If F100m = 1 Then
    F100m = 0
     Animacja = 1
  If Poziom(1) < 100 Then Incr Poziom(1)
  If Poziom(1) > 20 And Poziom(2) < 100 Then Incr Poziom(2)
  If Poziom(2) > 20 And Poziom(3) < 100 Then Incr Poziom(3)
  If Poziom(3) > 20 And Poziom(4) < 100 Then Incr Poziom(4)
  If Poziom(4) > 20 And Poziom(5) < 100 Then Incr Poziom(5)
  If Poziom(5) > 20 And Poziom(6) < 100 Then Incr Poziom(6)
  If Poziom(6) > 20 And Poziom(7) < 100 Then Incr Poziom(7)
  If Poziom(7) > 20 And Poziom(8) < 100 Then Incr Poziom(8)
  If Poziom(8) > 20 And Poziom(9) < 100 Then Incr Poziom(9)
  If Poziom(9) > 20 And Poziom(10) < 100 Then Incr Poziom(10)
  If Poziom(10) > 20 And Poziom(11) < 100 Then Incr Poziom(11)
  If Poziom(11) > 20 And Poziom(12) < 100 Then Incr Poziom(12)
  If Poziom(12) > 20 And Poziom(13) < 100 Then Incr Poziom(13)
  If Poziom(13) > 20 And Poziom(14) < 100 Then Incr Poziom(14)
  If Poziom(14) > 20 And Poziom(15) < 100 Then Incr Poziom(15)
  'If Poziom(15) > 20 And Poziom(16) < 100 Then Incr Poziom(16)
 ' If Poziom(16) > 20 And Poziom(17) < 100 Then Incr Poziom(17)
  If Poziom(15) = 100 Then
  Animacja = 0
 
    'End If
    End If
  End If
Loop
 
Prztimer0:
 
If Licznik = 100 Then
  Licznik = 0
  set f25m
  incr dziel
  if dziel = 4 then
    dziel = 0
    set f100m
  end if
End If
  Incr Licznik
 If Licznik < Poziom(1) Then Set D1 Else Reset D1
 If Licznik < Poziom(2) Then Set D2 Else Reset D2
 If Licznik < Poziom(3) Then Set D3 Else Reset D3
 If Licznik < Poziom(4) Then Set D4 Else Reset D4
 If Licznik < Poziom(5) Then Set D5 Else Reset D5
 If Licznik < Poziom(6) Then Set D6 Else Reset D6
 If Licznik < Poziom(7) Then Set D7 Else Reset D7
 If Licznik < Poziom(8) Then Set D8 Else Reset D8
 If Licznik < Poziom(9) Then Set D9 Else Reset D9
 If Licznik < Poziom(10) Then Set D10 Else Reset D10
 If Licznik < Poziom(11) Then Set D11 Else Reset D11
 If Licznik < Poziom(12) Then Set D12 Else Reset D12
 If Licznik < Poziom(13) Then Set D13 Else Reset D13
 If Licznik < Poziom(14) Then Set D14 Else Reset D14
 If Licznik < Poziom(15) Then Set D15 Else Reset D15
 
 Return

Portret użytkownika EDC

Programowy PWM

Tym sposobem sterowania program się chyba "rozwlecze" i trudne byłyby inne animacje. Zerknij tylko na ten mój film z linka. Link do filmu

Postaram się dodać animację rozpalania po kolei ale wszystkich diod. Musze się tylko "wdrożyć"w programowanie bo ostatnio miałem inne zajęcia ;)

Proszę. Chodzi mi między innymi o dodanie zmiennej Led_nr ponieważ numer indeksu w tablicy może być zmienną :D

Możesz więc tylko raz coś napisać a jeśli ta zmienna się zmieni, to kod będzie sie tyczył już innego elementu tablicy.
Więc zwiększam sobie wartość PWM i tutaj zamiast zapisu Wartość_pwm(1) pisze Wartosc_pwm(wartos_przechowywana_przez_inna_zmienna) Jeśli ta druga zmienna posiada wartości mieszczące sie w tablicy ...czyli w moim wypadku między 1 a 8 to program będzie działał na zmiennych tablicy od numerów Wartosc_pwm(1 do 8)
Przykład poniżej

$regfile = "attiny2313.dat"
$crystal = 8000000
$hwstack = 40
$swstack = 16
$framesize = 24
 
 
Config Portb = &B11111111 : Portb = &B11111111              'PORTB cały wyjscia, PORTB cały w stan wysoki
Config Portd = &B00000000 : Portd = &B11111111              'nieużywany PORTD cały wejście właczone podciąganie
 
'*** Timer0 Config for 8kHz  Interrupt CTC Mode ***
Config Timer0 = Timer , Prescale = 8 , Compare A = Disconnect , Compare B = Disconnect , Clear Timer = 1
Enable Compare0a : On Compare0a Int0_isr : Compare0a = 124
 
Enable Interrupts
 
'******************  Zmienne *******************
'***********************************************
Dim Licznik As Byte                                         'liczy od 1 do 100 w przerwaniu
Dim Pwm_led(8) As Byte                                      'osiem bajtów, dla każdego kanału wartosc PWM 1%-100%
Dim N As Byte                                               'pomocnicza
Dim Speed As Byte                                           'spowolnienie akcji
Dim Scenario As Byte                                        'wybor dwoch trybów
Dim Led_nr As Byte                                          'numer bajtu w tablicy PWM'ów
 
Led_nr = 1                                                  'zmienna ma 0 wiec nadaje jej wartosc 1
 
'**************  Petla glowna ******************
'***********************************************
Do
 
If Speed = 0 Then                                           'jesli nadszedl czas na zmiane PWM
 
 
 
Select Case Scenario                                        'sprawdz co robimy
 
Case 0                                                      'Scenariusz rozpalamy
 
   If Pwm_led(led_nr) < 100 Then                            'jesli wartosc pwm AKTUALNIE OBRABIANEJ DIODY...
   'zmienna led_nr pamieta ktora diode akurat rozjasniamy lub sciemniamy
       Incr Pwm_led(led_nr)
       Speed = 127 - Pwm_led(led_nr)
       Speed = Speed * 2
    Else                                                    'jesli doszlismy do 100 to bierzemy kolejna diode
       If Led_nr < 8 Then
         Incr Led_nr
        Else                                                'jesli doszlismy do konca to zabieram sie za sciemnianie
         Scenario = 1
         Led_nr = 1                                         'zaczynamy sciemniac od poczatku
        End If
    End If
 
Case 1
 
   If Pwm_led(led_nr) > 0 Then
       Decr Pwm_led(led_nr)
       Speed = 127 - Pwm_led(led_nr)
       Speed = Speed * 2
    Else
       If Led_nr < 8 Then
         Incr Led_nr
        Else
         Scenario = 0
         Led_nr = 1
        End If
    End If
 
 
End Select
 
 
End If
Loop
End
 
 
'************ Przerwanie timer 0 ***************
'***********************************************
Int0_isr:
 Incr Licznik                                               'zwieksz Licznik o jeden
 If Licznik = 100 Then Licznik = 0                          'jesli Licznik = 100 to wyzeruj
 
 'pętla dla wartości 0 do 7 czyli tak jak numery bitów w porcie
  For N = 0 To 7
 'jesli Licznik ma mniej niż PWM dla danego pinu to ustaw 0 na pin , w przeciwnym wypadku ustaw 1
 ' (do N trzeba dodac 1 bo tablice zaczynaja sie od 1, nie ma wartosci 0)
   If Licznik < Pwm_led(n + 1) Then Reset Portb.n Else Set Portb.n
  Next
 
  'odliczanie do zmiann wartosci
   If Speed > 0 Then Decr Speed                             'jesli Speed wieksza od zera to odejmuj jeden
Return

I efekt jego działania:

Zastosowałem tam też takie rozwiązanie które wymaga wyjaśnienia. Diody led się zapalają juz przy niskiej wartosci PWM wiec wymyśliłem sobie że im niższa wartość PWM tym dłużej wartosć tego PWM ma sie nie zmieniać. Czyli jeśli PWM ma wartosc 1 to odejmuję 1 od 127 i mam 126. 126 mnoże razy dwa i zawsze mieszczę sie w bajcie. 252 cykle muszą upłynać zanim znów zmienię wartość PWM. Za to potem wszystko przyspiesza proporcjonalnie ;)
Pewnie się zamotałem gdzieś ale może ktoś coś z tego podpatrzy :D

Przepisanie tego sposobu na dwa porty to nieskomplikowane. W swoim kodzie gasiłem tez od razu poprzednią diodę.
Sobie wyobraź że gasząć ósmą musisz rozpalać pierwszą i na odwót. Wszystko da się zrobić kilkoma matematycznymi obliczeniami.
Kiedy dojdziesz do tego że masz zapalone wszystkie diody to możesz dodać Scenario "Czekamy" :D Ja na potrzeby działania w kółko zrobiłem tylko dwa Scenario :D Bo potem można ich dopisać więcej.

-

BARTek
Moja strona

Portret użytkownika demsy1

Bardzo sprytnie napisany ten

Bardzo sprytnie napisany ten kod. Chciałbym to dostosować pod m16 tyle że wyskakuje mi błąd przy kompilacji w tym miejscu

Config Timer0 = Timer , Prescale = 8 , Compare A = Disconnect , Compare B = Disconnect , Clear Timer = 1
Enable Compare0a : On Compare0a Int0_isr : Compare0a = 124

Portret użytkownika EDC

Odp. Programowe PWM

Pisałem tak na szybko ale to przełknął.
Mega16 to jest taki dziadek jak Mega8 i one mają Compare dla tych małych ośmiobitowych Timerów tylko na Timer2.

Config Timer2 = Timer , Prescale = 8 , Compare = Disconnect , Clear Timer = 1
Enable Compare2 : On Compare2 Int0_isr : Compare2 = 124

-

BARTek
Moja strona

Portret użytkownika demsy1

FaktycznieDopiszę jeszcze

Faktycznie
Problem mam jeszcze jak chcę dodać do timera jeszcze jeden port

  For N = 0 To 7
  If Licznik < Pwm_led(n + 1) Then Set Portd.n Else Reset Portd.n
  Next

i później wysterować nim żeby w drugą strone diody się zapalały

Portret użytkownika EDC

Odp. Programowe PWM

Czy to nie będzie czasem tak, że jeśli dodałeś osiem kolejnych Pwm_led poprzez zapis Dim Pwm_led(16) As Byte to teraz powinieneś napisać 9? Tak myślę na szybko ;)

For N = 0 To 7
  If Licznik < Pwm_led(n + 9) Then Set Portd.n Else Reset Portd.n
Next

Planuję zrobić niedługo taką wersję na 16, ale muszę wydrapać te diody z tego projektu bo tylko tych żółtych mam kolejne osiem czy dziesięć :D
Może też na końcu będzie trzeba wziąć kalkulator i zobaczyć jak się to wyrabia czasowo :D

-

BARTek
Moja strona

Portret użytkownika demsy1

na próbę wrzuciłem toIf

Quote:
Czy to nie będzie czasem tak, że jeśli dodałeś osiem kolejnych Pwm_led poprzez zapis Dim Pwm_led(16) As Byte to teraz powinieneś napisać 9? Tak myślę na szybko ;)
For N = 0 To 7
If Licznik < Pwm_led(n + 9) Then Set Portd.n Else Reset Portd.n
Next

To nic nie da bo i tak zapali się tylko 8

For N = 0 To 7

na próbę wrzuciłem to

If Licznik < Pwm_led(1) Then Set D1 Else Reset D1
 If Licznik < Pwm_led(2) Then Set D2 Else Reset D2
 If Licznik < Pwm_led(3) Then Set D3 Else Reset D3
 If Licznik < Pwm_led(4) Then Set D4 Else Reset D4
 If Licznik < Pwm_led(5) Then Set D5 Else Reset D5
 If Licznik < Pwm_led(6) Then Set D6 Else Reset D6
 If Licznik < Pwm_led(7) Then Set D7 Else Reset D7
 If Licznik < Pwm_led(8) Then Set D8 Else Reset D8
 If Licznik < Pwm_led(9) Then Set D9 Else Reset D9
 If Licznik < Pwm_led(10) Then Set D10 Else Reset D10
 If Licznik < Pwm_led(11) Then Set D11 Else Reset D11
 If Licznik < Pwm_led(12) Then Set D12 Else Reset D12
 If Licznik < Pwm_led(13) Then Set D13 Else Reset D13
 If Licznik < Pwm_led(14) Then Set D14 Else Reset D14
 If Licznik < Pwm_led(15) Then Set D15 Else Reset D15

na tym działają wszystkie 15

Portret użytkownika EDC

Odp. Programowe PWM

Myślałem o drugiej pętli z inną literą portu, zaraz pod pierwszą, żeby się nie rozpisywać, ale tak pewnie nawet jest szybciej. Sprawdzę to w wolnej chwili na symulatorze.

-

BARTek
Moja strona

Portret użytkownika demsy1

Chciałbym się jeszcze

Chciałbym się jeszcze dowiedzieć jak zrobić żeby diody zapalały się od 15 do 1 bo kombinuje, ale mi nie wychodzi

Portret użytkownika EDC

Odp. Programowe PWM

Przed rozpoczęciem procedury Led_nr musi już mieć 15 (Led_nr = 15), potem zwiększasz PWM jak w moim oryginale, ale po dojściu do 100 zmniejszasz o jeden Led_nr

Coś na ten wzór

If Pwm_led(led_nr) < 100 Then                            'jesli wartosc pwm AKTUALNIE OBRABIANEJ DIODY...
   'zmienna led_nr pamieta ktora diode akurat rozjasniamy lub sciemniamy
       Incr Pwm_led(led_nr)
       Speed = 127 - Pwm_led(led_nr)
       Speed = Speed * 2
    Else                                                    'jesli doszlismy do 100 to bierzemy kolejna diode
       If Led_nr > 1 Then
         Decr Led_nr
        Else                                                'jesli doszlismy do konca to zabieram sie za sciemnianie
'tutaj koniec bo doszlo i cos musisz myslec czyli na przyklad zmiana scenario na Czekamy
         Scenario = 1
         Led_nr = 15                                         'zaczynamy sciemniac od poczatku
        End If
    End If

Od której diody chcesz zacząć wpisujesz zanim zaczniesz któraś procedurę a one potem albo obniżają PWM albo zwiększają i po osiągnieciu pułapu biorą sie za nastepną diodę. Co ciekawe ta wartośc 100 może być zmienną Więc jeśli gdzies w programie wpiszesz ze chcesz rozjasnic tylko do 50% to wszystko sie trochę szybciej potoczy ale cały łańcuch będzie swiecił z polową mocy. Tam można dopiero kombinowac :P
Albo sciemnic nie do zero a do 1-2 i bedzie podswietlone lekko

-

BARTek
Moja strona

Portret użytkownika demsy1

ja kombinowałem takf

ja kombinowałem tak

f Pwm_led(led_nr) < 100 Then                            
   'zmienna led_nr pamieta ktora diode akurat rozjasniamy lub sciemniamy
       Incr Pwm_led(led_nr)
       Speed = 127 - Pwm_led(led_nr)
       Speed = Speed * 2
    Else                                                    
       If Led_nr > 15 Then
         incr Led_nr
        Else                                                
         Scenario = 1
         Led_nr = 15                                         
        End If
    End If

Portret użytkownika EDC

Odp. Programowe PWM

Tu masz przerobiony kawałek który podmień w swoim programie

Led_nr = 15                                                  'zmienna ma 0 wiec nadaje jej wartosc 1
 
'**************  Petla glowna ******************
'***********************************************
Do
 
If Speed = 0 Then                                           'jesli nadszedl czas na zmiane PWM
 
 
 
Select Case Scenario                                        'sprawdz co robimy
 
Case 0                                                      'Scenariusz rozpalamy
 
   If Pwm_led(led_nr) < 100 Then                            'jesli wartosc pwm AKTUALNIE OBRABIANEJ DIODY...
   'zmienna led_nr pamieta ktora diode akurat rozjasniamy lub sciemniamy
       Incr Pwm_led(led_nr)
       Speed = 127 - Pwm_led(led_nr)
       Speed = Speed * 2
    Else                                                    'jesli doszlismy do 100 to bierzemy kolejna diode
       If Led_nr > 1 Then
         Decr Led_nr
        Else                                                'jesli doszlismy do konca to zabieram sie za sciemnianie
         Scenario = 1
         Led_nr = 15                                         'zaczynamy sciemniac od poczatku
        End If
    End If
 
Case 1
 
   If Pwm_led(led_nr) > 0 Then
       Decr Pwm_led(led_nr)
       Speed = 127 - Pwm_led(led_nr)
       Speed = Speed * 2
    Else
       If Led_nr > 1 Then
         Decr Led_nr
        Else
         Scenario = 0
         Led_nr = 15
        End If
    End If
 
 
End Select
 
 
End If
Loop

-

BARTek
Moja strona

Portret użytkownika demsy1

ok. poprawiłem i działa. a

ok. poprawiłem i działa. Jeszcze tylko procedura obsługi przycisków

Portret użytkownika demsy1

ADC

Witam wszystkich
Panowie ja chciałbym regulować potencjometrem zmienną E
mam napisane coś takiego

Config Adc = Single , Prescaler = Auto , Reference = Avcc
Start Adc

E = Getadc(1)

............
Incr Pwm_led(led_nr)
       Speed = 127 - Pwm_led(led_nr)
       Speed = E * 30

Ta predkość jest strasznie nierówna

Portret użytkownika EDC

Odp. ADC

Zmienna Speed jest typu Byte i może pomieścić maksymalnie wartość 255.
Zmienna E powinna być zadeklarowana jako Word ponieważ wartość odczytana z ADC ma maksymalnie 1023.
Żeby zmieścić 1023 i mieć w miarę proporcjonalna reakcje na potencjometr to odczyt z ADC trzeba wiec podzielić przez 4.
Kod mógłby w skrócie wyglądać tak:

Dim Speed As Byte
Dim E As Word
 
E = Getadc(1)
E = E / 4
Speed = E ' tu dopiero nastepuje zamiana typu Word na Byte no i wszystko sie zmiesci

Wszystko to już bez tego Speed = 127 - Pwm_led(led_nr). Tylko te trzy ostatnie linijki mojego kodu zamiast tego i w dodatku miejsce umieszczenia tego również należałoby przemyśleć.
ADC samo z siebie jest nieliniowe, ale widzisz sam, że to, co chciałeś zrobić, nie mieściło się w Bajcie.

-

BARTek
Moja strona

Portret użytkownika matrix

Odp. ADC

Ja jeszcze dorzucił bym do podziału odejmowanie nadmiaru powyżej 1000 czyli 23 a że jest dzielenie przez 4 to napisał bym tak:

E = Getadc(1)
If E > 23 then
   E = E - 23
end If
E = E/4

Zabieg taki spowoduje (według mnie oczywiście) że regulacja będzie taka bardziej równa ograniczając wynik od góry do 1000, a wynik mimo to w całym zakresie obrotu potencjometru będzie poprawny.
Chodzi o to że jeżeli otrzymasz adc=1023 czyli max wartości to łatwiej 1000/4 niż 1023/4. Ja zawsze tak robiłem i wychodziło mi to na dobre.

A żeby było jeszcze ciekawiej to ja uzywając programowego PWM'a dzieliłem wynik nie przez 4 a przez 10. Wówczas ograniczasz się do regulacji w wartościach od 0 do 100. Możesz mi wierzyć że regulacja w tym zakresie jest (bynajmniej dla mnie) wystarczająca.

Portret użytkownika EDC

Odp. ADC

No moja uwaga miała na celu uwidocznienie problemu.
Samo dzielenie też bowiem powinno się zrobić za pośrednictwem przesunięcia bitowego.
Shift E, Right, 2
To załatwia dzielenie jednym ruchem a tamtym sposobem mikrokontroler dzieli przez 4 wiecznie.
Nie chciałem wszystkiego wykładać na raz żeby nie zaciemniać.

Right, 1 - dzieli przez dwa
Right, 2 - dzieli przez cztery
....
Right, 8 - dzieli przez 256

Są to kolejne potęgi liczby 2. Przesuwa o te bity i gotowe. Nie musząc kombinować. Jest to dużo szybsze działanie.

-

BARTek
Moja strona

Portret użytkownika demsy1

ADC

Witam ponownie
Dzięki BARTEK właśnie o to mi chodziło
Napisałem tak

........
Do
E = Getadc(1)
'dalsza część kodu
.......
' i póżniej tak
 Incr Pwm_led(led_nr)
       E = E / 4
       Speed = E

Portret użytkownika gosc

PWM 15 diod

Witam
Kolego Bartku możesz mi podpowiedzieć jak można rozjaśnić wszystkie diody od razy bo kolejno wiem jak

Portret użytkownika EDC

Odp. PWM 15 diod

To chyba proste.. :D

Dim Pwm As Byte, Licznik As Byte
 
Do
 
 Incr Pwm
  waitms 10
 
Loop
 
Przerwanie_timera
 Incr Licznik
  If Licznik = 100 Then Licznik = 0                          'jesli Licznik = 100 to wyzeruj
 
 If Licznik < Pwm Then
   PORTB = &B11111111  ' specjalnie tak zapisałem żeby można było wybrać piny
   PORTD = &B11111110
 Else
   PORTB = 0
   PORTD = 0
 End If
Return

Nie rozwodziłem się nad tym że nieużywany do Pwm pin może mieć inny stan. Do każdego zagadnienia podchodzi się jednostkowo. To jest tylko przykład.

Miłego dnia

-

BARTek
Moja strona

Portret użytkownika gosc

Do kolegi BARTka

Witam
Mam nadzieje że kolega Mirek nie będzie miał mi za złe jak zapytam kolegę Bartka o jego projekt, a chodzi mi o termometr bezprzewodowy, jakiś czas temu widziałem jeszcze na stronie, a teraz nie mogę znaleźć, co się z nim stało?

Portret użytkownika EDC

Odp. Termometr bezprzewodowy

Jest pod przyciskiem "Moduły RF"
Przeniosłem tam wszystkie projekty z tymi tanimi modułami :D
Mam taki kod nadajnika który korzysta z uśpienia mikrokontrolera celem oszczędności baterii gdyby pracował za oknem, ale jeszcze nie ma go na stronie.
Mam też opracowany pilot i odbiornik 5 kanałowy :D On/Off
...ale, fakt faktem, mogłeś zapytać mailem, albo na forum projektów bo to offtop a nie chce się tu wstydzić :D

-

BARTek
Moja strona

Portret użytkownika demsy1

timer

Witam wszystkich ponownie
Mam pytanie do kolegi bartka, czy konfiguracja timera dla atmegi 8 jest taka sama co dla atmegi 16? Bo mam problem żeby uruchomić to na tmega 8

Config Timer2 = Timer , Prescale = 8 , Compare = Disconnect , Clear Timer = 1
Enable Compare2 : On Compare2 Int0_isr : Compare2 = 124

Portret użytkownika EDC

Odp. Timer

W czym problem? Zgłasza jakiś błąd czy po prostu nie działa?
Jeśli zgłasza błąd nieznanego konfigu to spotkałem się z tym u kogoś kto używał starej spolszczonej wersji Bascom która jeszcze nie miała Compare i CTC mode dla Mega8.

Należy wtedy użyć nowszego Bascoma ;)

Niektóre funkcje Bascom korzystaja z Timerów i wtedy tez nie możesz ich użyć. Na przykład RC5 może zająć Timer0 (albo inny)
Zegar w postaci Config Clock = Soft na pewno zajmuje Timer2 ..itd

-

BARTek
Moja strona

Portret użytkownika demsy1

Timer

Witam
Jednak timer był w porządku, po prostu namieszałem w pętli.

Widziałem jeszcze post że ktoś chciał rozjaśniać wszystkie diody od razu, ja mam napisane tak że jednym przyciskiem rozjaśnia się od Pwm_led(1) do Pwm_led(17),a drugim przyciskiem od Pwm_led(17) do Pwm_led(1), a chciałbym dopisać trzeci przycisk i rozjaśniać wszystkie. Jak dopisać procedurę żeby wszystkie się rozjaśniały?

'************    Przerwanie timer 0    ***************
'*****************************************************
Int0_isr:
 Incr Licznik
 If Licznik = 100 Then Licznik = 0
 
 If Licznik < Pwm_led(1) Then Set D1 Else Reset D1
 If Licznik < Pwm_led(2) Then Set D2 Else Reset D2
 If Licznik < Pwm_led(3) Then Set D3 Else Reset D3
 If Licznik < Pwm_led(4) Then Set D4 Else Reset D4
 If Licznik < Pwm_led(5) Then Set D5 Else Reset D5
 If Licznik < Pwm_led(6) Then Set D6 Else Reset D6
 If Licznik < Pwm_led(7) Then Set D7 Else Reset D7
 If Licznik < Pwm_led(8) Then Set D8 Else Reset D8
 If Licznik < Pwm_led(9) Then Set D9 Else Reset D9
 If Licznik < Pwm_led(10) Then Set D10 Else Reset D10
 If Licznik < Pwm_led(11) Then Set D11 Else Reset D11
 If Licznik < Pwm_led(12) Then Set D12 Else Reset D12
 If Licznik < Pwm_led(13) Then Set D13 Else Reset D13
 If Licznik < Pwm_led(14) Then Set D14 Else Reset D14
 If Licznik < Pwm_led(15) Then Set D15 Else Reset D15
 If Licznik < Pwm_led(16) Then Set D16 Else Reset D16
 If Licznik < Pwm_led(17) Then Set D17 Else Reset D17
 
 
 
    If Speed > 0 Then Decr Speed                             
 
   Return

Już doszedłem!!!
Banalnie proste, a nie wiedziałem

Portret użytkownika demsy1

Witam ponownie Kolego Bartku

Witam ponownie
Kolego Bartku mam pytanie jak mogę dopisać kawałek kody tak żeby sterować potencjometrem jasność zapalania kolejno diód?
Czyli ustawiam potencjometrem wypełnienie 20% i kolejno będą sie zapalały do 20%

Led_nr = 15                                                  'zmienna ma 0 wiec nadaje jej wartosc 1
 
'**************  Petla glowna ******************
'***********************************************
Do
 
If Speed = 0 Then                                           'jesli nadszedl czas na zmiane PWM
 
 
 
Select Case Scenario                                        'sprawdz co robimy
 
Case 0                                                      'Scenariusz rozpalamy
 
   If Pwm_led(led_nr) < 100 Then                            'jesli wartosc pwm AKTUALNIE OBRABIANEJ DIODY...
   'zmienna led_nr pamieta ktora diode akurat rozjasniamy lub sciemniamy
       Incr Pwm_led(led_nr)
       Speed = 127 - Pwm_led(led_nr)
       Speed = Speed * 2
    Else                                                    'jesli doszlismy do 100 to bierzemy kolejna diode
       If Led_nr > 1 Then
         Decr Led_nr
        Else                                                'jesli doszlismy do konca to zabieram sie za sciemnianie
         Scenario = 1
         Led_nr = 15                                         'zaczynamy sciemniac od poczatku
        End If
    End If
 
Case 1
 
   If Pwm_led(led_nr) > 0 Then
       Decr Pwm_led(led_nr)
       Speed = 127 - Pwm_led(led_nr)
       Speed = Speed * 2
    Else
       If Led_nr > 1 Then
         Decr Led_nr
        Else
         Scenario = 0
         Led_nr = 15
        End If
    End If
 
 
End Select
 
 
End If
Loop

wiem że muszę zadeklarować zmienną, napisać który ADC, ale co dalej...?
nie oczekuje rozwiązania tylko podpowiedzi

Portret użytkownika EDC

Odp. Programowy PWM

Wystarczy chyba tylko w tym miejscu zamiast 100 wstawić zmienną

If Pwm_led(led_nr) < 100 Then

Dim Max_pwm As Byte
' ...
If Pwm_led(led_nr) < Max_pwm Then

-

BARTek
Moja strona

Portret użytkownika demsy1

Dzięki BARTek

Właśnie o to mi chodziło

Portret użytkownika gosc

do demsy1

Czy mógłbyś udostępnić tutaj Twój kod programu,żeby można pobawić się z PWM i potencjometrami? Bo to co opisujesz wygląda ciekawie.

Portret użytkownika gosc

do demsy1

Czy mógłbyś udostępnić tutaj Twój kod programu,żeby można pobawić się z PWM i potencjometrami? Bo to co opisujesz wygląda ciekawie.

Portret użytkownika gosc

Jak sobie potrzebna pomoc to

Jak sobie potrzebna pomoc to pisać/pomagać, jak się już ją otrzymało to po co innym pomagać udostępniać-można przemilczeć, nie słyszeć..

Portret użytkownika gosc

takie tam

Jak sobie potrzebna pomoc to pisać/pomagać, jak się już ją otrzymało to po co innym pomagać udostępniać-można przemilczeć, nie słyszeć..