Skip to content

Instantly share code, notes, and snippets.

@idriszmy
Last active February 27, 2024 13:24
Show Gist options
  • Star 4 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save idriszmy/47ce97a34c07a9b3da79d4121269a40b to your computer and use it in GitHub Desktop.
Save idriszmy/47ce97a34c07a9b3da79d4121269a40b to your computer and use it in GitHub Desktop.
Play MP3 files from SD card using Maker Pi Pico and CircuitPython
"""
Play MP3 files from SD card using Maker Pi Pico and CircuitPython
Maker Pi Pico
- https://my.cytron.io/p-maker-pi-pico
6W Stereo USB Powered 3.5mm Jack Speaker
- https://my.cytron.io/p-6w-stereo-usb-powered-3-5mm-jack-speaker-black
Dual 18650 Dual Output 3.3V and 5V USB Module (optional)
- https://my.cytron.io/c-lithium-ion-rechargeable-battery-and-charger
3.7V 2000mAh Li-Ion Battery
- https://my.cytron.io/p-3.7v-2000mah-li-ion-battery
References:
- https://learn.adafruit.com/adafruit-microsd-spi-sdio
Last Modified: 5 Dec 2021
"""
import os
import time
import board
import digitalio
import busio
import sdcardio
import storage
from audiomp3 import MP3Decoder # pylint: disable=wrong-import-position
try:
from audioio import AudioOut
except ImportError:
try:
from audiopwmio import PWMAudioOut as AudioOut
except ImportError:
pass # not always supported by every board!
led = digitalio.DigitalInOut(board.LED)
led.direction = digitalio.Direction.OUTPUT
button1 = digitalio.DigitalInOut(board.GP20)
button1.direction = digitalio.Direction.INPUT
button2 = digitalio.DigitalInOut(board.GP21)
button2.direction = digitalio.Direction.INPUT
spi = busio.SPI(board.GP10, board.GP11, board.GP12)
sd = sdcardio.SDCard(spi, board.GP15)
vfs = storage.VfsFat(sd)
storage.mount(vfs, '/sd')
mp3files = sorted("/sd/" + filename for filename in os.listdir("/sd")
if filename.lower().endswith("mp3"))
# You have to specify some mp3 file when creating the decoder
mp3 = open(mp3files[0], "rb")
decoder = MP3Decoder(mp3)
audio = AudioOut(board.GP18, right_channel=board.GP19)
while True:
if button1.value == False:
filename = mp3files[0]
print("Playing", filename)
# Updating the .file property of the existing decoder
# helps avoid running out of memory (MemoryError exception)
decoder.file = open(filename, "rb")
audio.play(decoder)
while button1.value == False:
continue
while audio.playing:
if button1.value == False:
print("Stop", filename)
audio.stop()
while button1.value == False:
continue
break
if button2.value == False:
filename = mp3files[1]
print("Playing", filename)
# Updating the .file property of the existing decoder
# helps avoid running out of memory (MemoryError exception)
decoder.file = open(filename, "rb")
audio.play(decoder)
while button2.value == False:
continue
while audio.playing:
if button2.value == False:
print("Stop", filename)
audio.stop()
while button2.value == False:
continue
break
@zen375dragon
Copy link

zen375dragon commented Oct 20, 2022

Do I have to replace the "rb" with the mp3 file name? It says:
Traceback (most recent call last):
File "", line 55, in
ValueError: Invalid mode

How do I fix this?

@KjellConnelly
Copy link

@zen375dragon Old question, but if you stopped on this project, rb stands for Read Binary. This just means that when you open the mp3 file, you're only reading it, not writing to the file, so you leave that alone.

Error on line 55 means you don't have any mp3 files found at that path. Path should be sd/whatever.mp3. This code looks for all files that end with .mp3 in the sd folder. Since none were found, that's why you got the error.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment