11

This code does not turn the led on and off.

import  RPi.GPIO as GPIO
import time
GPIO.setmode(GPIO.BCM)
GPIO.setwarnings(False)
GPIO.setup(21,GPIO.OUT)
for number in range(0,10):
    GPIO.output(21,GPIO.LOW)
    time.sleep(1)
    GPIO.output(21,GPIO.HIGH)
GPIO.cleanup()

but when I print out the number in the loop it does work:

import  RPi.GPIO as GPIO
import time
GPIO.setmode(GPIO.BCM)
GPIO.setwarnings(False)
GPIO.setup(21,GPIO.OUT)
for number in range(0,10):
    GPIO.output(21,GPIO.LOW)
    time.sleep(1)
    GPIO.output(21,GPIO.HIGH)
    print(number)
GPIO.cleanup()

Any idea why that is?

Technico.top
  • 1,406
  • 13
  • 20
tazboy
  • 221
  • 2
  • 5

2 Answers2

51

Unroll your loop to understand what's happening here:

for number in range(0,10):
    GPIO.output(21,GPIO.LOW)
    time.sleep(1)
    GPIO.output(21,GPIO.HIGH)

turns into:

    GPIO.output(21,GPIO.LOW)
    time.sleep(1)
    GPIO.output(21,GPIO.HIGH)
    GPIO.output(21,GPIO.LOW)
    time.sleep(1)
    GPIO.output(21,GPIO.HIGH)
    GPIO.output(21,GPIO.LOW)
    time.sleep(1)
    GPIO.output(21,GPIO.HIGH)
    # [and so on]

As you can see, setting the pin low follows (near to) immediately after turning it high. In effect your LED will stay at one state for most of the time (that is, what we can perceive with the naked eye).

Fix it like this (for a 50:50 duty cycle):

for number in range(0,10):
    GPIO.output(21,GPIO.LOW)
    time.sleep(1)
    GPIO.output(21,GPIO.HIGH)
    time.sleep(1)
Ghanima
  • 15,855
  • 15
  • 61
  • 119
  • 2
    It may also be worth noting that the reason print() causes the original code to work is because writing to the screen is an insanely slow process and is essentially acting as the sleep(1) you suggested. – Jacobm001 Jun 08 '17 at 16:43
22

Try to replace your print by a time.sleep(0.05). You may occur this strange behavior as GPIO.output is switched too quickly from HIGH to LOW to be set/detected/seen. Increase/reduce the sleep duration until the program works fine (increase) and fast enough (decrease).

import  RPi.GPIO as GPIO
import time
GPIO.setmode(GPIO.BCM)
GPIO.setwarnings(False)
GPIO.setup(21,GPIO.OUT)
for number in range(0,10):
    GPIO.output(21,GPIO.LOW)
    time.sleep(1)
    GPIO.output(21,GPIO.HIGH)
    time.sleep(0.05)
GPIO.cleanup()
Technico.top
  • 1,406
  • 13
  • 20