mirror of
https://github.com/trudnai/Steve2.git
synced 2024-12-30 14:29:56 +00:00
60 lines
2.8 KiB
Python
Executable File
60 lines
2.8 KiB
Python
Executable File
#!/usr/local/bin/python3
|
||
|
||
### Convert SPKR Buffer to WAV -- (c) by Tamas Rudnai 2022
|
||
###
|
||
### This utility convert SPKR buffer output to an uncompressed WAV file
|
||
###
|
||
### Purpose is that sound generation can be analyzed by audio editor - Audacity for example
|
||
###
|
||
|
||
import os
|
||
import sys
|
||
import struct
|
||
|
||
# binpath = '/Users/trudnai/Library/Containers/com.trudnai.steveii/Data/'
|
||
# binfilename = binpath + 'steve2_audio_debug.bin'
|
||
|
||
def convert_bin_to_audio(filename):
|
||
data_size = os.path.getsize(filename)
|
||
channels = 2
|
||
sample_rate = 1023000 # 192000 # must be the same as in speaker.c : spkr_sample_rate
|
||
bits_per_sample = 16
|
||
header_size = 44
|
||
|
||
with open( filename, 'rb') as binfile:
|
||
wavfilename = os.path.splitext( os.path.basename(filename) )[0] + '.wav'
|
||
|
||
with open( wavfilename, 'wb+') as wavfile:
|
||
# WAV HEADER
|
||
wavfile.write( 'RIFF'.encode() ) # Marks the file as a riff file. Characters are each 1 byte long
|
||
wavfile.write( struct.pack('I', data_size + header_size ) ) # Size of the overall file - 8 bytes, in bytes (32-bit integer). Typically you’d fill this in after creation
|
||
wavfile.write( 'WAVE'.encode() ) # File Type Header. For our purposes, it always equals “WAVE”
|
||
|
||
# FMT HEADER
|
||
wavfile.write( 'fmt '.encode() ) # Format chunk marker. Includes trailing null (tr: Space works, null don't)
|
||
wavfile.write( struct.pack('I', 16 ) ) # Length of format data as listed above
|
||
|
||
# FMT DATA
|
||
wavfile.write( struct.pack('H', 1 ) ) # Type of format (1 is PCM) - 2 byte integer
|
||
wavfile.write( struct.pack('H', channels ) ) # Number of Channels - 2 byte integer
|
||
wavfile.write( struct.pack('I', sample_rate ) ) # Sample Rate - 32 byte integer. Common values are 44100 (CD), 48000 (DAT). Sample Rate = Number of Samples per second, or Hertz
|
||
wavfile.write( struct.pack('I', int(sample_rate * bits_per_sample * channels / 8) ) ) # (Sample Rate * BitsPerSample * Channels) / 8
|
||
wavfile.write( struct.pack('H', 4 ) ) # 0: (BitsPerSample * Channels) / 8
|
||
# 1: 8 bit mono2
|
||
# 2: 8 bit stereo
|
||
# 3: 16 bit mono
|
||
# 4: 16 bit stereo
|
||
wavfile.write( struct.pack('H', bits_per_sample ) ) # Bits per sample
|
||
|
||
# DATA HEADER
|
||
wavfile.write( 'data'.encode() ) # “data” chunk header. Marks the beginning of the data section
|
||
wavfile.write( struct.pack('I', data_size ) ) # Size of the data section
|
||
|
||
# // WAV DATA
|
||
wavfile.write( binfile.read() )
|
||
|
||
for filename in sys.argv:
|
||
convert_bin_to_audio(filename)
|
||
|
||
|