Icold
Icold

Reputation: 21

How to write frames from list to the 1 channel wav file correctly, using python.wave?

import wave

audio_file = wave.open('1.wav', 'rb')
frames = audio_file.readframes(audio_file.getnframes())
audio_file.close()

binary_data = list(frames)

output_file = wave.open('output.wav', 'wb')
output_file.setparams((1, 2, 48000, len(binary_data), 'NONE', 'not compressed'))

for value in binary_data:
    byt = value.to_bytes(2)
    output_file.writeframes(value.to_bytes(2))

output_file.close()

and i got noise in my output file

I want to just understand how to write data from frames transformed to list in wav file correctly, using python.wave.

Upvotes: 0

Views: 53

Answers (1)

PalaceSwitcher
PalaceSwitcher

Reputation: 1

When you use list on a bytes object, it turns every individual byte into an integer, which garbles the input frame data if the input WAV file is wider than 8 bits. A much simpler and faster way of doing this would be to write the frames directly to the output file, like this:

output_file.writeframes(frames)

However, this makes the resulting file either too slow or too fast since Python's wave module can't properly resample WAV files on its own. A better option would be to use scipy instead.

import numpy as np
from scipy.io import wavfile
import scipy.signal as sg

sample_rate, data = wavfile.read('1.wav')

samples = round(len(data) * 48000.0 / sample_rate) #Sample count
new_data = np.array(sg.resample(data, samples), dtype=np.int16) #Get sound data as 16-bit PCM
mono_data = np.array((new_data.sum(axis=1) / 2), dtype=np.int16) #Mix down to mono

wavfile.write('output.wav', 48000, mono_data)

Upvotes: 0

Related Questions