Skip to content

Instantly share code, notes, and snippets.

@jweinst1
Created October 7, 2021 16:12
Show Gist options
  • Save jweinst1/1cd52d7f037197e7efb146d2eb42cae5 to your computer and use it in GitHub Desktop.
Save jweinst1/1cd52d7f037197e7efb146d2eb42cae5 to your computer and use it in GitHub Desktop.
create an 8 bit sound wave file in python
import math
import wave
import struct
# Audio will contain a long list of samples (i.e. floating point numbers describing the
# waveform). If you were working with a very long sound you'd want to stream this to
# disk instead of buffering it all in memory list this. But most sounds will fit in
# memory.
audio = []
sample_rate = 44100
# generate saw_tooth waves
def saw_wave(x, h, w):
total_dist = (4 * h) + ( 2 * w)
clamped = x % total_dist
segment = total_dist / 6
if clamped < segment:
return clamped
elif clamped < (segment * 2):
return h
elif clamped < (segment * 3):
return h - (clamped - (segment * 2))
elif clamped < (segment * 4):
return 0 - (clamped - (segment * 3))
elif clamped < (segment * 5):
return -h
else:
return -h + (clamped - (segment * 5))
def create_waves(h, w):
global audio
for x in range(sample_rate):
audio.append(math.trunc(saw_wave(x, h, w)))
def save_wav(file_name):
# Open up a wav file
wav_file=wave.open(file_name,"w")
# wav params
nchannels = 1
sampwidth = 1
# 44100 is the industry standard sample rate - CD quality. If you need to
# save on file size you can adjust it downwards. The stanard for low quality
# is 8000 or 8kHz.
nframes = len(audio)
comptype = "NONE"
compname = "not compressed"
wav_file.setparams((nchannels, sampwidth, sample_rate, nframes, comptype, compname))
for sample in audio:
wav_file.writeframes(struct.pack('b', sample))
wav_file.close()
return
create_waves(50, 4)
create_waves(40, 4)
create_waves(30, 4)
create_waves(100, 20)
create_waves(110, 20)
save_wav("output.wav")
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment