Skip to content

Instantly share code, notes, and snippets.

@ShawnHymel
Created October 28, 2019 18:28
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save ShawnHymel/312537668d940999ec0d35bba9c2d44a to your computer and use it in GitHub Desktop.
Save ShawnHymel/312537668d940999ec0d35bba9c2d44a to your computer and use it in GitHub Desktop.
Spoopy Poopy
# Spoopy Poopy
# Makes a farting pumpkin!
# Author: Shawn Hymel
# Date: October 19, 2019
# See pins below to figure out how to connect peripherals
# Tested on Adafruit Feather M0 Express
# License: Beerware - As long as you retain this notice you
# can do whatever you want with this stuff. If we meet some day, and you think
# this stuff is worth it, you can buy me a beer in return.
import time
import board
import neopixel
import audioio
import random
from digitalio import DigitalInOut, Direction, Pull
# Parameters
cooloff_time = 5 # seconds
fog_warmup_delay = 0.1 # Time (sec) to warm ecig before releasing payload
num_pixels = 8 # Pixels in NeoPixel strip
neopixel_brightness = 0.8
neopixel_flicker_scaler = 0.3
flicker_delay_min = 0.01 # Seconds
flicker_delay_max = 0.100 # Seconds
flame_r = 226
flame_g = 121
flame_b = 35
# Pins
onboard_neopixel_pin = board.NEOPIXEL
status_led_pin = board.D13
neopixel_strip_pin = board.D9
pir_sensor_pin = board.D6
amp_shd_pin = board.D5
audio_out_pin = board.A0
fog_pin = board.A1
pump_pin = board.A2
# Onboard NeoPixel
led_rgb = neopixel.NeoPixel(onboard_neopixel_pin, 1)
led_rgb.brightness = 0.3
led_rgb[0] = (0, 0, 0)
# Status LEDs
status_led = DigitalInOut(status_led_pin)
status_led.direction = Direction.OUTPUT
status_led.value = False
# NeoPixel strip
pixels = neopixel.NeoPixel(neopixel_strip_pin, num_pixels, \
brightness=neopixel_brightness, auto_write=False, pixel_order=neopixel.GRB)
for i in range(0, num_pixels):
pixels[i] = (0, 0, 0)
pixels.show()
# PIR sensor
pir = DigitalInOut(pir_sensor_pin)
pir.direction = Direction.INPUT
# Audio amp shutdown control
amp_shd = DigitalInOut(amp_shd_pin)
amp_shd.direction = Direction.OUTPUT
amp_shd.value = False
# Fog (e-cig) control pin
fog = DigitalInOut(fog_pin)
fog.direction = Direction.OUTPUT
fog.value = False
# Air pump control pin
pump = DigitalInOut(pump_pin)
pump.direction = Direction.OUTPUT
pump.value = False
# Load audio file
wave_file = open("fart.wav", "rb")
wave = audioio.WaveFile(wave_file)
audio = audioio.AudioOut(audio_out_pin)
# Globals
pir_prev_state = False
#-------------------------------------------------------------------------------
# Functions
#-------------------------------------------------------------------------------
# Credit to mysecretstache for flicker effect
# https://codebender.cc/sketch:271084#Neopixel%20Flames.ino
def NeoFlicker():
for i in range(0, num_pixels):
# Set flicker vlaues
flicker = random.randint(0, 55)
r = flame_r - flicker
g = flame_g - flicker
b = flame_b - flicker
# Apply brightness multiplier
r = int(neopixel_flicker_scaler * r)
g = int(neopixel_flicker_scaler * g)
b = int(neopixel_flicker_scaler * b)
# Clamp values
r = max(min(r, 255), 0)
g = max(min(g, 255), 0)
b = max(min(b, 255), 0)
pixels[i] = (r, g, b)
pixels.show()
# Set NeoPixel strip to one color
def SetNeoColor(r, g, b):
for i in range(0, num_pixels):
pixels[i] = (r, g, b)
pixels.show()
#-------------------------------------------------------------------------------
# Main
#-------------------------------------------------------------------------------
timestamp = time.monotonic()
while True:
# Show PIR status on onboard NeoPixel
if ( True == pir.value ):
led_rgb[0] = (100, 0, 0)
else:
led_rgb[0] = (0, 0, 0)
# See if we're outside our "cooling off" period
if ( time.monotonic() - timestamp >= cooloff_time ):
# Show that we're armed
status_led.value = True
# Determine if PIR tripped
pir_state = pir.value
if (False == pir_prev_state) and (True == pir_state):
# Reset cooling off timer and status LEDs
timestamp = time.monotonic()
status_led.value = False
# --- Commence flatulence sequence ---
# Warm up ecig resistive element
print("Pressure is building...")
fog.value = True
time.sleep(fog_warmup_delay)
# Release the Kraken! Turn on onboard NeoPixel, run pump, play audio
print("I can't hold it any longer!")
SetNeoColor(255, 0, 0)
pump.value = True
amp_shd.value = True
audio.play(wave)
while audio.playing:
time.sleep(0.05)
pass
# Turn off audio amp, pump, ecig, and LEDs
print("Aaaaahhhhh...")
amp_shd.value = False
fog.value = False
pump.value = False
led_rgb[0] = (0, 0, 0)
SetNeoColor(0, 0, 0)
# Save state
pir_prev_state = pir_state
# Do flicker effect
NeoFlicker()
time.sleep(random.uniform(flicker_delay_min, flicker_delay_max))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment