Das PingPong wurde komplett in Bascom geschrieben. Der komplette Quelltext kann leider nicht freigegeben werden, wohl aber die entscheidenden Unterprogramme. Damit sind die ersten Schritte für eigene Software ganz einfach.
Die Timer-2-Interruptprozedur erledigt alles was mit dem Display zu tun hat. Auf der Anwenderseite gibt es eine Art Video-RAM im Array Leds(12). Die einzelnen Bits werden dann laufend auf die entsprechenden Ports verteilt. Außerdem erzeugt das Unterprogramm den Schiebetakt. Es wird eine einzelne Null zwischen vielen Einsen durch beide Schieberegister geschoben. Damit wird jeweils eine einzelne Kathoden-Reihe angesteuert.
Tim2_isr:
Col = Col + 1
If Col = 13 Then Col = 1
Vy = Col + 0
Portd = 0
Portb = 0
Portc = 0
If Col = 1 Then Portb.4 = 0 Else Portb.4 = 1
Portb.3 = 1 'cl
Portb.3 = 0
Portb.2 = 1 'Str
Portb.2 = 0
Portdout = Low(leds(vy))
Portcout = Portdout And 15
Portdout = Portdout And 240
Portd = Portdout
Portc = Portcout
Portb = High(leds(vy))
Return
End
Daneben gibt es eine Testroutine zur Ansteuerung aller LEDs. Genau dieses Unterprogramm wurde auch bei der Produktion verwendet und kann auch in der Komplettsoftware über Portc.2 gestartet werden.
Sub Test
For X = 1 To 12
Leds(x) = 1023
Next X
Waitms 1000
For X = 1 To 12
For Y = 1 To 12
Leds(y) = 0
Next Y
Leds(x) = 1023
Waitms 100
Next X
For Y = 1 To 10
For X = 1 To 12
Vhelp = Y - 1
Vhelp = 2 ^ Vhelp
Leds(x) = Vhelp
Next X
Waitms 100
Next Y
For X = 1 To 12
Leds(x) = 0
Next X
End Sub
Für das gesittete Abschalten des Controllers gibt es die Sub Standby. Der entscheidende Befehl ist Powerdown. Zuvor muss allerdings jeder Verbraucher im System abgeschaltet werden. Portd.2 ist der Interrupteingang. Der Pin wird als Eingang mit Pullup initalisiert. Ein Low-Pegel am Münzkontakt löst dann den Interrupt aus und weckt damit den Controller auf.
Sub Standby
Stop Timer2
Portc = 0
Portd = 0
Portb = 0
Stop Adc
Ddrd.2 = 0
Portd.2 = 1
Enable Int0
Powerdown
Ddrd.2 = 1
Portd.2 = 0
Start Adc
Start Timer2
End Sub
Int_isr:
Disable Int0
Return
Wichtig ist die Sub Initialisierung, die man am Anfang eines eigenen Programms aufrufen sollte. Damit werden alle Ports, der Timer, der Interrupt und der AD-Wandler passend eingestellt.
Sub Initialisierung
Config Portc = 15 'PORTC als AD-Eingang
Config Portb = Output
Config Portd = 255
Config Timer2 = Timer , Prescale = 8
On Ovf2 Tim2_isr
Enable Timer2
Enable Interrupts
Start Timer2
Config Adc = Single , Prescaler = 64 , Reference = Off
Start Adc
Config Int0 = Low Level 'Falling
On Int0 Int_isr
End Sub
Das erste eigene Programm ist damit sehr übersichtlich. Nach dem Start und der Initalisierung wird der LED-Test aufgerufen und danach der Controller abgeschaltet. Da beides in einer Do-Loop-Schleife liegt kann man das Programm über den Münzkontakt beliebig oft starten.
'Pingppong LED-Ansteuerung
$crystal = 8000000
$regfile = "m8def.dat"
$hwstack = 64
$swstack = 64
$framesize = 64
Dim Leds(12) As Word
Dim X As Byte
Dim Y As Byte
Declare Sub Standby
Declare Sub Test
Declare Sub Initialisierung
Initialisierung
Do
Test
Standby
Loop
'*** Service-Unterprogramme ****
...
Download: LEDmatrix1.zip
Probieren Sie mal etwas Eigenes. Es genügt Daten ins Leds-Array zu schreiben und schon kann man etwas sehen.
Do
Leds(1) = 1
Leds(2) = 2
Leds(3) = 4
Leds(4) = 8
Leds(5) = 16
Leds(6) = 32
Leds(7) = 64
Leds(8) = 128
Leds(9) = 256
Leds(10) = 512
Leds(11) = 0
Leds(12) = 1023
Wait 4
Standby
Loop
Wenn Sie die LED-Muster als Binärzahlen schreiben sind die entstehenden Muster direkt zu erkennen.
Do
Leds(2) = &B0000000000
Leds(3) = &B0000000100
Leds(4) = &B0011111110
Leds(5) = &B0000000100
Leds(6) = &B0000000000
Wait 4
Standby
Loop