GPIO Ausgang ist high obwohl er nicht angesteuert wird

  • Hallo,


    ich habe ein kleines Problem mit den GPIO´s und komme nicht weiter.

    Mittels eines MCP3008 frage ich einen LDR ab und möchte damit bis zu einer gewissen Schwelle eine LED einschalten. Wird diese Schwelle überschritten, soll eine andere LED ansteuert werden.

    Konkret schalte ich den GPIO32 oder den GPIO40 ein. Sobald einer der beiden angesteuert ist, leuchten leider beide LEDs.
    Die LED sind direkt mit dem GPIO verbunden und mit einem 470 Ohm Vorwiderstand versehen.


    Hier mein Programm:


    from MCP3008 import MCP3008

    from RPi import GPIO

    from time import sleep


    GPIO.setmode(GPIO.BOARD)

    GPIO.setup(32, GPIO.OUT)

    GPIO.setup(40, GPIO.OUT)


    adc=MCP3008()


    i=0


    for i in range(5):

    valueLDR=adc.read(adc_channel=1)

    print ("Helligkeit:",valueLDR)


    if (valueLDR > 2000):

    GPIO.output(32, True)

    print ("Motor rechts")

    sleep(3)


    else:

    GPIO.output(40, True)

    print ("Motor links")

    sleep(3)


    i=i+1


    GPIO.cleanup()


    Im Anhang habe ich die MCP3008 Abfrage und mein Testprogramm angehängt.


    Würde mich freuen, wenn einer von euch eine zündende Idee hat - oder den Fehler in meinem Programm findet.


    Danke und Grüße


    Jonas

    Files

    • MCP3008.py

      (1.58 kB, downloaded 78 times, last: )
    • Test.py

      (513 Byte, downloaded 74 times, last: )
  • Ja, das ist mir aufgefallen. Zum Testen war dies für mich ausreichend.

    Ich starte das Programm, valueLDR >2000 - also soll die LED am GPIO 32 eingeschaltet werden. Jedoch wird ebenfalls die LED am GPIO 40 aktiv.

    Der Schwellwert bleibt über die ganze Dauer (5 Zyklen) >2000.

    Es sollte die LED am GPIO 40 also gar nicht eingeschalten werden.

    Gleiches verhalten, wenn ich den LDR abdecke und der Wert dauerhaft unter der Schwelle von 2000 ist.

    Solange der Wert dauerhaft über/unter der Schwelle ist, sollte doch nur eine LED aktiv sein?!


    Habe grade trotzdem mein Programm angepasst:

    if (valueLDR > 2000):

    GPIO.output(32, True)

    print ("Motor rechts")

    sleep(3)

    GPIO.output(32, False)


    Damit funktioniert es auf jeden Fall. Kannst du mir bei meinem Denkfehler helfen?

    Danke!

  • Ich würde die beiden GPIOs gleichzeitig schalten:

    GPIO.output(32, True)

    GPIO.output(40, False)

    print ("Motor rechts")

    und nach else umgekehrt.


    Servus !

    RTFM = Read The Factory Manual, oder so

  • ich hatte gegrübelt aber keine Lust eine Wahrheitstabelle aufzustellen,

    deine Lösung ist so einfach und auch logisch, da braucht man das ja nicht.


    Wäre ich vielleicht später auch noch drauf gekommen, aber Python ist nicht so meins, deswegen schwieg ich, aber jetzt sieht man ja egal welche Programmiersprache, logisch sind sie alle.

    lasst die PIs am Leben !
    Energiesparen:
    Das Gehirn kann in Standby gehen. Abschalten spart aber noch mehr Energie, was immer mehr nutzen. Dieter Nuhr

  • Danke für die Idee RTFM. Habe mit Programmierung bisher noch nicht so viel am Hut.


    Bei meiner jetztigen Lösung schaltet die LED ja bei einer Änderung der Schwelle "sofort". Sinnvoller wäre es für mich erst umzuschalten, wenn der Wert ca. 1 Minute unter/über dem Schwellwert ist um kurzzeitige Verdunklung/Beleuchtung auszuschließen.

    Leider habe ich hier keine richtige Idee wie das zu realisieren ist.

  • bei einem for i in range(x) brauchst du i nicht selber erhöhen oder vorher definieren. Der fängt standardmäßig bei 0 an und hört bei x-1 auf. Um bei 1 anzufangen kannst du einfach den Startwert übergeben. for i range(1,6) würde von 1-5 zählen.


    Du musst also den LDR wert über nen Zeitraum x messen. z.B. 1min. Ich würde da aller 10 sekunden ne Messung machen und die Werte in ne Liste schreiben, wenn eines dieser Werte im normalen bereich sind brich ab und fang von vorne an, ansonste Schalte die LEDs

    Der Unterschied zwischen Genie und Wahnsinn definiert sich im Erfolg.

  • Und zeigst du uns auch wie? So funktioniert das hier normalerweise - wir helfen Probleme zu lösen und als Gegenleistung wird wenigstens die Umsetzung gepostet.

    Der Unterschied zwischen Genie und Wahnsinn definiert sich im Erfolg.

  • Alle Schwierigkeiten habe ich noch nicht gelöst, aber das mit den beiden LEDs schon. Ist so ausgeführt wie in #4 von RTFM vorgeschlagen:


    .....

    while True:

    valueLDR=adc.read(adc_channel=1)#A/D Wandler Kanal 1 auslesen (LDR)

    print ("Helligkeit:",valueLDR)

    sleep(2)


    #Wenn die Endlage rechts (auf) nicht erreicht ist:

    if not GPIO.input(10):

    #LDR Wert muss größer als x sein - hell

    if (valueLDR > 2000):

    GPIO.output(38, False)

    GPIO.output(37, True)

    print ("Motor rechts")

    sleep(1)


    #Wenn die Endlage links (ab) nicht erreicht ist:

    if not GPIO.input(11):

    #LDR Wert muss kleiner als x sein -dunkel

    if (valueLDR < 2000):

    GPIO.output(37, False)

    GPIO.output(38, True)

    print ("Motor links")

    sleep(1)


    GPIO.cleanup()


    Derzeit versuche ich noch, die LED bzw. den Motor nur zu aktivieren, wenn die valueLDR min. 1min größer bzw. kleiner dem Schwellwert (2000) ist. Da habe ich zwei Ansätze, die Helligkeit mehrmals in gewissen Abständen zu messen (mittels sleep()), zu addieren und dann einen Mittelwert zu bilden den ich mit einem "soll Mittelwert" vergleiche. Der andere Ansatz ist mit der valueLDR >2000 einen timer zu starten und nach Ablauf nochmal die valueLDE auszulesen - ist der zweite Wert ebenfalls >2000 darf der Motor aktiviert werden - analog zu valueLDR<2000.



    Grüße Jonas!

  • So, habe es mal mit dem Code-Button probiert ;)