Adding code and audio files for talking adabot clock

Adding code and wave files for Talking Adabot Clock project
This commit is contained in:
Liz 2023-08-25 11:30:03 -04:00
parent 70d280aae2
commit aa6da23a32
46 changed files with 175 additions and 0 deletions

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

View file

@ -0,0 +1,175 @@
# SPDX-FileCopyrightText: 2023 Liz Clark for Adafruit Industries
#
# SPDX-License-Identifier: MIT
import os
import time
import board
import audiocore
import audiobusio
import audiomixer
import pwmio
import adafruit_ds3231
from digitalio import DigitalInOut, Direction, Pull
import neopixel
import keypad
# enable external power pin
# provides power to the external components
external_power = DigitalInOut(board.EXTERNAL_POWER)
external_power.direction = Direction.OUTPUT
external_power.value = True
# setup external button pin as a keypad object
key = keypad.Keys((board.EXTERNAL_BUTTON,), value_when_pressed=False, pull=True)
# neopixel mouth setup
pixels = neopixel.NeoPixel(board.EXTERNAL_NEOPIXELS, 8, auto_write=True, brightness=0.2)
blue = (0, 0, 255)
off = (0, 0, 0)
pixels.fill(off)
# rtc module
i2c = board.I2C()
rtc = adafruit_ds3231.DS3231(i2c)
# pylint: disable-msg=using-constant-test
if False: # change to True if you want to set the time!
# year, mon, date, hour, min, sec, wday, yday, isdst
t = time.struct_time((2023, 8, 22, 16, 47, 00, 1, -1, -1))
# you must set year, mon, date, hour, min, sec and weekday
# yearday is not supported, isdst can be set but we don't do anything with it at this time
print("Setting time to:", t) # uncomment for debugging
rtc.datetime = t
print()
# pylint: enable-msg=using-constant-test
# sound arrays
bookend_sounds = []
hour_sounds = []
min_sounds = []
clock_queue = []
# bring in the audio files and put them into the different arrays
for filename in os.listdir('/clock_sounds'):
if filename.lower().endswith('.wav') and not filename.startswith('.'):
if filename.startswith('h'):
hour_sounds.append("/clock_sounds/"+filename)
elif filename.startswith('m'):
min_sounds.append("/clock_sounds/"+filename)
else:
bookend_sounds.append("/clock_sounds/"+filename)
# sort the arrays alphabetically
bookend_sounds.sort()
hour_sounds.sort()
min_sounds.sort()
print(hour_sounds)
print(min_sounds)
print(bookend_sounds)
# i2s amp setup with mixer
audio = audiobusio.I2SOut(board.I2S_BIT_CLOCK, board.I2S_WORD_SELECT, board.I2S_DATA)
mixer = audiomixer.Mixer(voice_count=1, sample_rate=22050, channel_count=1,
bits_per_sample=16, samples_signed=True)
audio.play(mixer)
mixer.voice[0].level = 0.5
# function for queueing wave files
def open_audio(wavs, num):
n = wavs[num]
f = open(n, "rb")
w = audiocore.WaveFile(f)
clock_queue.append(w)
return w
# queue boot up sound to play before going into the loop
boot_sound = open_audio(bookend_sounds, 2)
# function for gathering clock audio files
def prep_clock(hour_num, minute_num):
# queues "the time is.."
open_audio(bookend_sounds, 1)
# convert 24 hour time from RTC to 12 hour
if hour_num > 12:
hour_num = hour_num - 12
# set PM
ampm_num = 3
# otherwise its the morning
else:
# set AM
ampm_num = 0
# queueing hour, single digit waves have a 0 before the number
if hour_num <= 9:
print(hour_num)
h = hour_sounds.index(f'/clock_sounds/h0{hour_num}.wav')
else:
print(hour_num)
h = hour_sounds.index(f'/clock_sounds/h{hour_num}.wav')
# open wave file for the hour
open_audio(hour_sounds, h)
# if the minute is divisible by 10 (10, 20, 30, etc)
if minute_num % 10 == 0:
# check for on the hour (1:00, 2:00, etc)
if minute_num == 0:
m = min_sounds.index(f'/clock_sounds/m{minute_num}0.wav')
else:
m = min_sounds.index(f'/clock_sounds/m{minute_num}.wav')
print(minute_num)
# individual wave files exist for 1-19
elif minute_num <= 19:
print(minute_num)
# if it's a single digit number, bring in the "oh" wave file
if minute_num <= 9:
mm = min_sounds.index(f'/clock_sounds/m0x.wav')
open_audio(min_sounds, mm)
m = min_sounds.index(f'/clock_sounds/m{minute_num}.wav')
# otherwise, for minutes 21-59 that are not divisible by 10
else:
# we need to seperate the minutes digits
digits = list(map(int, str(minute_num)))
#print(digits)
# get the tens spot (30, 40, etc)
mm = min_sounds.index(f'/clock_sounds/m{digits[0]}x.wav')
# add the wav to the array
open_audio(min_sounds, mm)
# get the ones spot (1, 2, etc)
m = min_sounds.index(f'/clock_sounds/m{digits[1]}.wav')
# combined it will say ex: "30...5"
# add the wav to the array
open_audio(min_sounds, m)
# finish with am or pm
open_audio(bookend_sounds, ampm_num)
# initial RTC read
t = rtc.datetime
print(t)
# say the time on boot
pixels.fill(blue)
prep_clock(t.tm_hour, t.tm_min)
for i in range(len(clock_queue)):
mixer.voice[0].play(clock_queue[i], loop=False)
while mixer.playing:
pass
# clear the audio file queue
clock_queue.clear()
pixels.fill(off)
while True:
# listen for button input
event = key.events.get()
if event:
# if the button is pressed
if event.pressed:
# read from RTC module
t = rtc.datetime
# turn on neopixels
pixels.fill(blue)
# gather the audio files based on RTC reading
prep_clock(t.tm_hour, t.tm_min)
# play through each wave one by one
for i in range(len(clock_queue)):
mixer.voice[0].play(clock_queue[i], loop=False)
while mixer.playing:
pass
# afterwards clear out the queue
clock_queue.clear()
# turn off neopixels
pixels.fill(off)