Python Forum

Full Version: Does this code need to be so long?
You're currently viewing a stripped down version of our content. View the full version with proper formatting.
Made this timer to go with my son's BattleBots Arena (this one) and intend to build it into the housing of the motorized auger on one side. I got all that hardware figured out, but the code is kinda long. It works, but I just want to see if I can make it simpler.

Here is a video of what I have so far. The duration of the green LED on is going to be changed to a more realistic duration of a fight (line 82). I would watch the video first so you can see what it is doing. The video is this one: here

from machine import Pin, PWM
import time
from time import sleep
#import urequests

ledgreen = Pin(2, Pin.OUT)
ledamber = Pin(5, Pin.OUT)
ledred = Pin(6, Pin.OUT)

buzzerPIN=17
BuzzerObj=PWM(Pin(buzzerPIN))

button = Pin(15, Pin.IN, Pin.PULL_UP)

def buzzer(buzzerPinObject,frequency,sound_duration,silence_duration):
    buzzerPinObject.duty_u16(int(65536*0.2))
    buzzerPinObject.freq(frequency)
    sleep(sound_duration)
    buzzerPinObject.duty_u16(int(65536*0))
    sleep(silence_duration)
ledgreen.on()
time.sleep(.1)
ledred.on()
time.sleep(.1)
ledamber.on()
time.sleep(.2)
ledgreen.off()
time.sleep(.1)
ledred.off()
time.sleep(.1)
ledamber.off()
time.sleep(.2)
ledgreen.on()
time.sleep(.1)
ledred.on()
time.sleep(.1)
ledamber.on()
time.sleep(.2)
ledgreen.off()
time.sleep(.1)
ledred.off()
time.sleep(.1)
ledamber.off()
time.sleep(.2)
ledgreen.on()
time.sleep(.1)
ledred.on()
time.sleep(.1)
ledamber.on()
time.sleep(.1)
time.sleep(.2)
ledgreen.off()
time.sleep(.1)
ledred.off()
time.sleep(.1)
ledamber.off()

while True:
    if not button.value():
        
# Start the timer        
        print('Go!')
        ledgreen.off()
        ledred.off()
        ledamber.on()
        buzzer(BuzzerObj,523,0.5,0.0)
        ledamber.off()
        time.sleep(.2)
        ledamber.on()
        buzzer(BuzzerObj,523,0.5,0.0)
        ledamber.off()
        time.sleep(.2)
        ledamber.on()
        buzzer(BuzzerObj,523,0.5,0.0)
        time.sleep(.2)
        ledamber.off()
        
#  Match starts
        ledgreen.on()
        buzzer(BuzzerObj,987,1.5,0.1)
        # Start power to the relay here
        time.sleep(20)
        ledamber.on()  # Match ends soon!
        time.sleep(5)
        #ledgreen.off()
        
# Match ends
        ledamber.on()
        buzzer(BuzzerObj,523,0.8,0.0)
        ledamber.off()
        time.sleep(.2)
        ledamber.on()
        buzzer(BuzzerObj,523,0.8,0.0)
        ledamber.off()
        time.sleep(.2)
        ledamber.on()
        buzzer(BuzzerObj,523,0.8,0.0)
        ledamber.off()
        time.sleep(.2)
        ledamber.on()
        buzzer(BuzzerObj,523,0.8,0.0)
        ledamber.off()
        time.sleep(.2)
        ledamber.on()
        buzzer(BuzzerObj,523,0.8,0.0)
        time.sleep(.2)
        #ledamber.on()
        ledgreen.off()
        ledred.on()
        # Stop power to the relay here
        buzzer(BuzzerObj,987,3.5,0.1)
        #time.sleep(10)
        ledamber.off()
        time.sleep(5)
        ledred.off()
I totally forgot to demo what lines 21 through 56 do. It basically does a ripple effect with the three LEDs three times. Just for show when the timer gets plugged in. Like a power up confirmation.
An easy way to reduce code is to write a few functions. You repeat this sequence three times followed by sleep(0.2), sleep(0.2) and no sleep.
def light_show():
    ledgreen.on()
    time.sleep(.1)
    ledred.on()
    time.sleep(.1)
    ledamber.on()
    time.sleep(.2)
    ledgreen.off()
    time.sleep(.1)
    ledred.off()
    time.sleep(.1)
    ledamber.off()

for period in (0.2, 0.2, 0):
    light_show()
    sleep(period)
Of a loop. Or a combination of function and loop like this:
def countdown():
    for _ in range(4):
        ledamber.on()
        buzzer(BuzzerObj,523,0.8,0.0)
        ledamber.off()
        time.sleep(.2)
    
    ledamber.on()
    buzzer(BuzzerObj,523,0.8,0.0)
    time.sleep(.2)
    # Leave amber on

    ledgreen.off()
    ledred.on()
    # Stop power to the relay here
    buzzer(BuzzerObj,987,3.5,0.1)
    #time.sleep(10)
    ledamber.off()
    time.sleep(5)
    ledred.off()
That looks like a good idea. Thanks for that.

Shoulda mentioned a few placeholders in my code. Eventually I will have the code power a relay that controls the power to the auger motor. Instead of replacing the batteries too many times, I will use this Pico to control a relay that enables/disables the auger motor at the start and end of the battle! Push the button ->beep beep beep green -> motor starts, etc. Power will come from an external 5VDC source.
(Sep-26-2022, 09:47 PM)duckredbeard Wrote: [ -> ]but the code is kinda long. It works, but I just want to see if I can make it simpler.
Are you looking for constructions like this?
all_leds = [ledgreen, ledamber, ledred]

for i in range(3):
    for led in all_leds:
        led.on
        time.sleep(.1)
    time.sleep(.1)
    for led in all_leds:
        led.off
        time.sleep(.1)
(Instead of lines 21 through 56, for example.)