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

flaga przerwania wewnetrznego i wyswietlanie co 0,5s

mariansq 04 Maj 2011 10:10 2588 25
  • #1 9468138
    mariansq
    Poziom 15  
    Witam

    Utknąłem z moim kodem i plątam sie w koło ciągle, dlatego proszę o pomoc.

    W podprogramie "przyciski" przerwania od timer0 mam zrealizowany odczyt przycisków i zrobiłem sobie "flagi czasowe"
    przyciski: 'przerwanie co 26ms
    .
    kod sprawdzania przycisków
    .
    incr licz
    if licz=19 then ' flaga co ok 0,5 s
       flaga_500ms=0 ' w warunkach początkowych flaga_500ms =1 czyli u mnie wyłączona
    licz = 0
    end if
    Return
    


    Główny mój problem polega na tym, że chciałbym odczytać np. w procedurze lub podprogramie wartość napięcia z ADC i wynik wyświetlać co te 500 ms wykorzystując flagę z przerwania.
    Ale nie wiem czemu warunek „IF” wykonywany jest za każdym przejściem programu, a nie tylko wtedy kiedy flaga_500ms=0 kod:


    
    sub odczytaj
    
    for i = 0 to 99 ' robie srednia ze 100 pomiarów
         wart_adc=getadc(0)
         bufor=bufor * wart_adc
    next i
        bufor=bufor / 100
        bufor=bufor * 0,0049
        bufor=bufor * 4
    
        if flaga_500ms=0 then ' nie wiem czemu ale ten warunek wykonuje sie za 
           wynik=bufor              każdym przejsciem programu a nie kiedy flaga = 0
           flaga_500ms=1
        end if
    end sub


    potem oczywiście wyświetlam zmienną wynik w odpowiednim miejscu:
     wys=fusing(wynik , "#.&&")


    i tu tez pojawia sie mniejszy juz problem od poprzedniego ale jest.
    Jeśli wyświetla sie liczba przeformatowana przez „fusing”, to obserwuje migotanie różnych znaków na ostatniej cyfrze co jakiś czas - znaki ascii np :,>,? i inne tez tego nie rozumiem.

    Teraz opisze jeszcze kilka założeń pomocnych w analizie:
    - żadnych waitms'ów w kodzie programu głównego (program zasuwa ile fabryka), tylko przy warunkach wyboru podmenu wykonywane jednorazowo przy naciśnięciu przycisku celem uniknięcia przeskoku do dalszych podmenu.
    - unikanie instrukcji CLS w programie głównym, jest tylko przed pętla programu głównego Do…Loop - obrazy wymazuje natpisujac kolejne z pełna obsada znaków i pustych pól
    - wyświetlanie wyników pomiaru z ADC co 0,5 sekundy za pomocą flagi z przerwania , a nie z opóźnień instrukcją waitms

    To tak pokrótce – problemy:
    1.
    czyli program smiga z pełną szybkością odczytując ADC i uśredniając wyniki a co ok. 0,5 sek flaga_500ms od przerwania ma wykonać warunek if , w którym następuje przypisanie wartości zmierzonej do zmiennej wyświetlanej na LCD. No i to jak już wspomniałem nie dokona mi działa bo zachowuje się tak jakby na „pełnej prędkości „ wyświetlał mi wyniki, a nie co 0,5 s

    2. Drugim problemem jest wyświetlanie , prześwitywanie różnych znaków na ostatniej cyfrze zmiennej konwertowanej przez Fusing; problem ten już zauważyłem jeszcze zanim powstał problem nr 1. Może to efekt nadpisywania ekranów bez użycia CLS , ale gdy przełączam Menu to nie ma żadnych takich efektów lub wyświetlam wartości zmiennej bez użycia Fusing. To pojawia się jak używam Fusing(zmienna , "#.&&").

    Przyznam się, że to pierwszy w ten sposób przez ze mnie robiony program, ale jeśli wszystko zadziała to spełni moje oczekiwania.

    Proszę o pomoc i dziękuję.
  • #2 9468309
    Wojtek75
    Poziom 24  
    Ogólnie na podstawie tego, co opisałeś nie da się jednoznacznie stwierdzić gdzie leży problem.
    Jaki to uC i na jakiej prędkości działa? Jak wygląda konfiguracja T0. Pokaż ustawienia stosu?
  • #3 9468396
    mariansq
    Poziom 15  
    Procesor
    uPC Mega16 z zegarem ustawionym na 8MHz
    timer: 125ns*1024*200= ok 26ms
    
    Config Timer0=Timer , Prescale = 1024
    On Timer0 Przyciski
    .
    .
    potem
    .
    Enable interrupts
    Enable Timer0
    Load Timer0, 200
    
    Do
    
    Program główny
    Loop
    
    End
    
    Przyciski:
    Load Timer0, 200
    
    kod przycisków
    
    incr licz 
    if licz=19 then ' flaga co ok 0,5 s 
       flaga_500ms=0 ' w warunkach początkowych flaga_500ms =1 czyli u mnie wyłączona 
    licz = 0 
    end if 
    
    Return
    


    Przerwanie działa bo obsługuje nim przyciski, ale zakałapućkałem sie z zastosowaniem flagi do wyswietlenia co 0,5s wartości z pomiaru z ADC.

    Myk wydaje sie byc prosty - program odczytuje ADC, przelicza a za pomoca flagi z przerwania wyswietlamy wynik co 0,5s tylko jakoś sobienie radze:)

    Moze moja koncepcja jest błedna, może inaczej trzeba to zrobić?

    Myslałem tez ze może to pod przerwaniem zrobić - ale wolałbym przerwanie wykorzystac tylko do dosłownego przerwania - czyli ustawienia flag lub wartości i wychodzimy,a reszta w programie.
  • #4 9468494
    Wojtek75
    Poziom 24  
    mariansq napisał:
    Procesor
    uPC Mega16 z zegarem ustawionym na 8MHz
    timer: 125ns*1024*200= ok 26ms

    Trochę dziwnie to liczysz:
    1024/8000000=0,000128us
    200*0,000128=0,0256s=~25,6ms

    Mniejsza z tym, mniej więcej się zgadza.

    Co ze stosem? Masz to gdzieś na początku programu?
    Kod: text
    Zaloguj się, aby zobaczyć kod

    Jeżeli nie masz to dopisz. Możesz się trochę pobawić wartościami przy swstack i hwstack ale zbyt mocno ich nie zwiększaj.
  • #5 9468663
    mariansq
    Poziom 15  
    No niestety nie mam tego kodu w swym programie-dopisze.

    Wojtek75, myslisz że to sprawa stosu? Czy to moze byc powodem tego, iż program pomija instrukcje "if " i wykonuje jej zawartość niezależnie czy flaga_500ms jest 0 czy 1?
    Moze źle ta flage wystawiam?

    Kurcze niby to takie proste a zamotałem sie na maks:)

    Mam wszystko:
    -przerwanie jest i działa
    - odczyt i obliczenia działaja
    tylko to razem powiazać żeby wyswietlić wynik jak przerwanie wystawi flage i tak w koło.
  • #6 9469153
    Konto nie istnieje
    Konto nie istnieje  
  • #7 9471419
    Wojtek75
    Poziom 24  
    Jeżeli masz zadeklarowane sporo zmiennych, korzystasz z przerwań, wywołujesz z pętli głównej podprogramy, procedury, funkcje to może się zdarzyć że standardowe ustawienia stosu nie wystarczą i trzeba zrobić korektę. Sprawdź to o czym pisałem wcześniej, będziesz widział czy jest jakaś poprawa.
  • #8 9471643
    mariansq
    Poziom 15  
    Dzisiaj zamierzam to sprawdzic, wczoraj już nie miałem sił - ginekolog, szkoła rodzenia itp-wrażenia:)

    Faktycznie zmiennych juz troszke jest, poza tym menu oparte mam na CASE'ach i jest ich troche-przełączam dziesiatkami (dana dziesiatka to okreslone menu i podmenu).
    Procedury dopiero 3 i ze 2 podprogramiki w tym od przerwania. Najgorsze, ze to dopiero początek:-( eh :-) Nigdy wczesniej nie miałem z tym problemów ale chyba dlatego ze nie miałem rozbudowanego programu wraz z wykorzystywaniem przerwań. Nic trzeba sie czegos nowego nauczyć:)
    Wojtek75 zastosuje Twoje zalecenia i dam znać co i jak . Pamieć flash dopiero w 1/4 zapełniona wiec miejsca jeszcze sporo na i2c, RS232, 1 Wire i troche procedur:-)
    Myslę, ze jeszcze musze zweryfikować program pod kątem zmiennych czy można je zwalniać i wykorzystać dalej-choć raczej tak robie. Głownie sa typu byte i bit no ale do pomiarów mam word dla ADC i single.
  • #9 9471703
    piotr5000
    Poziom 21  
    mariansq - sprawdź czy jeśli wywołasz odczyt so 5 sekund zamiast 0,5
    czyli if licz =190

    to program zadziała prawidłowo ?

    Jest możliwe , że wykonanie 100 pomiarów , uśrednienie , wykonanie pozostałych procedur trwa powyżej 0,5 sekundy i masz wrażenie , że warunek jest wykonywany bez względu na stan flagi , a prawdziwa przyczyna jest taka , że flaga w czasie wykonania podprogramów została ponownie ustawiona ?
  • #10 9472128
    mariansq
    Poziom 15  
    Mysle, że obliczenia trwaja znacznie szybciej - dowodem jest zmiana nastaw potencjometem.Wtedy momentalnie mam nowe wyniki zgodne z multimetrem (kilkanaście zmian na sek, podczas ruchu potencjometrem zamiast co 0,5s)

    Aha i jeszcze jedno pytanie ważne:
    Czy podczas kompilacji programu jesli coś nie tak ze stosem program wywali komunikat czy raczej nie jest w stanie okreslic wielkosci stosu podczas kompilacji?
  • #11 9472668
    dondu
    Moderator na urlopie...
    mariansq napisał:
    Czy podczas kompilacji programu jesli coś nie tak ze stosem program wywali komunikat czy raczej nie jest w stanie okreslic wielkosci stosu podczas kompilacji?

    Wyobraź sobie sytuację gdy na przykład masz program który zagnieżdża się wraz z nadchodzącymi danymi np. po SPI, ciągle skacze do obsługi przerwania, a tam jako pierwszy rozkaz, często w kodach spotykamy SEI() i delay() lub while(). Na stosie odkładana jest kolejna porcja danych i tak w kółko, przy każdej odebranej danej.

    Czy stos się przepełni zależy jedynie od ilości danych, które napłyną, a tego kompilator nie wie.
  • #12 9474201
    mariansq
    Poziom 15  
    Faktycznie ustawienia stosu były do baniaka , nie zwróciłem wcześniej na to uwagi.
    Było:
    $hwstack = 12 dałem 40
    $swstack = 8 40
    $framesize =16 24
    Wartości ustawiłem w srodowisku Bascom w option/compiler/chip
    w działaniu programu nic sie nie zmieniło:-(.

    
    sub oblicz()
    For X = 0 To 99
       Wart1_adc = Getadc(0)
       Ua_bufor = Ua_bufor + Wart1_adc
       Next X
    
       Ua_bufor = Ua_bufor / 100
       Ua_bufor = Ua_bufor * 0.0049
       Ua_bufor = Ua_bufor * 4
    
       If Flaga_500ms = 0 Then
          Ua_srednia = Ua_bufor
          Flaga_500ms = 1
          Reset Led3
       Else
          Set Led3
       End If
    end sub
    


    dodałem kontrolnie led , zeby widzieć czy mruga. W menu głównym mruga czyli jak uruchomi sie program to pod case 1 mruga co 0,5 s, ale pod case 11 mruga nieregularnie i w zalezności od ustawionego napiecia pomiaru-dziwne. Czyli raz zadziała co 0,5 s a czesciej tak jakby nie było warunku if sprawdzajacego flage przypisujacego wartość do wyświetlenia :

    
    Do
    .
    call oblicz()
    
    kod
    .
    
    case 1: 'menu głowne gdy nacisne enter to wchodze do case11
          Locate 1 , 1
          Lcd Licznik ; " " ; "Menu Glowne:" ; " " ; Chr(0) ;
          Locate 2 , 1
          Lcd " Pomiary el    >"
    .
    .
    case 11:
          I2csend &H42 , &B00001000
          Ua_wart = Fusing(ua_srednia , "#.&&")
          Locate 1 , 1
          Lcd Ua_wart ; "           "
          Locate 2 , 1
          Lcd " 
         
    Loop
    


    Kurcze moze inaczej trzeba do tego podejść?
    No ale główne założenie to takie, żeby program odczytywał i liczył wartości zmierzone w programie głównym (procedura) a wielkośc do wysietlenia żeby była wystawiana co 0,5s za posrednictwem flagi i wyswietlona w odpowiednim "case"

    co tu wymyslic
  • #14 9474326
    mariansq
    Poziom 15  
    Program dopiero powstaje (dopiero mam szkielet do uzupełnienia), wiec moze byc duzo elementów nieaktywnych takich jak PWM'y i i2C itp(ale konfiguracje juz sa), głównie jest MENU nieskonczone ale tyle co jes to działa , no i nieszczesny pomiar z wyswietleniem co 0,5 s za pomoca flagi z przerwania. Docelowo będą czytane wszystkie wejscia ADC ale jak utknołem z jednym probleme to nie rozwijam tematu coby niezamotac kodu bardziej niz jest:)

    Oby moderator mi wybaczył wklejanie robali:-)
    w razie problemów zrobie załącznik-nie chce smiecić na forum

    
    $regfile = "m16def.dat"
    $crystal = 8000000
    
    
    
    '===============================================================================
    ' Instrukcje konfiguracji peryferiow oraz urzadzeń zewnetrznych
    '===============================================================================
    
    ' konfiguracja LCD
    Config Lcd = 16 * 2
    Config Lcdpin = Pin , Db4 = Portc.5 , Db5 = Portc.4 , Db6 = Portc.3 , Db7 = Portc.2 , E = Portc.6 , Rs = Portc.7
    ' konfiguracja I2C
    Config Sda = Portc.1
    Config Scl = Portc.0
    ' konfiguracja piów wejsciowych
    Config Pinb.0 = Input
    Config Pinb.1 = Input
    Config Pinb.2 = Input
    Config Pinb.3 = Input
    ' konfiguracja pinów wyjściowych
    Config Pinb.4 = Output
    Config Pinb.5 = Output
    Config Pinb.6 = Output
    Config Pinb.7 = Output
    Config Pind.4 = Output
    Config Pind.5 = Output
    ' konfiguracja beep'era
    Config Pind.3 = Output
    
    
    Config Pind.7 = Output
    
    ' konfiguracja timerów
    Config Timer0 = Timer , Prescale = 1024
    Config Timer2 = Pwm , Async = Off , Prescale = 8 , Pwm = On , Compare Pwm = Clear Up
    Config Timer1 = Pwm , Pwm = 10 , Compare A Pwm = Clear Down , Compare B Pwm = Clear Down , Prescale = 64
    ' konfiguracja wewnetrznego przetwornika A/C
    Config Adc = Single , Prescaler = Auto , Reference = Off
    
    On Timer0 Przyciski
    
    
    
    
    
    '===============================================================================
    ' Deklaracje nagłówków funkcji oraz procedur
    '===============================================================================
     Declare Sub Pcf_ster()
     Declare Sub Migaj()
     Declare Sub Plus_minus(byval Parametr As Byte , Byval Parametr2 As Byte)
     Declare Sub Oblicz()
    '===============================================================================
    ' Instrukcje konfiguracyjne przerwania
    '===============================================================================
    
    
    
    
    '===============================================================================
    ' Definicje zmiennych, stałycy i aliasów
    '===============================================================================
     Dim I As Byte , X As Byte
     Dim K As Byte
     Dim Licz As Byte , Licz1 As Byte , Licznik As Byte
     Dim Bufor As Byte
     Dim Bufor2 As Byte
     Dim Przycisk As Byte
     Dim Granica_max As Byte , Granica_min As Byte , Strona As Byte
     Dim A_pwm As Integer , B_pwm As Integer
     Dim Wart1_adc As Word
     Dim Ua As Single , Ub_plus As Single ,
     Dim Ua_srednia As Single , Ua_bufor As Single
     Dim Ua_wart As String * 3
    
     Dim Flaga1 As Bit , Flaga2 As Bit , Flaga3 As Bit , Flaga4 As Bit
     Dim Flaga_200ms As Bit , Flaga_500ms As Bit
    
    Led_lcd Alias Portd.7
    
    ' aliasy przycisków  UWAGA zmienna alias jest typu Bit!
    Beck Alias Pinb.0
    Menu Alias Pinb.1
    Enter Alias Pinb.2
    Nexxt Alias Pinb.3
    ' aliasy LED'ów - zapalenie przez "reset", zgaezenie przez "set"
    Led1 Alias Portb.4
    Led2 Alias Portb.5
    Led3 Alias Portb.6
    Led4 Alias Portb.7
    ' alias Beep'era
    Buzer Alias Portd.3
    
    ' symbole graficzne
    
    Deflcdchar 0 , 1 , 1 , 1 , 5 , 9 , 31 , 8 , 4               ' enter ? with number (0-7)
    Deflcdchar 1 , 15 , 9 , 9 , 15 , 32 , 32 , 32 , 32          ' stopien ? with number (0-7)
    Deflcdchar 2 , 32 , 14 , 17 , 17 , 10 , 10 , 27 , 32        ' znak ohma
    '===============================================================================
    ' Program Główny
    '===============================================================================
    
    ' Ustawienia koncowe timera0 - odblokowanie globalnego systemu przerwań
    Enable Interrupts
    Enable Timer0
    Load Timer0 , 200
    
    ' rezystory podciagajace do przycisków
    Set Portb.0
    Set Portb.1
    Set Portb.2
    Set Portb.3
    
    Portb = &B11111111                                          ' wpisanie jedynek celem odczytu stanów na wejsciach
    Bufor = Pinb
    
    
    Licznik = 1
    Strona = Licznik
    ' ustawienie pierwszego obrazu
    Granica_max = 6
    Granica_min = 1
    Flaga1 = 1
    Flaga2 = 1
    Flaga3 = 1
    Flaga4 = 1
    Flaga_500ms = 1
    
    ' zerowanie zmiennych
    Ua_srednia = 0
    Ua_bufor = 0
    
    
    Portd.3 = 1
    Licz = 0
    Licz1 = 0
    
    ' wyłaczenie przekaźników na czas pisania softu
    I = 0
    I2csend &H42 , I
    Ocr2 = 200
    
    ' $$$$$$$$$$$$$$$$$$ Główna petla $$$$$$$$$$$$$$$$$$
    
    
    Start Adc
    
    Waitms 200
    Cursor Off
    Cls
    
    
    
    Do
    
    
    Call Migaj()
    Call Plus_minus(granica_max , Granica_min)
    Call Oblicz()
    
    
    ' warunki poruszania sie po Menu
    If Przycisk.1 = 0 Then
       Licznik = 1
       Granica_max = 6
       Granica_min = 1
       Flaga3 = 1
    End If
    
    ' zalacz pomiary elektryczne
    If Flaga3 = 0 And Licznik = 1 Then
       Licznik = 11
       Granica_max = 16
       Granica_min = 11
       Strona = Licznik
       Waitms 200                                               ' opoznienie zmiany stany przycisku celem unikniecia samoistnego przejscia w glab menu
       Flaga3 = 1
    End If
    
    'zalacz pomiary temperatury
    If Flaga3 = 0 And Licznik = 2 Then
       Licznik = 21
       Granica_max = 24
       Granica_min = 21
    
       Waitms 200
       Flaga3 = 1
    
    ' zalacz sterowanie z komputera i lokalne
    End If
    
    If Flaga3 = 0 And Licznik = 4 Then
       Licznik = 31
       Granica_max = 32
       Granica_min = 31
       Waitms 200                                               ' opoznienie zmiany stany przycisku celem unikniecia samoistnego przejscia w glab menu
       Flaga3 = 1
    End If
    
    If Flaga3 = 0 And Licznik = 6 Then
       Licznik = 41
       Granica_max = 46
       Granica_min = 41
       Waitms 200                                               ' opoznienie zmiany stany przycisku celem unikniecia samoistnego przejscia w glab menu
       Flaga3 = 1
    End If
    
    
    
    
    
    ' tworzenie zmiennej strona która numeruje nap pozycje w podmenu
    Strona = Licznik - Granica_min
    Strona = Strona + 1
    
    ' menu główne
    '//////////////////////////////////////
    
    Select Case Licznik
    
       Case 1 :
    
          Locate 1 , 1
          Lcd Licznik ; " " ; "Menu Glowne:" ; " " ; Chr(0) ;
          Locate 2 , 1
          Lcd " Pomiary el    >"
    
       Case 2 :
          Locate 1 , 1
          Lcd Licznik ; " " ; "Menu Glowne:" ; " " ; Chr(0) ;
          Locate 2 , 1
          Lcd "< Pomiary temp >"
    
       Case 3 :
          Locate 1 , 1
         Lcd Licznik ; " " ; "Menu Glowne:" ; " " ; Chr(0) ;
          Locate 2 , 1
          Lcd "< Generator    >"
    
       Case 4:
          Locate 1 , 1
          Lcd Licznik ; " " ; "Menu Glowne:" ; " " ; Chr(0) ;
          Locate 2 , 1
          Lcd "< RS 232       >"
    
       Case 5:
          Locate 1 , 1
          Lcd Licznik ; " " ; "Menu Glowne:" ; " " ; Chr(0) ;
          Locate 2 , 1
          Lcd "< Ladowarka    >"
    
       Case 6:
    
          Locate 1 , 1
          Lcd Licznik ; " " ; "Menu Glowne:" ; " " ; Chr(0) ;
          Locate 2 , 1
          Lcd "< Ustawienia    "
    
    
    
    
    
    
    ' pomiary elektryczne
    '/////////////////////////////////////
    
    
       Case 11:
          I2csend &H42 , &B00001000
    
          Ua_wart = Fusing(ua_srednia , "#.&&")
          Locate 1 , 1
          Lcd Ua_wart ; "           "
          Locate 2 , 1
          Lcd "                "
    
    
       Case 12:
    
          Locate 1 , 1
          Lcd Strona ; "< Menu:       >"
          Locate 2 , 1
          Lcd "    strona2     >"
    
       Case 13:
    
          Locate 1 , 1
          Lcd Strona ; "< Menu:       >"
          Locate 2 , 1
          Lcd "    strona3     >"
    
       Case 14:
    
          Locate 1 , 1
          Lcd Strona ; "< Menu:       >"
          Locate 2 , 1
          Lcd "    strona4     >"
    
        Case 15:
    
          Locate 1 , 1
          Lcd Strona ; "< Menu:       >"
          Locate 2 , 1
          Lcd "    strona5     >"
    
        Case 16:
    
          Locate 1 , 1
          Lcd Strona ; "< Menu:        "
          Locate 2 , 1
          Lcd "    strona6     >"
    
    ' pomiary temperatury
    '/////////////////////////////////////
    
    
       Case 21:
    
          Locate 1 , 1
          Lcd " T1out:    " ; Chr(1) ; "C" ; Strona ; ">"
          Locate 2 , 1
          Lcd " T2out:    " ; Chr(1) ; "C   "
    
       Case 22:
          Locate 1 , 1
           Lcd "<T3out:    " ; Chr(1) ; "C" ; Strona ; ">"
          Locate 2 , 1
          Lcd " T4out:    " ; Chr(1) ; "C   "
       Case 23:
          Locate 1 , 1
          Lcd "<Tnpn:     " ; Chr(1) ; "C" ; Strona ; ">"
          Locate 2 , 1
          Lcd " Tpnp:     " ; Chr(1) ; "C   "
       Case 24:
          Locate 1 , 1
          Lcd "<Tgrez:    " ; Chr(1) ; "C" ; Strona ; " "
          Locate 2 , 1
          Lcd "     puste      "
    ' generator
    '////////////////////////////////////
    
    
    ' Sterowanie PC
       Case 31:
    
          Locate 1 , 1
          Lcd Licznik ; " Menu:            "
          Locate 2 , 1
          Lcd "    lokalne    >"
    
       Case 32:
          Locate 1 , 1
          Lcd Licznik ; " Menu:            "
          Locate 2 , 1
          Lcd "<   z komputera   "
    
    
    ' Ustawienia
       Case 41:
    
          Locate 1 , 1
          Lcd Licznik ; " Menu:            "
          Locate 2 , 1
          Lcd "    ust LCD    >"
    
       Case 42:
          Locate 1 , 1
          Lcd Licznik ; " Menu:            "
          Locate 2 , 1
          Lcd "<       Beep      "
    
       Case 43:
    
          Locate 1 , 1
          Lcd Licznik ; " Menu:            "
          Locate 2 , 1
          Lcd "     Alarm     >"
    
       Case 44:
          Locate 1 , 1
          Lcd Licznik ; " Menu:            "
          Locate 2 , 1
          Lcd "<     zaciski     "
        Case 45:
    
          Locate 1 , 1
          Lcd Licznik ; " Menu:            "
          Locate 2 , 1
          Lcd "    status     >"
    
       Case 46:
          Locate 1 , 1
          Lcd Licznik ; " Menu:            "
          Locate 2 , 1
          Lcd "<      inne       "
    
    End Select
    
    Waitms 100
    
    
    
    
    Loop
    
    
    
    
    End                                                         'end program
    
    
    '===============================================================================
    'Definicje wcześniej zadeklarowanych funkcji i procedur
    '===============================================================================
    
    Sub Pcf_ster()
    
    
    ' w budowie
    
    End Sub
    '***********************
    
    ' **********************
    Sub Migaj()
    
    For K = 0 To 3
       I = K + 4
       If Przycisk.k = 0 Then
    
          Reset Portb.i
    
       Else
    
          Set Portb.i
    
       End If
    Next K
    
    I = 0
    End Sub
    '************************
    Sub Oblicz()
    
    
    
    
       For X = 0 To 99
       Wart1_adc = Getadc(0)
       Ua_bufor = Ua_bufor + Wart1_adc
       Next X
    
       Ua_bufor = Ua_bufor / 100
       Ua_bufor = Ua_bufor * 0.0049
       Ua_bufor = Ua_bufor * 4
    
       If Flaga_500ms = 0 Then
          Ua_srednia = Ua_bufor
          Flaga_500ms = 1
          Reset Led3
       Else
          Set Led3
       End If
    
    
    End Sub
    
    '**************************
    
    
    Sub Plus_minus(byval Parametr As Byte , Byval Parametr2 As Byte)
    
    
       If Przycisk.3 = 0 And Licznik >= 1 Then
          Incr Licznik
       End If
       If Przycisk.0 = 0 And Licznik =< Parametr Then
          Decr Licznik
       End If
       If Licznik >= Parametr Then
          Licznik = Parametr
       End If
       If Licznik =< Parametr2 Then
          Licznik = Parametr2
       End If
    
    End Sub
    
    '===============================================================================
    ' Podprogramy obsługi przerwan oraz tablice
    '===============================================================================
    
    Przyciski:
    
    Load Timer0 , 200
    
    
    If Beck = 0 Or Menu = 0 Or Enter = 0 Or Nexxt = 0 Then
    
      If Bufor = Pinb Then
         Przycisk = Pinb
         ' flaga ustawiona ma wartosc zero  tak jak wcisniety przycisk tylko na stałe
         Flaga1 = Przycisk.0
         Flaga2 = Przycisk.1
         Flaga3 = Przycisk.2
         Flaga4 = Przycisk.3
    
                                                 ' zapisanie do zmiennej przycisk wartosci portu B
      Else
         Przycisk = Pinb And &B00001111
         Bufor = Pinb                                           ' zapisanie do bufora wartosci portu b z wcisnietym przyciskiem
    
      End If
    Else
    
      Przycisk = Pinb Or &B00001111
    
    End If
    
    
    
    Incr Licz
    If Licz = 8 Then
       Licz = 0
       Set Flaga_200ms
    End If
    
    Incr Licz1
    
    If Licz1 = 19 Then
         Flaga_500ms = 0
         Licz1 = 0
    End If
    
    Return
    
    '**************************
    
    
    
    
  • Pomocny post
    #15 9474516
    xury
    Specjalista automatyka domowa
    Teraz przypomniałem sobie, że miałem podobne problemy i wydaje mi się, że coś wspólnego miało z tym Fusing. Spróbuj wyświetlać na razie bez konwersji single na tekst. Ach te problemy miałem na wersji 1.11.9.8
    https://www.elektroda.pl/rtvforum/topic1758870.html
  • #16 9474576
    mariansq
    Poziom 15  
    moja wersja to jeszcze 1.11.7.3 :)

    Zapisałem program w nowym pliku i wyciełem niepotrzebne rzeczy coby zostawic tylko , przerwanie, procedurke oblicz i efektnadal został.
    Czyli co którys raz led kontrolny mignoł co 0,5s lub wcale. Ale tu ciekawostka.
    Gdy przekreciłem potencjometr od napiecia na 3/4 zakresu to program jakby zaczynał poprawnie działac-dziwne.

    No ale do sedna - oczytałrm "xury" Twoja wiadomość i wywaliłem w tym okrojonym kodzi instrukcje fusing

    Podziekowania

    efekt:

    program działa poprawnie-wyswietla co 0,5 sek wartośc i mignie ledem testowym.
    huuuuuraaaa :-)

    mam nadzieje , że jeszcze pomozesz mi dalej uporac sie z tym problemem fusing

    sprawdze zaraz w duzym kodzie czy tez bedzie działać.

    No ale jak temu zapobiec - jak przeformatowac te wyswietlane wynikido granic uzytecznosci:)
    Moze tez soft zdało by sie zmienić u mnie- nie mam nowszego Bascoma.


    W programie , który dodałem tez działa bez fusing - "smierdział mi od poczatku wyswietlaniem tych krzaków ale żeby cały soft wywalał to bym nie wpadł:)
  • #18 9474817
    mariansq
    Poziom 15  
    Fusing beeeeeee:-) , Ale jak ja biedny teraz wyświetle sobie liczbe do dwuch miejsc po przecinku?:-) bo juz taki dobry z programowania to narazie nie jestem. Nie ma jakies innej instrukcji jakiegoś format czy coś:)
    Zaznaczam, ze C nie znam tylko Bascom na poziomie radzenia sobie i VBA ale to nie ta działka:)

    PS Patrze na wyswietlacz i nie wierze ze chodzi-co ja sie nagimnastykowałem z różnymi wariantami-ale czego sie nie robi by nie miec waitms i innych takich.
  • #19 9474852
    xury
    Specjalista automatyka domowa
    Format powoduje te same problemy. Bo okazało się że ja się pomyliłem z tym Fusing, bo ja miałem to samo z Format właśnie, jak teraz zagłębiłem się w lekturze swojego tematu.
    Wydaje mi się, ze trzeba to robić na piechotę bez konwersji liczby na tekst.
    Wyświetlać liczbę, a nie potrzebne rzeczy szybko przesłaniać spacjami, lub coś w tym rodzaju.
    Albo - teraz mi przyszło do głowy użyj INT i FRAC.

    Czyli reasumując problemy, które nas obu dotknęły to konwersja liczby na tekst
  • #20 9475376
    Wojtek75
    Poziom 24  
    Czyli jednak problemy z konwersją.
    mariansq napisał:
    moja wersja to jeszcze 1.11.7.3 :)

    Zdecydowanie bym ci jednak zalecał ściągnąć najnowszą dostępną wersję.
  • #21 9475936
    mariansq
    Poziom 15  
    Dzis spróbuje napisac sobie procedure konwertujaca liczbe na format 0,00 - mam pomysła:-).
    Koncepcje podsunął kolega xury i wielkie dzieki dla niego.

    Jaka jest najnowsza wersja Bascom, ale taka która pewnie i stabilnie działa?

    Czy nowsza wersja nie będzie mieć problemów z konwersjami czy lepiej zrobić sobie jednak na piechote i nie łudzić sie że "niedobre" fusingi i formaty zadziałaja :-) ?

    Apropo tych fusingów i formatów- problemy z nimi zaczynają sie w przypadku używania przerwań? Na to by wyglądało.

    W programach bez przerwań programy chodzą mi stabilnie z formatowaniem na string.
  • #22 9476057
    piotrva
    VIP Zasłużony dla elektroda
    najnowsza wersja BASCOM jest dostępna zawsze jako update na stronie wydawcy, teraz to już jest 2.xxxxx
  • #23 9478932
    mariansq
    Poziom 15  
    Kombinuje z tym formatem i juz mam prawie rozwiazany problem tylko jak wyswietlić liczbe bez przecinka i zera po nim czyli zamiast 12.0 ma byc 12 ?

    Ok już po problemie-zacmiło mnie bo późno i piwo czeka:-)

    wystarczyło odpowiednie zmienne zrobic jako word i integer:-)
    Oto moja procedurka formatujaca liczby do dowolnej ilosci mejsc po przecinku bez uzycia "paskudnych" instrukcji tekstowych fusing i format:-)
    
    Declare Sub Formatuj(wartosc As Single , Byval Przecinek As Byte ) 
    Dim calkowita as integer, ulamkowa as single, ulamkowa1 as word
    
    
    Sub formatuj (wartosc, przecinek)
    
    Przecinek= 10 ^ przecinek
    
    Calkowita= int ( wartosc)
    Ulamkowa=frac(wartosc)
    Ulamkowa = Ulamkowa * Przecinek
    Ulamkowa1 = Round(ulamkowa)
    
    End sub
    
    
    


    No niestety wyswietlanie trzeba składać ale to i takwygodniejsze niż "zamazywać" pustymi polami

    
    lcd calkowita;".";ulamkowa1"           "
    


    Kombinowałem aby wartośc ta była jedna liczba ale typ single zawsze robi xx.0 , a jak dodam cześć ulamkową do całkowitej to z powrotem "format szedł na grzyby"

    no chyba że coś jeszcze wykminie:)
  • #25 9479060
    mariansq
    Poziom 15  
    I posłuchałem kolegi. Instrukcja frac wydobywa liczbe do postaci 0.xxxxxxxx. Potem trezeba zrobić mnożenie przez ilość miejsc po przecinku jakie chcemy miec czyli 2 miejsca to mnozymy przez 100.
    Nastepnie mamy postac (dla 2 miejsc) xx.xxxxxx i traktujemy to "round(x)" co nam daje wynik postaci yy.0 (gdzie yy to nasze zaokraglone miejsca po przecinku) . Ale formacik yy.0 tego co po przecinku troche komplikuje sprawe. Pomnieważ chcąc otrzymać zapis xx.yy nalezy dodać yy.0 / 100 do liczby całkowitej z formatem xx.0. Problem w tym że podzielenie yy.0 / 100 spowrotem tworzy 0.yyyyyyyyyy i znowu mamy robale. dlatego narazie pewnym rozwiazaniem jest to co zrobiłem wyzej - zmienna calkowita i ulamkowa1 sa typu word ale nawet bezpieczniej i lepiej bedzie gdy zmienna całkowita bedzie typu integer:-) gdy ujemne liczby maja byc. Procedurka działa bezproblemowo - jutro spróbuje "zatrudnić" ja do wyswietlania wielu wyników.




    A jednak:-( znalazłem "babola" w tym rozwiazaniu - kurcze:-)

    procedura powyższa nie jest w stanie przekonwertowac liczby postaci np:
    12,012345

    przekształci ją na 12,1 !
    dopiero 12,1234 zrobi na 12,12 lub 12,5678 na 12,57

    Wiem gdzie tkwi problem i jutro to zmienie - mam pomysła - troche sie uprości procedura no i niestety z góry trzeba sie bedzie zastanowić ile na maksa ma być miejsc po przecinku wykorzystywane w programie. Czyli jesli zadeklarujemy 4 miejsca to 3,2,1 po przecinku do wykorzystania w całym programie bezproblemowo bez zmiany kodu.

    chyba , że przyśni mi sie coś lepszego:-)

    ================
    7 maja 2011
    ================
    Witam ponownie poniżej rozwiazanie formatowania bez fusingów i formatów z zaokragleniem do 2 miejsc po przecinku. Tym razem procedura działa prawidłowo.

    
    
    Declare Sub Formatuj(wartosc As Single )
    ' i co najwazniejsze to odpowiednie typy zmiennych!!!
    Dim Calkowita As Integer , Ulamkowa As Single , Dziesiatki As Byte , Setki As Byte
    
    Sub Formatuj(wartosc )
    
    Calkowita = Int(wartosc)
    Ulamkowa = Frac(wartosc)
    Ulamkowa = Ulamkowa * 10
    Dziesiatki = Int(ulamkowa)
    
    Ulamkowa = Frac(ulamkowa)
    Ulamkowa = Ulamkowa * 10
    Ulamkowa = Round(ulamkowa)
    Setki = Int(ulamkowa)
    ' korekta zaokraglania ostatniej liczby
    if Setki = 10 Then
       Setki = 0
       Dziesiatki=1
    End If
    
    End Sub
    
    'tak wyswietlamy - lepsze to niz kombiunowanie z zamazywaniem
    Lcd Calkowita ; "." ; Dziesiatki ; Setki ; "          "
    
    


    no to teraz jak zrobiłem formatowanie , mozna dalej pisac program:-)
    jeszcze raz podziekowania dla kolegi "xury"

    temat zostawiam póki co otwarty
REKLAMA