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

ATmega16 - optymalna obsługa animacji diod led w C

mitny 18 Sty 2011 10:06 1941 15
REKLAMA
  • #1 9021682
    mitny
    Poziom 13  
    Witam,
    Mam do was pytanie jak najwydajniej, najsprawniej i najlepiej wykonać animację diod led. Diodami steruję multipleksowo za pomocą 25 pinów.
    Nie wiem którą drogę wybrać do zapisu animacji w kodzie - klatek animacji będzie od kilkuset do kilku tysięcy. Myślałem nad jakimś zapisem klatek do tablicy a potem np. co sekundę odczyt kolejnego elementu tablicy i potem pętla wyświetlająca tą klatkę. Jednak wydaje mi się, że taka duża liczba klatek nie zmieści się w pamięci RAM i powinienem jednak zapisać to w kodzie programu gdzie pamięci jest znacznie więcej.

    Proszę o sugestie w którą stronę powinienem pójść?
  • REKLAMA
  • #2 9021736
    LordBlick
    VIP Zasłużony dla elektroda
    Ostatnio kartę Kingston 4GB miniSDHC z adapterem na SD standard kupiłem w znanej sieci marketów typu owadopodobnego za niecałe 30 zł... Ogromną zaletą jest proste programowanie przez wrzucenie spreparowanego pliku na kartę.
  • #3 9021992
    hotdog
    Poziom 26  
    jedyne rozwiązanie to karta SD, lub jakiś zewnętrzny flash (np at25df021).

    Przelicz sobie z ilości pixeli ile wyjdzie Tobie klatek w pamięci programu.

    Co do samego programu to jedyny poprawny sposób to realizacja multipleksowania w przerwaniu timera. Wtedy w programie głównym tylko bufor sobie uzupełniasz.
  • #4 9022355
    mitny
    Poziom 13  
    To jeszcze z innej strony. Mam też ATmegę 32. Gdyby założyć, że będę miał np. max 1000 klatek każda klatka to 150 pixeli - razem to daje około 18KB.
    Klatki przygotowuję za pomocą innego programu który w efekcie daje mi ciąg 150 zer i jedynek.
    Jak wrzucić to do kodu by nie zajmowało jakoś specjalnie więcej?
  • REKLAMA
  • REKLAMA
  • #6 9022555
    mitny
    Poziom 13  
    Czy dobrze rozumiem, że dzięki temu hintowi mogę sobie zdefiniować odpowiednią tablicę która będzie w pamięci programu?
    W takim przypadku mógłbym zrobić kilku wymiarową tablicę i w programie ją przeglądać?
    Czy jest w C jakiś sposób na utworzenie takiej tablicy ale binarnej (by nie marnować pamięci)?
  • #7 9022667
    hotdog
    Poziom 26  
    To nie ma znaczenia. Każda tablica skompiluje się do binarnej. Wszystko trafi do pliku hex. Czy napiszesz {255,0xFF,0b11111111} to wszystko będzie ta sama wartości.

    Nigdy nie umieszczałem w programie tyle danych, ale mniej więcej powinieneś zrobić to tak:

    
    uint8_t PROGMEM tablica[1000][15] = {
        {255,128,130,255,128,130,255,128,130,255,128,130,255,128,130},
        {255,128,130,255,128,130,255,128,130,255,128,130,255,128,130},
        ...........
        {255,128,130,255,128,130,255,128,130,255,128,130,255,128,130}
    };
    


    co z tym dalej zrobić to sobie doczytaj tutaj:
    http://www.nongnu.org/avr-libc/user-manual/group__avr__pgmspace.html
  • #8 9022799
    mitny
    Poziom 13  
    To już rozumiem ale miałem na myśli coś innego. Chodzi o to czy da się taką tablicę zdefiniować tak, że każda wartość w tablicy zajmie 1 bit pamięci (bo będę tam przechowywać wartości 0,1)? W twoim przypadku każda wartość zajmie aż 8 bitów.
  • #9 9022844
    hotdog
    Poziom 26  
    nie ma takiej możliwości, trzeba ręcznie wyciągać bity z bajtów (maski bitowe, logiczny and i or)
  • REKLAMA
  • #10 9022907
    LordBlick
    VIP Zasłużony dla elektroda
    Wpisuj po prostu 0b... do tej tablicy, a reszta należy do procedury interpretującej...
    Co więcej, możesz zadeklarować tablicę 16 bit i ten niewykorzystany bit użyć np do kontroli parzystości, czy czegokolwiek...
    uint16_t PROGMEM tablica[1000] = {
       0b0011101101101101,
       0b0011011011011101,
        ...........
       0b0111011110110101,
    }; 
    Można każdą klatkę deklarować oddzielnie dla czytelności o dogodnej szerokości bitów z dopełnieniem do 8.
  • #11 9026127
    mitny
    Poziom 13  
    Raczej zastosuję taką tablicę:
    uint8_t PROGMEM tablica[1000][19] = {
     {0b0011101101101101,
       0b0011011011011101,
        ...........
       0b0111011110110101},
        ..........
     {0b0011101101101101,
       0b0011011011011101,
        ...........
       0b0111011110110101},
    }; 


    Pierwszy wymiar to będą klatki a drugi to już po prostu dopełnienie do 150bitów. Aby nie marnować pamięci będę musiał przy odczycie nie interesować się 2 wymiarem tylko przeskakiwać po bitach ale to już problem funkcji odczytującej.
  • #12 9028589
    mitny
    Poziom 13  
    hotdog napisał:

    Co do samego programu to jedyny poprawny sposób to realizacja multipleksowania w przerwaniu timera. Wtedy w programie głównym tylko bufor sobie uzupełniasz.

    Mógłbyś to trochę jaśniej opisać? Jak to powinno być zrealizowane aby światło diody było stabilne i równe?
    Głównie chodzi mi o to, że w moim rozwiązaniu dioda zapala się i gaśnie co jakiś czas przez co zdecydowanie słabiej świeci.
  • #13 9028894
    hotdog
    Poziom 26  
    W przerwaniu od timera robisz takie rzeczy (w tej kolejności):
    - wyłączasz aktualny wiersz;
    - ustawiasz aktualną wartość kolumn;
    - czasami trzeba dodać krótkie opóźnienie ze 2 -3 nop'y kwestia testów;
    - włączasz następny wiersz.

    Będzie to płynnie działać już przy prędkości 50Hz * ilość wierszy.

    Jak korzystasz z wewnętrznej pamięci flash, to możesz dane ładować i zapisywać w przerwaniu, bo nie ma tutaj żadnego opóźniania jak by to było w przypadku pamięci na SPI. Nie wiem jak masz wszystko zorganizowane (ilośc wierszy, ilość kolumn), więc to na tyle.

    Pozdrawiam
  • #14 9028938
    mitny
    Poziom 13  
    Zmieniłem poprzedni post ale trochę późno :)
    Mam 15 wierszy i 10 kolumn - razem 150 diod (tzn tyle będzie docelowo).
    Robię właśnie tak jak opisujesz ale dioda przez to zdecydowanie słabiej świeci.
  • #15 9029024
    hotdog
    Poziom 26  
    To rozumiem że tylko jednak kolumna, czy jeden wiersz naraz jest aktywna?

    Nie przeskoczysz tego że diody będą słabiej świecić. To normalne, każda będzie dawał 10 (lub 15) razy mniej światła. Jedyne co można zrobić to zmniejszyć rezystory, ponieważ w impulsie diody mogą brać więcej prądu niż mogą nominalnie.

    Poczytaj poniższy wątek, tyczy się wyświetlaczy LED, ale to w sumie bez różnicy.
    https://www.elektroda.pl/rtvforum/topic1691942.html
  • #16 9029610
    mitny
    Poziom 13  
    Tak w obecnym rozwiązaniu jednocześnie aktywny jest tylko 1 wiersz.
    Dzięki za pomoc - kod animacji udało się zmieścić i wygodnie obsłużyć w pamięci procesora. Pozostał jednak problem jasności diod. Utrata jasności jest spora nawet jak zastosuję mniejsze rezystory.
    Być może będę musiał zmienić sterowanie multipleksowane na jakieś inne w którym diody będą świeciły na stałe.
REKLAMA