' µC Deklarationen $regfile = "m8515.dat" 'ATMEGA8515-Deklarationen $crystal = 4000000 ' Variablen Dim Temp_ziffer As Byte 'welche ziffer soll bearbeitet werden Dim Bcd_aus As Byte 'enthält den Wert der dez zahl die ausgegeben werden soll Dim Ausgang As Byte 'Segmentfolge die Ausgegeben wird aus Segmentcode - Tabelle Dim Sek_blink As Bit 'Blinkt im Sekunden Takt Dim Z1_sekunde As Byte 'Zeit Variablen Dim Z1_minute As Byte 'enthalten die Uhrzeit 'Z1-... => Low Wert der Zeit Dim Z2_sekunde As Byte 'Z2-... => High Wert der Zeit Dim Z2_minute As Byte ' Ein-/Ausgänge Config Portb = Output 'Port B als Ausgang Ddrd = &B0111100 '1 Ausgang, 0 Eingang Portd = &B1000011 '1 = PullUp aktiviert Eingang (Taster gegen Masse) 'Ausgänge: Segment_a Alias Portb.0 Segment_b Alias Portb.1 Segment_c Alias Portb.2 Segment_d Alias Portb.3 Segment_e Alias Portb.4 Segment_f Alias Portb.5 Segment_g Alias Portb.6 Dezimalpunkt Alias Portb.7 Ziffer_1 Alias Portd.2 Ziffer_2 Alias Portd.3 Ziffer_3 Alias Portd.4 Ziffer_4 Alias Portd.5 'Eingänge: T_min_stellen Alias Pind.0 T_h_stellen Alias Pind.1 ' Sonstiges Const Load_timer1 = 62755 'Konstande auf die der Timer1 geladen wird '4MHz = 62755 | 62760 etwas zu langsam <> 62750 etwas zu schnell '+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ ' Timer0 für Multiplexausgabe '+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ On Timer0 7segment 'Interrupt-Routine für Timer0-Overflow Config Timer0 = Timer , Prescale = 64 'Takt: Quarz/Prescale (möglich: 1, 8, 64, 256, 1024) Enable Timer0 'Timer0-Overflow-Interrupt einschalten '+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ ' Timer 1 als Zeitbasis '+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ On Timer1 Sekunde_plus 'Interrupt-Routine für Timer1-Overflow Config Timer1 = Timer , Prescale = 64 'Takt: Quarz/Prescale (möglich: 1, 8, 64, 256, 1024) Enable Timer1 'Timer0-Overflow-Interrupt einschalten Enable Interrupts 'Interrupts global zulassen Load Timer1 , Load_timer1 'Lädt den Timer auf einen wert vor '+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ ' Hauptprogramm '+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Do 'Start Hauptschleife If Z1_sekunde = 0 And Z2_sekunde = 0 And Z1_minute = 0 And Z2_minute = 0 Then Portd.1 = 1 'Pin wird auf High, also 5V geschaltet Waitms 1000 Portd.1 = 0 'Pin wird auf Low, also 0V geschaltet Waitms 1000 Portd.1 = 1 'Pin wird auf High, also 5V geschaltet Waitms 1000 Portd.1 = 0 'Pin wird auf Low, also 0V geschaltet Waitms 1000 Else If Z1_sekunde > 0 Then Z1_sekunde = Z1_sekunde - 1 Else Z1_sekunde = 9 If Z2_sekunde > 0 Then Z2_sekunde = Z2_sekunde - 1 Else Z2_sekunde = 5 If Z1_minute > 0 Then Z1_minute = Z1_minute - 1 Else Z1_minute = 9 If Z2_minute > 0 Then Z2_minute = Z2_minute - 1 End If End If End If End If End If ' ### Counter stellen ### ' Wird der Taster "T_min_stellen" betätigt werden die Minuten um eins erhöht. ' Wird der Taster "T_h_stellen" betätigt werden die Minuten um eins verringert. ' Werden beide gleichzeitig betätigt werden Sekunden und Minuten auf Null gesetzt. ' Wird einer der Taster länger betätigt (> 150ms) gibt es einen schnellvorlauf If T_min_stellen = 0 Then 'Wird "T_min_stellen" betätigt Waitms 150 'Entprellen If T_min_stellen = 0 Then 'Ist der Taster immer noch betätigt Incr Z1_minute 'wird Minute um eins erhöht Z1_sekunde = 0 'Sekunden auf Null setzen Z2_sekunde = 0 End If End If If T_h_stellen = 0 Then 'Wird "T_min_stellen" betätigt Waitms 150 'Entprellen If T_h_stellen = 0 Then 'Ist der Taster immer noch betätigt Decr Z1_minute 'wird Minute um eins verringert Z1_sekunde = 0 'Sekunden auf Null setzen Z2_sekunde = 0 End If End If If T_min_stellen = 0 And T_h_stellen = 0 Then 'Wenn "T_Min_stellen" und "T_H_stellen" gleichzeitig betätigt Z1_minute = 0 'dann werden Minuten und Sekunde auf 0 gestzt Z2_minute = 0 Z1_sekunde = 0 Z2_sekunde = 0 End If Loop 'Ende Hauptschleife End 'Programm Ende '+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ ' Interrupt-Routine für Ziffer ausgabe im 7 Segmentcode '+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ ' Bei jedem Aufruf wir nur eine Ziffer ausgegeben, d.h nur eine Anzeige wird ' angesteuert. Die anderen bleiben dunkel. Bei jedem Aufruf wird eine Anzeige ' weitergeschaltet. ' ' Anzeigen anordnung ' ' 1111 2222 3333 4444 ' 1 1 2 2 3 3 4 4 ' 1111 2222 3333 4444 ' 1 1 2 2 3 3 4 4 ' 1111o 2222o 3333o 4444o ' ' ^-- Dezimalpunkt ' ^---- 4. Ziffer | Minute Low Wert | Variable Zl_minute ' ^---------- 3. Ziffer | Minute High Wert | Variable Zh_minute ' ^----------------- 2. Ziffer | Stunde Low Wert | Variable Zl_stunde ' ^----------------------- 1. Ziffer | Stunde High Wert | Variable Zh_stunde 7segment: If Temp_ziffer = 4 Then Temp_ziffer = 0 'bestimmt die auszugebende Ziffer (1 bis 4) Incr Temp_ziffer 'bei jedem aufruf des Lable wir eine andere Ziffer ausgegeben Portb = &B11111111 'Alle Ziffern aus, ansonsten gibt es "Geister" Anzeigen Select Case Temp_ziffer 'welche Ziffer soll angesteuert werden Case 1 : Ziffer_1 = 1 '1. Ziffer Ziffer_2 = 0 Ziffer_3 = 0 Ziffer_4 = 0 Bcd_aus = Z2_minute Case 2 : Ziffer_1 = 0 '2. Ziffer Ziffer_2 = 1 Ziffer_3 = 0 Ziffer_4 = 0 Dezimalpunkt = Sek_blink 'Dezimalpunkt Bcd_aus = Z1_minute Case 3 : Ziffer_1 = 0 '3. Ziffer Ziffer_2 = 0 Ziffer_3 = 1 Ziffer_4 = 0 Bcd_aus = Z2_sekunde Case 4 : Ziffer_1 = 0 '4. Ziffer Ziffer_2 = 0 Ziffer_3 = 0 Ziffer_4 = 1 Bcd_aus = Z2_sekunde End Select 'Ermittelt aus der Segmentfolge-Tabelle den 7 Segmentcode für die auszugebende Zahl Select Case Bcd_aus Case 1 : Ausgang = Lookup(1 , Segmentfolge) Case 2 : Ausgang = Lookup(2 , Segmentfolge) Case 3 : Ausgang = Lookup(3 , Segmentfolge) Case 4 : Ausgang = Lookup(4 , Segmentfolge) Case 5 : Ausgang = Lookup(5 , Segmentfolge) Case 6 : Ausgang = Lookup(6 , Segmentfolge) Case 7 : Ausgang = Lookup(7 , Segmentfolge) Case 8 : Ausgang = Lookup(8 , Segmentfolge) Case 9 : Ausgang = Lookup(9 , Segmentfolge) Case 0 And Temp_ziffer = 1 : Ausgang = Lookup(10 , Segmentfolge) 'Nullstellenunterdrückung bei der ersten Ziffer Case 0 And Temp_ziffer > 1 : Ausgang = Lookup(0 , Segmentfolge) 'wenn nicht erste Ziffer Null anzeigen End Select 'Ausgabe des 7 Segmentcodes (Invertierend [Not] bei Anz. mit gem. Anode) Segment_a = Not Ausgang.0 'Segment A Segment_b = Not Ausgang.1 'Segment B Segment_c = Not Ausgang.2 'Segment C Segment_d = Not Ausgang.3 'Segment D Segment_e = Not Ausgang.4 'Segment E Segment_f = Not Ausgang.5 'Segment F Segment_g = Not Ausgang.6 'Segment G Return '+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ ' Interrupt-Routine für Timer1 / Zeitbasis '+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Sekunde_plus: Load Timer1 , Load_timer1 'Lädt den Timer auf einen wert vor Decr Z1_sekunde 'Vermindert den Low Wert der Sekunde um eins Toggle Sek_blink 'Ändert sich jede Sek., 1sec an 1sec aus Return '+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ ' 7 Segmentcode - Tabelle '+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ ' ' --A-- ' | | ' F B ' | | ' --G-- ' | | ' E C ' | | ' --D-- Segmentfolge: 'GFEDCBA / "1" Segment AN Data &B0111111 '0 Data &B0000110 '1 Data &B1011011 '2 Data &B1001111 '3 Data &B1100110 '4 Data &B1101101 '5 Data &B1111101 '6 Data &B0000111 '7 Data &B1111111 '8 Data &B1101111 '9 Data &B0000000 'leeres Feld (zur Nullstellenunterdrückung)