User avatar
MarkHaysHarris777
Posts: 1820
Joined: Mon Mar 23, 2015 7:39 am
Location: Rochester, MN
Contact: Website

Programable PWM Oscillators - Using the PI to Play Music

Thu Jun 02, 2016 9:58 am

musical_pi.jpg
listening to pwm via 8 ohm speaker
musical_pi.jpg (39.11 KiB) Viewed 1070 times
In the pic above I have connected an 8 ohm 1/2 watt loud-speaker in series with a 16v 100mf cap between ground and the channel 0 pwm pin12 {GPIO18}. I find it interesting that with this simple setup you can hear the pwm working; and, because you can set the frequency with a float, you can program the pwm oscillators to play musical scales in tune (more or less). ;)

I'll try to upload the audio later... for now, the code below will generate diatonic scales in alternate third patterns (in tune) for several keys (as long as you keep the frequencies low on the keyboard!

The setup is straight-forward, just follow the pic... be careful to make sure the little negative stripe on the electrolytic cap goes to ground!

To run the code use:

Code: Select all

./concert_scale.sh  4  1  .2  .1
The first parm is the note offset (pick a key), the second parm is the register, and the last two parms are the hold time, and release time of each note.

For some reason I don't understand yet, the PWM oscillators are noisy (irritatingly dirty) and at upper frequencies they aren't very precise... but down lower they're not bad for experimenting with sound; even with this unfiltered non amplified setup pictured.... a truly inexpensive and fun experiment !

edit: When I have used PWM in the past on the PI, I thought I would see small 'glitches' from time to time in the LEDs, or in the motors... well, they're there! You can hear them very clearly ... don't know what's going on, but I'm sure its the reason for the dirty sound quality in the stereo output of the composite video (if its based on the pwm, and I think it must be).


concert_scale.sh

Code: Select all

#!/usr/bin/python
#
# concert_scale.sh
#
#  Mark H. Harris
#  v.01.b
#  06-02-2016
#

## Import the necessary header modules
from time import sleep
from sys import argv
import RPi.GPIO as GPIO

## Setup the GPIO for PWM on pin12 {GPIO18}
GPIO.setmode(GPIO.BOARD)
GPIO.setup(12, GPIO.OUT)
p = GPIO.PWM(12, 220)
p.stop()

## Determine the intervals of the chromatic scale
chromatic=[]
ss = 2.0 ** (1.0 / 12)
ssc = 1 
for n in range(36):
    ssc*=ss
    chromatic.append(ssc)

## Build list of diatonic intervals for chromatic indexing
base_offset=int(argv[1])
diatonic=[]
dia_index=[0,2,4,5,7,9,10,12,14,16,17,19,21,22,24]
for ndx in dia_index:
    diatonic.append(ndx+base_offset)

## Build the concert diatonic scale  164.8=E
S_diatonic=[]
for note in diatonic:
    S_diatonic.append(chromatic[note]*164.8)

## Build tune note index codex
h_tune = [3,5,4,6,5,7,6,4,5,3,4,2,3,3,3]
yankee = [3,3,4,5,3,5,4,0,3,3,4,5,3,3,2,2,3,3,4,5,6,5,4,3,2,0,1,2,3,3,3,3]

## Build tune3 ... up and down the half-scale in alternate thirds
tune3 = []
for xnote in h_tune:
    tune3.append(S_diatonic[xnote])

## Build yankee doodle ... 
doodle = []
for xnote in yankee:
    doodle.append(S_diatonic[xnote])

## Define the 'scale playing' function
def scale(tune, register, duty, on_delay, rel_delay):
    for note in tune:
        p.ChangeFrequency(note*register)
        p.start(duty)
        sleep(on_delay)
        p.stop()
        sleep(rel_delay)

## Play the concert scale : scale(tune, 2, 1, 50, .2 .1 )
#    command line:  ./concert_scale.sh 2 1 .2 .1 
#
scale(doodle, int(argv[2]), 50, float(argv[3]), float(argv[4]))
sleep(.7)
scale(tune3, int(argv[2]), 50, float(argv[3]), float(argv[4]))
sleep(.7)

## Cleanup the GPIO stuff...
GPIO.cleanup()

marcus
marcus
:ugeek:

User avatar
MarkHaysHarris777
Posts: 1820
Joined: Mon Mar 23, 2015 7:39 am
Location: Rochester, MN
Contact: Website

Re: Programable PWM Oscillators - Using the PI to Play Music

Thu Jun 02, 2016 1:57 pm

edit: OP updated the code posting above {final}

I expanded the scale a bit, to allow for all keys 0 - 11, and now this little diddy plays Yankee-Doodle...

... I know its cheezy; but it will play it in every key!

(stick to register 1, all keys sound basically decent in the first register)

marcus
marcus
:ugeek:

Return to “Graphics, sound and multimedia”