Erstaunlich wie schnell man eine Sprache hassen lernt. Und das auch noch bevor man in die wirklichen Probleme bei größeren Projekten kommt. Das schlimmste sind die deutschen Namen für Variablen und Methoden. Wenn man so etwas jahrelang nur auf Englisch macht, fehlt da einfach die Übung
Hier ist das python3 Programm, das noch einiges an Überarbeitung braucht.
Eine Anfängerfreundlich Dokumentation, eine GUI in Tk und vor allem sollte man sich auf die Zeiten verlassen können. Irgendwas muß ich da kurz vor Schluß falsch gemacht haben, aber ich wollte Dir schon mal ein Rückmeldung geben.
So wie das Programm konfiguriert ist, brauchst Du drei Buzzer.
Einen für die Rennleitung, um die einzelnen Läufe zu starten und zu stoppen.
Zwei für die Teilnehmer.
Die verwendeten Pins, Anzahl der Runden und die verwendeten Dateien muß man im Source-Code konfigurieren.
Die aktuellen Teilnehmer werden aus einer Datei gelesen.
Alles nicht schön, aber ich habe so gelernt, daß ich einen Pi3 mit 4GB RAM haben will, damit ich meinen Pfeilsuchroboter in C#/mono zusammenschustern kann.
Code: Select all
#!/usr/bin/python3
import os
import time
import datetime
import RPi.GPIO as GPIO
import subprocess
import operator
import csv
#
# Einstellungen
#
anzahlBuzzer = 2 # Anxzahl der Buzzer für die Teilnehmer. Die Rennleitung benötigt einen weiteren
anzahlRunden = 5 # Die Runden pro Lauf
pinBuzzer = [22, 27] # Die Pins an dem die Buzzer der Teilnehmer angeschlossen sind
pinRennleitung = 17 # Der Pin an dem der Buzzer der Rennleitung angeschlossen ist
entprellZeit = datetime.timedelta(seconds=2) # Entprellzeit der Buzzer
dateiCountDown = '/home/pi/Videos/test3.mp4'
dateiTeilnehmer = '/home/pi/TeamDatei.csv'
dateiErgebnisse = '/home/pi/Ergebnisse.csv'
#
# Globale Variablen
#
pinZuIndex = {}
rundenZaehler = [0 for b in range(anzahlBuzzer)]
rundenAnkuenfte = [[datetime.datetime.max for r in range(anzahlRunden)] for b in range(anzahlBuzzer)]
teamReihenfolge = []
rangliste = {}
#
# Unterprogramme
#
def leseTeamReihenfolge():
with open(dateiTeilnehmer, 'r') as teamDatei:
teamReader = csv.reader(teamDatei, dialect='excel')
for zeile in teamReader:
teamReihenfolge.append(zeile)
def schreibeErgebnisListe(lauf, gestartetUm):
with open(dateiErgebnisse, 'a') as ergebnisDatei:
ergWriter = csv.writer(ergebnisDatei, dialect='excel')
for t in range(anzahlBuzzer):
neueZeile = []
neueZeile.append(lauf[t])
neueZeile.append(str(gestartetUm))
# Gesamtzeit
if rundenAnkuenfte[t][anzahlRunden-1] == datetime.datetime.max :
neueZeile.append("dnf")
rangliste[lauf[t]] = datetime.timedelta.max
else:
zeit = rundenAnkuenfte[t][anzahlRunden-1]-gestartetUm
neueZeile.append(str(zeit))
rangliste[lauf[t]] = zeit
# Rundenzeiten
for r in range(anzahlRunden):
if rundenAnkuenfte[t][r] == datetime.datetime.max:
neueZeile.append("dnf")
else:
if r == 0:
zeit = rundenAnkuenfte[t][r]-gestartetUm
else:
zeit = rundenAnkuenfte[t][r]-rundenAnkuenfte[t][r-1]
neueZeile.append(str(zeit))
ergWriter.writerow(neueZeile)
def zeigeReihenfolge():
print("Reihenfolge:")
i = 1
for lauf in teamReihenfolge:
s = " Lauf " + str(i) + ": "
for t in lauf:
s += t + ", "
i += 1
print(s)
def zeigeRangliste():
print("")
print("Rangliste:")
sortiert = sorted(rangliste.items(), key=operator.itemgetter(1))
r = 1
for i in sortiert:
s = str(r) + ". " + i[0] + " - "
if i[1] == datetime.timedelta.max:
s += "dnf"
else:
s += str(i[1])
print(s)
r += 1
print("")
def initialisiereGPIO():
GPIO.setmode(GPIO.BCM)
GPIO.setwarnings(False)
GPIO.setup(pinRennleitung, GPIO.IN, pull_up_down=GPIO.PUD_UP)
for pin in pinBuzzer:
GPIO.setup(pin, GPIO.IN, pull_up_down=GPIO.PUD_UP)
def macheBuzzerScharf():
for pin in pinBuzzer:
GPIO.add_event_detect(pin, GPIO.FALLING, ankunft)
def sicherBuzzer():
for pin in pinBuzzer:
GPIO.remove_event_detect(pin)
# Callback, der die Rundenzeiten waehrend des Rennens speichert
def ankunft(pin):
ankunftsZeit = datetime.datetime.now();
i = pinZuIndex[pin]
runde = rundenZaehler[i]
if runde < anzahlRunden:
#if runde>0:
#print(ankunftsZeit - rundenAnkuenfte[i][runde-1])
if runde == 0 or (ankunftsZeit - rundenAnkuenfte[i][runde-1]) > entprellZeit:
rundenAnkuenfte[i][runde] = ankunftsZeit
rundenZaehler[i] += 1
print(str(pin) + " Runde " + str(runde) + " gewertet")
else:
print(str(pin) + " entprellt")
else:
print(str(pin) + " zu viele Runden")
# Bereitet die globalen Variablen für den nächsten Lauf vor
def initLauf():
rundenAnkuenfte = [[datetime.datetime.max for r in range(anzahlRunden)] for b in range(anzahlBuzzer)]
i = 0
for pin in pinBuzzer:
pinZuIndex[pin] = i
rundenZaehler[i] = 0
i += 1
#
# Hautprogramm
#
print("fireWorkOut V0.1")
print("")
initialisiereGPIO()
leseTeamReihenfolge()
zeigeReihenfolge()
print("")
print("")
laufNr = 0
for lauf in teamReihenfolge:
laufNr += 1
print("Lauf " + str(laufNr))
print("Teilnehmer:")
for teilnehmer in lauf:
print(" " + teilnehmer)
print("")
initLauf()
time.sleep(1) # schlechte Entprellung der beiden Rennleitungsklicks pro Lauf
print("Warte auf OK von Rennleitung")
GPIO.wait_for_edge(pinRennleitung, GPIO.FALLING)
retcode = subprocess.call(['/usr/bin/omxplayer', dateiCountDown], stdout=subprocess.DEVNULL)
#print(retcode)
laufGestartetUm = datetime.datetime.now()
macheBuzzerScharf()
print("Gestartet um " + str(laufGestartetUm) + ". Warte auf Rennleitung")
ende = False
while not ende:
GPIO.wait_for_edge(pinRennleitung, GPIO.FALLING)
laufGestopptUm = datetime.datetime.now()
if (laufGestopptUm - laufGestartetUm) > entprellZeit:
print("Lauf beendet")
ende = True
else:
print("rennleitung entprellt")
sicherBuzzer()
schreibeErgebnisListe(lauf, laufGestartetUm)
zeigeRangliste()
Eine Teilnehmerdatei muss genauso viele Spalten haben wie die definierten Buzzer