Add code for CP basic data structures guide
This commit is contained in:
parent
328752ffb1
commit
995e7fdeb0
4 changed files with 255 additions and 0 deletions
31
CircuitPython_101/basic_data_structures/play_note/code.py
Normal file
31
CircuitPython_101/basic_data_structures/play_note/code.py
Normal file
|
|
@ -0,0 +1,31 @@
|
|||
import time
|
||||
import board
|
||||
import pulseio
|
||||
|
||||
C4 = 261
|
||||
C_SH_4 = 277
|
||||
D4 = 293
|
||||
D_SH_4 = 311
|
||||
E4 = 329
|
||||
F4 = 349
|
||||
F_SH_4 = 369
|
||||
G4 = 392
|
||||
G_SH_4 = 415
|
||||
A4 = 440
|
||||
A_SH_4 = 466
|
||||
B4 = 493
|
||||
|
||||
def play_note(note):
|
||||
if note[0] != 0:
|
||||
pwm = pulseio.PWMOut(board.D12, duty_cycle = 0, frequency=note[0])
|
||||
pwm.duty_cycle = 0x7FFF
|
||||
time.sleep(note[1])
|
||||
if note[0] != 0:
|
||||
pwm.deinit()
|
||||
|
||||
|
||||
a4_quarter = (A4, 0.25)
|
||||
c4_half = (C4, 0.5)
|
||||
|
||||
play_note(a4_quarter)
|
||||
play_note(c4_half)
|
||||
86
CircuitPython_101/basic_data_structures/song_book/code.py
Normal file
86
CircuitPython_101/basic_data_structures/song_book/code.py
Normal file
|
|
@ -0,0 +1,86 @@
|
|||
import time
|
||||
import board
|
||||
import debouncer
|
||||
import busio as io
|
||||
import digitalio
|
||||
import pulseio
|
||||
import adafruit_ssd1306
|
||||
|
||||
i2c = io.I2C(board.SCL, board.SDA)
|
||||
reset_pin = digitalio.DigitalInOut(board.D11)
|
||||
oled = adafruit_ssd1306.SSD1306_I2C(128, 32, i2c, reset=reset_pin)
|
||||
button_select = debouncer.Debouncer(board.D7, mode=digitalio.Pull.UP)
|
||||
button_play = debouncer.Debouncer(board.D9, mode=digitalio.Pull.UP)
|
||||
|
||||
C4 = 261
|
||||
C_SH_4 = 277
|
||||
D4 = 293
|
||||
D_SH_4 = 311
|
||||
E4 = 329
|
||||
F4 = 349
|
||||
F_SH_4 = 369
|
||||
G4 = 392
|
||||
G_SH_4 = 415
|
||||
A4 = 440
|
||||
A_SH_4 = 466
|
||||
B4 = 493
|
||||
|
||||
songbook = {'Twinkle Twinkle': [(C4, 0.5), (C4, 0.5), (G4, 0.5), (G4, 0.5), (A4, 0.5), (A4, 0.5), (G4, 1.0), (0, 0.5),
|
||||
(F4, 0.5), (F4, 0.5), (E4, 0.5), (E4, 0.5), (D4, 0.5), (D4, 0.5), (C4, 0.5), (0, 0.5),
|
||||
(G4, 0.5), (G4, 0.5), (F4, 0.5), (F4, 0.5), (E4, 0.5), (E4, 0.5), (D4, 0.5), (0, 0.5),
|
||||
(G4, 0.5), (G4, 0.5), (F4, 0.5), (F4, 0.5), (E4, 0.5), (E4, 0.5), (D4, 0.5), (0, 0.5),
|
||||
(C4, 0.5), (C4, 0.5), (G4, 0.5), (G4, 0.5), (A4, 0.5), (A4, 0.5), (G4, 1.0), (0, 0.5),
|
||||
(F4, 0.5), (F4, 0.5), (E4, 0.5), (E4, 0.5), (D4, 0.5), (D4, 0.5), (C4, 0.5), (0, 0.5)],
|
||||
|
||||
'ItsyBitsy Spider': [(G4, 0.5), (C4, 0.5), (C4, 0.5), (C4, 0.5), (D4, 0.5), (E4, 0.5), (E4, 0.5), (E4, 0.5), (D4, 0.5), (C4, 0.5), (D4, 0.5), (E4, 0.5), (C4, 0.5), (0, 0.5),
|
||||
(E4, 0.5), (E4, 0.5), (F4, 0.5), (G4, 0.5), (G4, 0.5), (F4, 0.5), (E4, 0.5), (F4, 0.5), (G4, 0.5), (E4, 0.5), (0, 0.5)],
|
||||
|
||||
'Old MacDonald': [(G4, 0.5), (G4, 0.5), (G4, 0.5), (D4, 0.5), (E4, 0.5), (E4, 0.5), (D4, 0.5), (0, 0.5),
|
||||
(B4, 0.5), (B4, 0.5), (A4, 0.5), (A4, 0.5), (G4, 0.5), (0, 0.5),
|
||||
(D4, 0.5), (G4, 0.5), (G4, 0.5), (G4, 0.5), (D4, 0.5), (E4, 0.5), (E4, 0.5), (D4, 0.5), (0, 0.5),
|
||||
(B4, 0.5), (B4, 0.5), (A4, 0.5), (A4, 0.5), (G4, 0.5), (0, 0.5),
|
||||
(D4, 0.5), (D4, 0.5), (G4, 0.5), (G4, 0.5), (G4, 0.5), (D4, 0.5), (D4, 0.5), (G4, 0.5), (G4, 0.5), (G4, 0.5), (0, 0.5),
|
||||
(G4, 0.5), (G4, 0.5), (G4, 0.5), (G4, 0.5), (G4, 0.5), (G4, 0.5), (0, 0.5),
|
||||
(G4, 0.5), (G4, 0.5), (G4, 0.5), (G4, 0.5), (G4, 0.5), (G4, 0.5), (0, 0.5),
|
||||
(G4, 0.5), (G4, 0.5), (G4, 0.5), (D4, 0.5), (E4, 0.5), (E4, 0.5), (D4, 0.5), (0, 0.5),
|
||||
(B4, 0.5), (B4, 0.5), (A4, 0.5), (A4, 0.5), (G4, 0.5), (0, 0.5)]
|
||||
}
|
||||
|
||||
def play_note(note):
|
||||
if note[0] != 0:
|
||||
pwm = pulseio.PWMOut(board.D12, duty_cycle = 0, frequency=note[0])
|
||||
pwm.duty_cycle = 0x7FFF
|
||||
time.sleep(note[1])
|
||||
if note[0] != 0:
|
||||
pwm.deinit()
|
||||
|
||||
|
||||
def play_song(songname):
|
||||
for note in songbook[songname]:
|
||||
play_note(note)
|
||||
|
||||
|
||||
def update(songnames, selected):
|
||||
oled.fill(0)
|
||||
line = 0
|
||||
for songname in songnames:
|
||||
if line == selected:
|
||||
oled.text(">", 0, line * 8)
|
||||
oled.text(songname, 10, line * 8)
|
||||
line += 1
|
||||
oled.show()
|
||||
|
||||
|
||||
selected_song = 0
|
||||
song_names = sorted(list(songbook.keys()))
|
||||
while True:
|
||||
button_select.update()
|
||||
button_play.update()
|
||||
update(song_names, selected_song)
|
||||
if button_select.fell:
|
||||
print("select")
|
||||
selected_song = (selected_song + 1) % len(songbook)
|
||||
elif button_play.fell:
|
||||
print("play")
|
||||
play_song(song_names[selected_song])
|
||||
|
||||
105
CircuitPython_101/basic_data_structures/song_book/debouncer.py
Normal file
105
CircuitPython_101/basic_data_structures/song_book/debouncer.py
Normal file
|
|
@ -0,0 +1,105 @@
|
|||
"""
|
||||
The MIT License (MIT)
|
||||
|
||||
Copyright (c) 2018 Dave Astels
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in
|
||||
all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
THE SOFTWARE.
|
||||
|
||||
--------------------------------------------------------------------------------
|
||||
Debounce an input pin.
|
||||
"""
|
||||
|
||||
import time
|
||||
import digitalio
|
||||
|
||||
class Debouncer(object):
|
||||
"""Debounce an input pin"""
|
||||
|
||||
DEBOUNCED_STATE = 0x01
|
||||
UNSTABLE_STATE = 0x02
|
||||
CHANGED_STATE = 0x04
|
||||
|
||||
|
||||
def __init__(self, pin, mode=None, interval=0.010):
|
||||
"""Make am instance.
|
||||
:param int pin: the pin (from board) to debounce
|
||||
:param int mode: digitalio.Pull.UP or .DOWN (default is no pull up/down)
|
||||
:param int interval: bounce threshold in seconds (default is 0.010, i.e. 10 milliseconds)
|
||||
"""
|
||||
self.state = 0x00
|
||||
self.pin = digitalio.DigitalInOut(pin)
|
||||
self.pin.direction = digitalio.Direction.INPUT
|
||||
if mode != None:
|
||||
self.pin.pull = mode
|
||||
if self.pin.value:
|
||||
self.__set_state(Debouncer.DEBOUNCED_STATE | Debouncer.UNSTABLE_STATE)
|
||||
self.previous_time = 0
|
||||
if interval is None:
|
||||
self.interval = 0.010
|
||||
else:
|
||||
self.interval = interval
|
||||
|
||||
|
||||
def __set_state(self, bits):
|
||||
self.state |= bits
|
||||
|
||||
|
||||
def __unset_state(self, bits):
|
||||
self.state &= ~bits
|
||||
|
||||
|
||||
def __toggle_state(self, bits):
|
||||
self.state ^= bits
|
||||
|
||||
|
||||
def __get_state(self, bits):
|
||||
return (self.state & bits) != 0
|
||||
|
||||
|
||||
def update(self):
|
||||
"""Update the debouncer state. Must be called before using any of the properties below"""
|
||||
self.__unset_state(Debouncer.CHANGED_STATE)
|
||||
current_state = self.pin.value
|
||||
if current_state != self.__get_state(Debouncer.UNSTABLE_STATE):
|
||||
self.previous_time = time.monotonic()
|
||||
self.__toggle_state(Debouncer.UNSTABLE_STATE)
|
||||
else:
|
||||
if time.monotonic() - self.previous_time >= self.interval:
|
||||
if current_state != self.__get_state(Debouncer.DEBOUNCED_STATE):
|
||||
self.previous_time = time.monotonic()
|
||||
self.__toggle_state(Debouncer.DEBOUNCED_STATE)
|
||||
self.__set_state(Debouncer.CHANGED_STATE)
|
||||
|
||||
|
||||
@property
|
||||
def value(self):
|
||||
"""Return the current debounced value of the input."""
|
||||
return self.__get_state(Debouncer.DEBOUNCED_STATE)
|
||||
|
||||
|
||||
@property
|
||||
def rose(self):
|
||||
"""Return whether the debounced input went from low to high at the most recent update."""
|
||||
return self.__get_state(self.DEBOUNCED_STATE) and self.__get_state(self.CHANGED_STATE)
|
||||
|
||||
|
||||
@property
|
||||
def fell(self):
|
||||
"""Return whether the debounced input went from high to low at the most recent update."""
|
||||
return (not self.__get_state(self.DEBOUNCED_STATE)) and self.__get_state(self.CHANGED_STATE)
|
||||
33
CircuitPython_101/basic_data_structures/song_list/code.py
Normal file
33
CircuitPython_101/basic_data_structures/song_list/code.py
Normal file
|
|
@ -0,0 +1,33 @@
|
|||
import time
|
||||
import board
|
||||
import pulseio
|
||||
|
||||
C4 = 261
|
||||
C_SH_4 = 277
|
||||
D4 = 293
|
||||
D_SH_4 = 311
|
||||
E4 = 329
|
||||
F4 = 349
|
||||
F_SH_4 = 369
|
||||
G4 = 392
|
||||
G_SH_4 = 415
|
||||
A4 = 440
|
||||
A_SH_4 = 466
|
||||
B4 = 493
|
||||
|
||||
twinkle = [(C4, 0.5), (C4, 0.5), (G4, 0.5), (G4, 0.5), (A4, 0.5), (A4, 0.5), (G4, 0.5), (0, 0.5),
|
||||
(F4, 0.5), (F4, 0.5), (E4, 0.5), (E4, 0.5), (D4, 0.5), (D4, 0.5), (C4, 0.5)]
|
||||
|
||||
def play_note(note):
|
||||
if note[0] != 0:
|
||||
pwm = pulseio.PWMOut(board.D12, duty_cycle = 0, frequency=note[0])
|
||||
pwm.duty_cycle = 0x7FFF
|
||||
time.sleep(note[1])
|
||||
if note[0] != 0:
|
||||
pwm.deinit()
|
||||
|
||||
def play_song(song):
|
||||
for note in song:
|
||||
play_note(note)
|
||||
|
||||
play_song(twinkle)
|
||||
Loading…
Reference in a new issue