logo elektroda
logo elektroda
X
logo elektroda
Adblock/uBlockOrigin/AdGuard mogą powodować znikanie niektórych postów z powodu nowej reguły.

[Atmega8] Sterownik urządzeń (klawiatura + podczerwień)

lukasz_16 25 Lip 2008 21:09 3788 11
  • #1 5378258
    lukasz_16
    Poziom 11  
    Witam,
    Zaprojektowałem sterownik, który docelowo ma służyć do włączania różnych urządzeń elektrycznych.
    Włączanie ma odbywać się za pomocą klawiatury matrycowej 4x4 oraz/lub pilota (RC5).

    - Zasilanie układu to +5V z zasilacza stabilizowanego (dlatego w projekcie nie ma stabilizacji napięcia zasilającego).
    - Dioda podłączona do mikrokontrolera ma spełniać rolę "diody diagnostycznej" np. zamigać kilka razy po zmianie stanu któregoś z wyjść uC.
    - Odbiornik podczerwieni do TSOP1736.
    - Wyjścia ULN'a będę podłączone do przekaźników z cewką 5V

    Zwracam się z prośbą o zweryfikowanie mojego projektu (czy nie ma jakiś "wad konstrukcyjnych") oraz o pomysły na jego usprawnienie (głównie chodzi o kod programu).
    Proszę o wyrozumiałość, gdyż dopiero zaczynam swoją przygodę z mikrokontrolerami :)

    [Atmega8] Sterownik urządzeń (klawiatura + podczerwień)

    ' --- Schemat polaczen ---
    ' TSOP1736              ( input )  -> D.2 (INT0)
    ' Dioda diagnostyczna   ( output ) -> D.7
    ' Klawiatura 4x4        ( input )  -> B.0 - B.7
    ' ULN2803               ( output ) -> C.0 , C.1 , C.2 , C.3 , C.4 , C.5 , D.5 , D.6
    
    $regfile "m8def.dat"
    $crystal = 1000000
    
    Config Rc5 = Pind.2
    
    ' klawiatura matrycowa
    Config Kbd = Portb , Debounce = 500 , Delay = 100
    
    Config Portc.0 = Output
    Config Portc.1 = Output
    Config Portc.2 = Output
    Config Portc.3 = Output
    Config Portc.4 = Output
    Config Portc.5 = Output
    Config Portd.5 = Output
    Config Portd.6 = Output
    
    Out1 Alias Portc.0
    Out2 Alias Portc.1
    Out3 Alias Portc.2
    Out4 Alias Portc.3
    Out5 Alias Portc.4
    Out6 Alias Portc.5
    Out7 Alias Portd.5
    Out8 Alias Portd.6
    
    Config Portd.7 = Output
    
    Diagled Alias Portd.7
    
    Enable Interrupts
    
    ' Zmienne
    Dim Address As Byte
    Dim Command As Byte
    Dim Key As Byte
    
    Dim Dled As Bit
    Dim Dledcount As Integer
    Dim Temp As Integer
    
    ' Deklaracje procedur
    Declare Sub Allon
    Declare Sub Alloff
    Declare Sub Diag
    
    
    ' Glowny program
    
    Gosub Alloff
    Do
       Key = Getkbd()
          If Key <> 16 Then
             Gosub Diag
    
             Select Case Key
                Case 1 : Out1 = Not Out1
                Case 2 : Out2 = Not Out2
                Case 3 : Out3 = Not Out3
                Case 4 : Out4 = Not Out4
                Case 5 : Out5 = Not Out5
                Case 6 : Out6 = Not Out6
                Case 7 : Out7 = Not Out7
                Case 8 : Out8 = Not Out8
                Case 10 : Gosub Allon
                Case 12 : Gosub Alloff
             End Select
    
          End If
    
       Getrc5(address , Command)
          If Address = 1 Then
             Command = Command And &B01111111
             Gosub Diag
    
             Select Case Command
                Case 1 : Out1 = Not Out1
                Case 2 : Out2 = Not Out2
                Case 3 : Out3 = Not Out3
                Case 4 : Out4 = Not Out4
                Case 5 : Out5 = Not Out5
                Case 6 : Out6 = Not Out6
                Case 7 : Out7 = Not Out7
                Case 8 : Out8 = Not Out8
                Case 9 : Gosub Allon
                Case 10 : Gosub Alloff
             End Select
    
          End If
    Loop
    End
    'KONIEC GLOWNEGO PROGRAMU
    
    'dioda diagnostyczna
    ' zmiana stanu diody w co 25 wywolaniu procedury
    Sub Diag
       If Dledcount = 0 Then
          If Dled = 0 Then
             Dledcount = 1000
          End If
          Dled = Not Dled
       End If
    
       If Dled = 1 Then
          Temp = Dledcount Mod 25
          If Temp = 0 Then
             Diagled = Not Diagled
          End If
       End If
    
       Decr Dledcount
    End Sub
    
    'wszystkie wlaczone
    Sub Allon
       Reset Out1 : Reset Out2 : Reset Out3 : Reset Out4 : Reset Out5 : Reset Out6 : Reset Out7 : Reset Out8
    End Sub
    
    'wszystkie wylaczone
    Sub Alloff
       Set Out1 : Set Out2 : Set Out3 : Set Out4 : Set Out5 : Set Out6 : Set Out7 : Set Out8
    End Sub
  • #2 5378423
    mirekk36
    Poziom 42  
    hmm wydaje się, że koniecznie powinieneś dać także VCC do nóżki procka AVCC oraz GND do nóżki AGND. Poza tym wejście AVREF można dla spokoju przetwornika podłączyć kondensatorkiem 100nF do masy.

    kondensator 100uF, który mam nadzieję umieszczasz blisko nóżek procka możesz spokojnie zmniejszyć do wartości 47uF albo nawet 22uF - ale za to nie powinieneś nigdy zapominać, że zawsze ale to zawsze prawie do każdego aktywnego scalaka że tak powiem powinno się dawać jeszcze na nóżkach zasilania także kondensatorek 100nF (tego nigdy przy procku nie powinno zabraknąć)

    to tyle tak na gorąco odnośnie schematu, który jak na początkującego b.fajnie narysowałeś w eagle a nie tak jak niektórzy, połączenia puszczają na ukos :)

    Dodano po 3 [minuty]:

    odnośnie programu tak na początek bez wielkiego wgłębiania się to warto chyba abyś dał obsługę Getrc5 w przerwaniu a w pętli głównej tylko sprawdzał flagę i w zależności od niej odczytywał jaki kod klawisza nadleciał z pilota. Samo polecenie Getrc5 w pętli głównej będzie wprowadzało małe opóźnienie i twoja klawiaturka czasem może być "narowista", jakby klawisze od razu nie reagowały
  • #3 5378438
    Dr.Vee
    VIP Zasłużony dla elektroda
    Witam,

    Koniecznie 100nF pomiędzy VCC i GND procesora.
    Możesz dodać złącze ISP, do programowania procesora bez usuwania go z układu.

    Pozdrawiam,
    Dr.Vee
  • #5 5378460
    mirekk36
    Poziom 42  
    popełniłem swego czasu taką obsługę Getrc5 w przerwaniu z wykorzystaniem bitu Toggle, który przydaje się do sprawdzenia czy mamy wciąż wciśnięty klawisz - wtedy zmienna Repeat = 1 a gdy tylko raz to Repeat = 0. To się czasem przydaje i fajnie można wykorzystać, oto przykładzk - hmmm może troszkę rozbudowany bo z wstawkami asemblerowymi ale można je pominąć jak coś i zastąpić czystym bascomem, który jest w komentarzach wstawek asemblerowych :)

    '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
    '''''''''''''''''  konfiguracja przerwania i  zmiennych  ''''''''''''''
    '''''''''''''''''  do obsługi kodów z pilota IR - RC5    ''''''''''''''
    '''''''''''''''''''------------------------------------''''''''''''''''
    Config Rc5 = Pind.3 , Timer = 2
    Dim Address As Byte , Command As Byte                       ' zmienne przechowujące ostatnio odebrany adres i kod z pilota
    Dim Ir_flag As Byte                                         ' FLAGA - ustawiana w przerwaniu po odebraniu sygnału z pilota
    Dim Toggle_bit As Byte , Last_toggle_bit As Byte            ' zmienne pomocnicze dla ustalenia REPEAT klawisza
    Last_toggle_bit = 2                                         ' na początku trzeba ustawić wartość inną niż ZERO lub JEDEN
    Dim Repeat As Byte                                          ' zmienna przyjmuje wartość 1 gdy klawisz jest w trybie REPEAT (cały czas wciśnięty)
    Repeat = 0                                                  '
    Ir_flag = 0                                                 ' zerowanie zmiennych
    
    On Int1 Int1_rc5                                            ' obsługa odbioru kodów z pilota Getrc5
    Config Int1 = Low Level                                     ' wyzwalanie przerwania niskim poziomem
    Enable Int1                                                 ' aktywacja przerwania INT1
    
    Enable interrupts
    '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''


    tu akurat używałem do obsługi Getrc5 timera2 ale można dać bez tego parametru i będzie działał domyślnie na timerze0

    potem obsługa przerwania:
    ''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
    ''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
    ''''''''''''                                     '''''''''''''''''''''''''''
    ''''''''''''   Obsługa przerwania PILOTA IR RC5  '''''''''''''''''''''''''''
    ''''''''''''                                     '''''''''''''''''''''''''''
    ''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
    ''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
    Int1_rc5:
       Disable Int1
       Enable Interrupts
       If Ir_flag = 0 Then
          Getrc5(address , Command)
          Ir_flag = 1
       End If
    Return
    ''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''


    a potem gdzieś w pętli głównej:

       '''''''''''''''''''''''''''''''''''''''''''''''''''''''''
       '''''''''''''''''''''''''''''''''''''''''''''''''''''''''
       ' obsługa odebranego kodu z pilota IR
       '''''''''''''''''''''''''''''''''''''''''''''''''''''''''
       '''''''''''''''''''''''''''''''''''''''''''''''''''''''''
       If Ir_flag = 1 Then
          If Address <> 255 Then
    
             ' dzięki asemblerowi oszczędzamy tu prawie 100 bajtów pamięci
             ' i optymalizujemy program pod kątem szybkości
             ' - ustawienie zmiennej REPEAT
             ' - rozdzielenie komendy z pilota (Command) i bitu Toggle (Toggle_bit)
             $asm
                'Toggle_bit = Command.7
                lds   r16, {Command}
                ldi   r17, 1
                sbrs  r16, 7
                clr   r17
                sts   {Toggle_bit}, r17
                'Command = Command And &B01111111
                andi  r16, &b01111111
                sts   {Command}, R16
                'If Last_toggle_bit = Toggle_bit Then Repeat = 1 Else Repeat = 0 End If
                lds   r16, {Last_toggle_bit}
                clr   r18
                cp    r16, r17
                brne  not_set_tg_bit
                ldi   r18, 1
             Not_set_tg_bit:
                sts   {Repeat}, r18
                'Last_toggle_bit = Toggle_bit
                sts   {Last_toggle_bit}, r17
             $end Asm
    
             '---------------------------------------------------
             '---------------------------------------------------
             '       Tu --> własna obsługa  kodów z pilota
             '---------------------------------------------------
             Cls
             Lcd "adr: " ; Address ; " kod: " ; Command ;
             Lowerline
             Lcd "Toggle: " ; Toggle_bit ; "  R:" ; Repeat
             '---------------------------------------------------
             '---------------------------------------------------
          End If
    
    
          Ir_flag = 0                                           ' wyzerowanie flagi aby możliwy był kolejny odbiór danych z pilota
          Enable Int1                                           ' odblokowanie przerwania do obsługi odczytu pilota
       End If
       '''''''''''''''''''''''''''''''''''''''''''''''''''''''''
       ''''''''''''''''''''''''''''''''''''''''''''''''' koniec obsługi IR
       '''''''''''''''''''''''''''''''''''''''''''''''''''''''''


    Dodano po 1 [minuty]:

    taaak i kolega Balu ma rację - nie zauważyłem, koniecznie musisz podciągnąć linię sygnałową z czujnika IR do VCC za pomocą jakiegoś rezystorka

    Dodano po 4 [minuty]:

    aha - i jeszcze jedno ten kondensatorek 100uF przy odbiorniku IR też jest zbyt gigantyczny wg mnie, wystarczy nawet 4,7uF ale musisz go dać za rezystorkiem 220R, bezpośrednio przy nóżce VCC odbiornika bo tak to ten rezystorek troszkę nie ma sensu
  • #6 5379005
    dawid512
    Poziom 32  
    Cytat:
    aha - i jeszcze jedno ten kondensatorek 100uF przy odbiorniku IR też jest zbyt gigantyczny wg mnie, wystarczy nawet 4,7uF ale musisz go dać za rezystorkiem 220R, bezpośrednio przy nóżce VCC odbiornika bo tak to ten rezystorek troszkę nie ma sensu


    Ma sens, z kondensatorem 100uF działa pięknie i nie ma zakłóceń.
  • #7 5379158
    mirekk36
    Poziom 42  
    sorki kolego dawid512 ale chyba nie do końca rozumiesz pewnej różnicy pomiędzy takim podłączeniem rezystora i kondensatora jakie pokazał autor - a pomiędzy tym jak należy to zrobić aby zniwelować wpływ zakłóceń na linii zasilania - które zostało przedstawione w nocie aplikacyjnej. Proponuję ci przyjrzeć się temu rozwiązaniu, przemyśleć i wtedy zrozumiesz dlaczego może być mniejszy kondensator ale przy nóżce scalaka IR - TFMS, przed rezystorem. I dlaczego w schemacie autora sam rezystor nie ma sensu.


    [Atmega8] Sterownik urządzeń (klawiatura + podczerwień)
  • #8 5380337
    lukasz_16
    Poziom 11  
    mirekk36 napisał:
    sorki kolego dawid512 ale chyba nie do końca rozumiesz pewnej różnicy pomiędzy takim podłączeniem rezystora i kondensatora jakie pokazał autor - a pomiędzy tym jak należy to zrobić aby zniwelować wpływ zakłóceń na linii zasilania - które zostało przedstawione w nocie aplikacyjnej. Proponuję ci przyjrzeć się temu rozwiązaniu, przemyśleć i wtedy zrozumiesz dlaczego może być mniejszy kondensator ale przy nóżce scalaka IR - TFMS, przed rezystorem. I dlaczego w schemacie autora sam rezystor nie ma sensu.


    Koledze dawidowi512 chyba nie chodziło o umiejscowienie kondensatora, ale o jego pojemność. Niby w nocie katalogowej TSOP1736 zalecają kondensator 4.7µF, ale znalazłem w necie, opisy przypadków że ludziom wszystko zaczynało działać dopiero po zamontowaniu kondensatora o większej pojemności np. 100µF.
  • #9 5380343
    Balu
    Poziom 38  
    Koledze mirek chodziło o UMIEJSCOWIENIE kondensatora, nie o pojemność (przede wszystkim).
    Tamgdzie jest na schemacie NIC nie da nawet jak będzie miał 1F... (no może wtedy da:D)...
  • #10 5380442
    lukasz_16
    Poziom 11  
    Zamieszczam poprawiony schemat. Mam nadzieję, że już wszystko jest poprawnie.

    Za Waszą radą dodałem także złącze do programowania.

    [Atmega8] Sterownik urządzeń (klawiatura + podczerwień)
  • #11 5380568
    Dr.Vee
    VIP Zasłużony dla elektroda
    Witam,

    Zgodnie z dokumentacją atmela na pinie 3 złącza ISP w wersji 10-pinowej powinieneś mieć GND, a u Ciebie ten pin "wisi".

    Pozdrawiam,
    Dr.Vee
  • #12 5380578
    ZbeeGin
    Poziom 39  
    Dr.Vee napisał:
    Zgodnie z dokumentacją atmela na pinie 3 złącza ISP w wersji 10-pinowej powinieneś mieć GND, a u Ciebie ten pin "wisi".

    W różnych programatorach ten pin jest różnie wykorzysytywany. Dlatego zostawiłbym go w spokoju tak jak jest.
REKLAMA