Module audioio.audiowriter
Writing numpy arrays of floats to audio files.
write_audio()
: write audio data to file.available_formats()
: audio file formats supported by any of the installed audio modules.available_encodings()
: encodings of an audio file format supported by any of the installed audio modules.format_from_extension()
: deduce audio file format from file extension.
The data to be written are 1-D or 2-D numpy arrays of floats ranging between -1 and 1 with first axis time and second axis channel.
For support of more audio formats, you might need to install additional packages. See installation for further instructions.
For a demo, run the script as:
python -m audioio.audiowriter
Expand source code
"""
Writing numpy arrays of floats to audio files.
- `write_audio()`: write audio data to file.
- `available_formats()`: audio file formats supported by any of the installed audio modules.
- `available_encodings()`: encodings of an audio file format supported by any of the installed audio modules.
- `format_from_extension()`: deduce audio file format from file extension.
The data to be written are 1-D or 2-D numpy arrays of floats ranging between -1 and 1
with first axis time and second axis channel.
For support of more audio formats, you might need to install additional packages.
See [installation](https://bendalab.github.io/audioio/installation)
for further instructions.
For a demo, run the script as:
```
python -m audioio.audiowriter
```
"""
import os
import subprocess
import numpy as np
from .audiomodules import *
def format_from_extension(filepath):
"""Deduce audio file format from file extension.
Parameters
----------
filepath: string
Name of the audio file.
Returns
-------
format: string
Audio format deduced from file extension.
"""
if not filepath:
return None
ext = os.path.splitext(filepath)[1]
if not ext:
return None
if ext[0] == '.':
ext = ext[1:]
if not ext:
return None
ext = ext.upper()
if ext == 'WAVE':
return 'WAV'
ext = ext.replace('MPEG' , 'MP')
return ext
def formats_wave():
"""Audio file formats supported by the wave module.
Returns
-------
formats: list of strings
List of supported file formats as strings.
"""
if not audio_modules['wave']:
return []
else:
return ['WAV']
def encodings_wave(format):
"""Encodings of an audio file format supported by the wave module.
Parameters
----------
format: str
The file format.
Returns
-------
encodings: list of strings
List of supported encodings as strings.
"""
if not audio_modules['wave']:
return []
elif format.upper() != 'WAV':
return []
else:
return ['PCM_32', 'PCM_16', 'PCM_U8']
def write_wave(filepath, data, samplerate, format=None, encoding=None):
"""Write audio data using the wave module from pythons standard libray.
Documentation
-------------
https://docs.python.org/3.8/library/wave.html
Parameters
----------
filepath: string
Full path and name of the file to write.
data: 1-D or 2-D array of floats
Array with the data (first index time, second index channel,
values within -1.0 and 1.0).
samplerate: float
Sampling rate of the data in Hertz.
format: string or None
File format, only 'WAV' is supported.
encoding: string or None
Encoding of the data: 'PCM_32', 'PCM_16', or 'PCM_U8'
If None or empty string use 'PCM_16'.
Raises
------
ImportError
The wave module is not installed.
*
Writing of the data failed.
ValueError
File format or encoding not supported.
"""
if not audio_modules['wave']:
raise ImportError
if not filepath:
raise ValueError('no file specified!')
if not format:
format = format_from_extension(filepath)
if format and format.upper() != 'WAV':
raise ValueError('file format %s not supported by wave module' % format)
wave_encodings = {'PCM_32': [4, 'i4'],
'PCM_16': [2, 'i2'],
'PCM_U8': [1, 'u1'] }
if not encoding:
encoding = 'PCM_16'
encoding = encoding.upper()
if encoding not in wave_encodings:
raise ValueError('file encoding %s not supported by wave module' % encoding)
sampwidth = wave_encodings[encoding][0]
dtype = wave_encodings[encoding][1]
wf = wave.open(filepath, 'w') # 'with' is not supported by wave
channels = 1
if len(data.shape) > 1:
channels = data.shape[1]
wf.setnchannels(channels)
wf.setnframes(len(data))
wf.setframerate(int(samplerate))
wf.setsampwidth(sampwidth)
factor = 2**(sampwidth*8-1)
if sampwidth == 1:
buffer = np.floor((data+1.0) * factor).astype(dtype)
buffer[data >= 1.0] = 2*factor - 1
else:
buffer = np.floor(data * factor).astype(dtype)
buffer[data >= 1.0] = factor - 1
try:
wf.writeframes(buffer.tobytes())
except AttributeError:
wf.writeframes(buffer.tostring())
wf.close()
def formats_ewave():
"""Audio file formats supported by the ewave module.
Returns
-------
formats: list of strings
List of supported file formats as strings.
"""
if not audio_modules['ewave']:
return []
else:
return ['WAV', 'WAVEX']
def encodings_ewave(format):
"""Encodings of an audio file format supported by the ewave module.
Parameters
----------
format: str
The file format.
Returns
-------
encodings: list of strings
List of supported encodings as strings.
"""
if not audio_modules['ewave']:
return []
elif format.upper() != 'WAV' and format.upper() != 'WAVEX':
return []
else:
return ['PCM_64', 'PCM_32', 'PCM_16', 'FLOAT', 'DOUBLE']
def write_ewave(filepath, data, samplerate, format=None, encoding=None):
"""Write audio data using the ewave module from pythons standard libray.
Documentation
-------------
https://github.com/melizalab/py-ewave
Parameters
----------
filepath: string
Full path and name of the file to write.
data: 1-D or 2-D array of floats
Array with the data (first index time, second index channel,
values within -1.0 and 1.0).
samplerate: float
Sampling rate of the data in Hertz.
format: string or None
File format, only 'WAV' and 'WAVEX' are supported.
encoding: string or None
Encoding of the data: 'PCM_64', 'PCM_32', PCM_16', 'FLOAT', 'DOUBLE'
If None or empty string use 'PCM_16'.
Raises
------
ImportError
The ewave module is not installed.
*
Writing of the data failed.
ValueError
File format or encoding not supported.
"""
if not audio_modules['ewave']:
raise ImportError
if not filepath:
raise ValueError('no file specified!')
if not format:
format = format_from_extension(filepath)
if format and format.upper() != 'WAV' and format.upper() != 'WAVEX':
raise ValueError('file format %s not supported by ewave module' % format)
ewave_encodings = {'PCM_64': 'l',
'PCM_32': 'i',
'PCM_16': 'h',
'FLOAT': 'f',
'DOUBLE': 'd' }
if not encoding:
encoding = 'PCM_16'
encoding = encoding.upper()
if encoding not in ewave_encodings:
raise ValueError('file encoding %s not supported by ewave module' % encoding)
channels = 1
if len(data.shape) > 1:
channels = data.shape[1]
with ewave.open(filepath, 'w', sampling_rate=int(samplerate),
dtype=ewave_encodings[encoding], nchannels=channels) as wf:
wf.write(data, scale=True)
def formats_wavfile():
"""Audio file formats supported by the scipy.io.wavfile module.
Returns
-------
formats: list of strings
List of supported file formats as strings.
"""
if not audio_modules['scipy.io.wavfile']:
return []
else:
return ['WAV']
def encodings_wavfile(format):
"""Encodings of an audio file format supported by the scipy.io.wavfile module.
Parameters
----------
format: str
The file format.
Returns
-------
encodings: list of strings
List of supported encodings as strings.
"""
if not audio_modules['scipy.io.wavfile']:
return []
elif format.upper() != 'WAV':
return []
else:
return ['PCM_U8', 'PCM_16', 'PCM_32', 'PCM_64', 'FLOAT', 'DOUBLE']
def write_wavfile(filepath, data, samplerate, format=None, encoding=None):
"""Write audio data using the scipy.io.wavfile module.
Documentation
-------------
http://docs.scipy.org/doc/scipy/reference/io.html
Parameters
----------
filepath: string
Full path and name of the file to write.
data: 1-D or 2-D array of floats
Array with the data (first index time, second index channel,
values within -1.0 and 1.0).
samplerate: float
Sampling rate of the data in Hertz.
format: string or None
File format, only 'WAV' is supported.
encoding: string or None
Encoding of the data: 'PCM_64', 'PCM_32', PCM_16', 'PCM_U8', 'FLOAT', 'DOUBLE'
If None or empty string use 'PCM_16'.
Raises
------
ImportError
The wavfile module is not installed.
ValueError
File format or encoding not supported.
*
Writing of the data failed.
"""
if not audio_modules['scipy.io.wavfile']:
raise ImportError
if not filepath:
raise ValueError('no file specified!')
if not format:
format = format_from_extension(filepath)
if format and format.upper() != 'WAV':
raise ValueError('file format %s not supported by scipy.io.wavfile module' % format)
wave_encodings = {'PCM_U8': [1, 'u1'],
'PCM_16': [2, 'i2'],
'PCM_32': [4, 'i4'],
'PCM_64': [8, 'i8'],
'FLOAT': [4, 'f'],
'DOUBLE': [8, 'd']}
if not encoding:
encoding = 'PCM_16'
encoding = encoding.upper()
if encoding not in wave_encodings:
raise ValueError('file encoding %s not supported by scipy.io.wavfile module' % encoding)
sampwidth = wave_encodings[encoding][0]
dtype = wave_encodings[encoding][1]
if sampwidth == 1:
factor = 2**(sampwidth*8-1)
buffer = np.floor((data+1.0) * factor).astype(dtype)
buffer[data >= 1.0] = 2*factor - 1
elif dtype[0] == 'i':
factor = 2**(sampwidth*8-1)
buffer = np.floor(data * factor).astype(dtype)
buffer[data >= 1.0] = factor - 1
else:
buffer = data.astype(dtype, copy=False)
wavfile.write(filepath, int(samplerate), buffer)
def formats_soundfile():
"""Audio file formats supported by the SoundFile module.
Returns
-------
formats: list of strings
List of supported file formats as strings.
"""
if not audio_modules['soundfile']:
return []
else:
return sorted(list(soundfile.available_formats()))
def encodings_soundfile(format):
"""Encodings of an audio file format supported by the SoundFile module.
Parameters
----------
format: str
The file format.
Returns
-------
encodings: list of strings
List of supported encodings as strings.
"""
if not audio_modules['soundfile']:
return []
else:
return sorted(list(soundfile.available_subtypes(format)))
def write_soundfile(filepath, data, samplerate, format=None, encoding=None):
"""Write audio data using the SoundFile module (based on libsndfile).
Documentation
-------------
http://pysoundfile.readthedocs.org
Parameters
----------
filepath: string
Full path and name of the file to write.
data: 1-D or 2-D array of floats
Array with the data (first index time, second index channel,
values within -1.0 and 1.0).
samplerate: float
Sampling rate of the data in Hertz.
format: string or None
File format.
encoding: string or None
Encoding of the data.
If None or empty string use 'PCM_16'.
Raises
------
ImportError
The SoundFile module is not installed.
*
Writing of the data failed.
"""
if not audio_modules['soundfile']:
raise ImportError
if not filepath:
raise ValueError('no file specified!')
if not format:
format = format_from_extension(filepath)
if not format:
format = 'WAV'
if format:
format = format.upper()
if not encoding:
encoding = 'PCM_16'
encoding = encoding.upper()
soundfile.write(filepath, data, int(samplerate), format=format, subtype=encoding)
def formats_wavefile():
"""Audio file formats supported by the wavefile module.
Returns
-------
formats: list of strings
List of supported file formats as strings.
"""
if not audio_modules['wavefile']:
return []
formats = []
for attr in dir(wavefile.Format):
v = getattr(wavefile.Format, attr)
if ( isinstance(v, int)
and v & wavefile.Format.TYPEMASK > 0
and v != wavefile.Format.TYPEMASK ):
formats.append(attr)
return sorted(formats)
def encodings_wavefile(format):
"""Encodings supported by the wavefile module.
Parameters
----------
format: str
The file format (ignored).
Returns
-------
encodings: list of strings
List of supported encodings as strings.
"""
if not audio_modules['wavefile']:
return []
if not format.upper() in formats_wavefile():
return []
encodings = []
for attr in dir(wavefile.Format):
v = getattr(wavefile.Format, attr)
if ( isinstance(v, int)
and v & wavefile.Format.SUBMASK > 0
and v != wavefile.Format.SUBMASK ):
encodings.append(attr)
return sorted(encodings)
def write_wavefile(filepath, data, samplerate, format=None, encoding=None):
"""Write audio data using the wavefile module (based on libsndfile).
Documentation
-------------
https://github.com/vokimon/python-wavefile
Parameters
----------
filepath: string
Full path and name of the file to write.
data: 1-D or 2-D array of floats
Array with the data (first index time, second index channel,
values within -1.0 and 1.0).
samplerate: float
Sampling rate of the data in Hertz.
format: string or None
File format as in wavefile.Format.
encoding: string or None
Encoding of the data as in wavefile.Format.
If None or empty string use 'PCM_16'.
Raises
------
ImportError
The wavefile module is not installed.
ValueError
File format or encoding not supported.
*
Writing of the data failed.
"""
if not audio_modules['wavefile']:
raise ImportError
if not filepath:
raise ValueError('no file specified!')
if not format:
format = format_from_extension(filepath)
if not format:
format = 'WAV'
format = format.upper()
try:
format_value = getattr(wavefile.Format, format)
except AttributeError:
raise ValueError('file format %s not supported by wavefile module' % format)
if not encoding:
encodings = encodings_wavefile(format)
encoding = encodings[0]
if 'PCM_16' in encodings:
encoding = 'PCM_16'
encoding = encoding.upper()
try:
encoding_value = getattr(wavefile.Format, encoding)
except AttributeError:
raise ValueError('file encoding %s not supported by wavefile module' % encoding)
channels = 1
if len(data.shape) > 1:
channels = data.shape[1]
else:
data = data.reshape((-1, 1))
with wavefile.WaveWriter(filepath, channels=channels, samplerate=int(samplerate),
format=format_value|encoding_value) as w:
w.write(data.T)
def formats_pydub():
"""Audio file formats supported by the Pydub module.
Returns
-------
formats: list of strings
List of supported file formats as strings.
"""
if not audio_modules['pydub']:
return []
formats = []
command = [pydub.AudioSegment.converter, '-formats']
with open(os.devnull, 'rb') as devnull:
p = subprocess.Popen(command, stdin=devnull, stdout=subprocess.PIPE,
stderr=subprocess.PIPE, universal_newlines=True)
skip = True
for line in p.communicate()[0].split('\n'):
if '--' in line[:3]:
skip = False
continue
if skip:
continue
cols = line.split()
if len(cols) > 2 and 'E' in cols[0]:
formats.append(cols[1].upper())
return formats
def encodings_pydub(format):
"""Encodings of an audio file format supported by the Pydub module.
Parameters
----------
format: str
The file format.
Returns
-------
encodings: list of strings
List of supported encodings as strings.
"""
pydub_encodings = {'pcm_s16le': 'PCM_16',
'pcm_s24le': 'PCM_24',
'pcm_s32le': 'PCM_32',
'pcm_f32le': 'FLOAT',
'pcm_f64le': 'DOUBLE',
}
if not audio_modules['pydub']:
return []
if format.upper() not in formats_pydub():
return []
encodings = []
command = [pydub.AudioSegment.converter, '-encoders']
with open(os.devnull, 'rb') as devnull:
p = subprocess.Popen(command, stdin=devnull, stdout=subprocess.PIPE,
stderr=subprocess.PIPE, universal_newlines=True)
skip = True
for line in p.communicate()[0].split('\n'):
if '--' in line[:3]:
skip = False
continue
if skip:
continue
cols = line.split()
if len(cols) > 2 and cols[0][0] == 'A':
encoding = cols[1]
if encoding in pydub_encodings:
encoding = pydub_encodings[encoding]
encodings.append(encoding.upper())
return encodings
def write_pydub(filepath, data, samplerate, format=None, encoding=None):
"""Write audio data using the Pydub module.
Documentation
-------------
https://github.com/jiaaro/pydub
Parameters
----------
filepath: string
Full path and name of the file to write.
data: 1-D or 2-D array of floats
Array with the data (first index time, second index channel,
values within -1.0 and 1.0).
samplerate: float
Sampling rate of the data in Hertz.
format: string or None
File format, everything ffmpeg or avtools are supporting.
encoding: string or None
Encoding of the data.
If None or empty string use 'PCM_16'.
Raises
------
ImportError
The Pydub module is not installed.
*
Writing of the data failed.
ValueError
File format or encoding not supported.
"""
if not audio_modules['pydub']:
raise ImportError
if not filepath:
raise ValueError('no file specified!')
if not format:
format = format_from_extension(filepath)
if format and format.upper() not in formats_pydub():
raise ValueError('file format %s not supported by Pydub module' % format)
pydub_encodings = {'PCM_16': 'pcm_s16le',
'PCM_24': 'pcm_s24le',
'PCM_32': 'pcm_s32le',
'DOUBLE': 'pcm_f32le',
'FLOAT': 'pcm_f64le',
}
if encoding:
encoding = encoding.upper()
if encoding in pydub_encodings:
encoding = pydub_encodings[encoding]
if encoding not in encodings_pydub(format):
raise ValueError('file encoding %s not supported by Pydub module' % encoding)
encoding = encoding.lower()
else:
encoding = None
channels = 1
if len(data.shape) > 1:
channels = data.shape[1]
int_data = (data*(2**31-1)).astype(np.int32)
sound = pydub.AudioSegment(int_data.ravel(), sample_width=4,
frame_rate=samplerate, channels=channels)
sound.export(filepath, format=format.lower(), codec=encoding)
audio_formats_funcs = (
('soundfile', formats_soundfile),
('wavefile', formats_wavefile),
('wave', formats_wave),
('ewave', formats_ewave),
('scipy.io.wavfile', formats_wavfile),
('pydub', formats_pydub)
)
""" List of implemented formats functions.
Each element of the list is a tuple with the module's name and the formats function.
"""
def available_formats():
"""Audio file formats supported by any of the installed audio modules.
Returns
-------
formats: list of strings
List of supported file formats as strings.
"""
formats = set()
for module, formats_func in audio_formats_funcs:
formats |= set(formats_func())
return sorted(list(formats))
audio_encodings_funcs = (
('soundfile', encodings_soundfile),
('wavefile', encodings_wavefile),
('wave', encodings_wave),
('ewave', encodings_ewave),
('scipy.io.wavfile', encodings_wavfile),
('pydub', encodings_pydub)
)
""" List of implemented encodings functions.
Each element of the list is a tuple with the module's name and the encodings function.
"""
def available_encodings(format):
"""Encodings of an audio file format supported by any of the installed audio modules.
Parameters
----------
format: str
The file format.
Returns
-------
encodings: list of strings
List of supported encodings as strings.
"""
got_sndfile = False
encodings = set()
for module, encodings_func in audio_encodings_funcs:
if got_sndfile and module == 'scipy.io.wavfile':
continue
encs = encodings_func(format)
encodings |= set(encs)
if module in ['soundfile', 'wavefile'] and len(encs) > 0:
got_sndfile = True
return sorted(list(encodings))
audio_writer_funcs = (
('soundfile', write_soundfile),
('wavefile', write_wavefile),
('wave', write_wave),
('ewave', write_ewave),
('scipy.io.wavfile', write_wavfile),
('pydub', write_pydub)
)
""" List of implemented write functions.
Each element of the list is a tuple with the module's name and the write function.
"""
def write_audio(filepath, data, samplerate, format=None, encoding=None, verbose=0):
"""Write audio data to file.
Parameters
----------
filepath: string
Full path and name of the file to write.
data: 1-D or 2-D array of floats
Array with the data (first index time, second index channel,
values within -1.0 and 1.0).
samplerate: float
Sampling rate of the data in Hertz.
format: string or None
File format. If None deduce file format from filepath.
See `available_formats()` for possible values.
encoding: string or None
Encoding of the data. See `available_encodings()` for possible values.
If None or empty string use 'PCM_16'.
verbose: int
If >0 show detailed error/warning messages.
Raises
------
ValueError
`filepath` is empty string.
IOError
Writing of the data failed.
Examples
--------
```
import numpy as np
from audioio import write_audio
samplerate = 28000.0
freq = 800.0
time = np.arange(0.0, 1.0, 1/samplerate) # one second
data = np.sin(2.0*np.p*freq*time) # 800Hz sine wave
write_audio('audio/file.wav', data, samplerate)
```
"""
if not filepath:
raise ValueError('no file specified!')
# write audio file by trying available modules:
success = False
for lib, write_file in audio_writer_funcs:
if not audio_modules[lib]:
continue
try:
write_file(filepath, data, samplerate, format, encoding)
success = True
if verbose > 0:
print('wrote data to file "%s" using %s module' %
(filepath, lib))
if verbose > 1:
print(' sampling rate: %g Hz' % samplerate)
print(' channels : %d' % (data.shape[1] if len(data.shape) > 1 else 1))
print(' frames : %d' % len(data))
break
except Exception as e:
pass
if not success:
raise IOError('failed to write data to file "%s"' % filepath)
def demo(file_path, channels=2, encoding=''):
"""Demo of the audiowriter functions.
Parameters
----------
file_path: string
File path of an audio file.
encoding: string
Encoding to be used.
"""
print('generate data ...')
samplerate = 44100.0
t = np.arange(0.0, 1.0, 1.0/samplerate)
data = np.zeros((len(t), channels))
for c in range(channels):
data[:,c] = np.sin(2.0*np.pi*(440.0+c*8.0)*t)
print("write_audio(%s) ..." % file_path)
write_audio(file_path, data, samplerate, encoding=encoding, verbose=2)
print('done.')
def main(args):
"""Call demo with command line arguments.
Parameters
----------
args: list of strings
Command line arguments as provided by sys.argv
"""
help = False
file_path = None
encoding = ''
mod = False
nchan = False
channels = 2
for arg in args[1:]:
if mod:
select_module(arg)
mod = False
elif nchan:
channels = int(arg)
nchan = False
elif arg == '-h':
help = True
break
elif arg == '-m':
mod = True
elif arg == '-n':
nchan = True
elif file_path is None:
file_path = arg
else:
encoding = arg
break
if file_path is None:
file_path = 'test.wav'
if help:
print('')
print('Usage:')
print(' python -m audioio.audiowriter [-m module] [-n channels] [<filename>] [<encoding>]')
return
demo(file_path, channels=channels, encoding=encoding)
if __name__ == "__main__":
import sys
main(sys.argv)
Global variables
var audio_formats_funcs
-
List of implemented formats functions.
Each element of the list is a tuple with the module's name and the formats function.
var audio_encodings_funcs
-
List of implemented encodings functions.
Each element of the list is a tuple with the module's name and the encodings function.
var audio_writer_funcs
-
List of implemented write functions.
Each element of the list is a tuple with the module's name and the write function.
Functions
def main(args)
-
Call demo with command line arguments.
Parameters
args
:list
ofstrings
- Command line arguments as provided by sys.argv
Expand source code
def main(args): """Call demo with command line arguments. Parameters ---------- args: list of strings Command line arguments as provided by sys.argv """ help = False file_path = None encoding = '' mod = False nchan = False channels = 2 for arg in args[1:]: if mod: select_module(arg) mod = False elif nchan: channels = int(arg) nchan = False elif arg == '-h': help = True break elif arg == '-m': mod = True elif arg == '-n': nchan = True elif file_path is None: file_path = arg else: encoding = arg break if file_path is None: file_path = 'test.wav' if help: print('') print('Usage:') print(' python -m audioio.audiowriter [-m module] [-n channels] [<filename>] [<encoding>]') return demo(file_path, channels=channels, encoding=encoding)
def format_from_extension(filepath)
-
Deduce audio file format from file extension.
Parameters
filepath
:string
- Name of the audio file.
Returns
format
:string
- Audio format deduced from file extension.
Expand source code
def format_from_extension(filepath): """Deduce audio file format from file extension. Parameters ---------- filepath: string Name of the audio file. Returns ------- format: string Audio format deduced from file extension. """ if not filepath: return None ext = os.path.splitext(filepath)[1] if not ext: return None if ext[0] == '.': ext = ext[1:] if not ext: return None ext = ext.upper() if ext == 'WAVE': return 'WAV' ext = ext.replace('MPEG' , 'MP') return ext
def formats_wave()
-
Audio file formats supported by the wave module.
Returns
formats
:list
ofstrings
- List of supported file formats as strings.
Expand source code
def formats_wave(): """Audio file formats supported by the wave module. Returns ------- formats: list of strings List of supported file formats as strings. """ if not audio_modules['wave']: return [] else: return ['WAV']
def encodings_wave(format)
-
Encodings of an audio file format supported by the wave module.
Parameters
format
:str
- The file format.
Returns
encodings
:list
ofstrings
- List of supported encodings as strings.
Expand source code
def encodings_wave(format): """Encodings of an audio file format supported by the wave module. Parameters ---------- format: str The file format. Returns ------- encodings: list of strings List of supported encodings as strings. """ if not audio_modules['wave']: return [] elif format.upper() != 'WAV': return [] else: return ['PCM_32', 'PCM_16', 'PCM_U8']
def write_wave(filepath, data, samplerate, format=None, encoding=None)
-
Write audio data using the wave module from pythons standard libray.
Documentation
https://docs.python.org/3.8/library/wave.html
Parameters
filepath
:string
- Full path and name of the file to write.
data
:1-D
or2-D array
offloats
- Array with the data (first index time, second index channel, values within -1.0 and 1.0).
samplerate
:float
- Sampling rate of the data in Hertz.
format
:string
orNone
- File format, only 'WAV' is supported.
encoding
:string
orNone
- Encoding of the data: 'PCM_32', 'PCM_16', or 'PCM_U8' If None or empty string use 'PCM_16'.
Raises
ImportError
- The wave module is not installed.
- *
- Writing of the data failed.
ValueError
- File format or encoding not supported.
Expand source code
def write_wave(filepath, data, samplerate, format=None, encoding=None): """Write audio data using the wave module from pythons standard libray. Documentation ------------- https://docs.python.org/3.8/library/wave.html Parameters ---------- filepath: string Full path and name of the file to write. data: 1-D or 2-D array of floats Array with the data (first index time, second index channel, values within -1.0 and 1.0). samplerate: float Sampling rate of the data in Hertz. format: string or None File format, only 'WAV' is supported. encoding: string or None Encoding of the data: 'PCM_32', 'PCM_16', or 'PCM_U8' If None or empty string use 'PCM_16'. Raises ------ ImportError The wave module is not installed. * Writing of the data failed. ValueError File format or encoding not supported. """ if not audio_modules['wave']: raise ImportError if not filepath: raise ValueError('no file specified!') if not format: format = format_from_extension(filepath) if format and format.upper() != 'WAV': raise ValueError('file format %s not supported by wave module' % format) wave_encodings = {'PCM_32': [4, 'i4'], 'PCM_16': [2, 'i2'], 'PCM_U8': [1, 'u1'] } if not encoding: encoding = 'PCM_16' encoding = encoding.upper() if encoding not in wave_encodings: raise ValueError('file encoding %s not supported by wave module' % encoding) sampwidth = wave_encodings[encoding][0] dtype = wave_encodings[encoding][1] wf = wave.open(filepath, 'w') # 'with' is not supported by wave channels = 1 if len(data.shape) > 1: channels = data.shape[1] wf.setnchannels(channels) wf.setnframes(len(data)) wf.setframerate(int(samplerate)) wf.setsampwidth(sampwidth) factor = 2**(sampwidth*8-1) if sampwidth == 1: buffer = np.floor((data+1.0) * factor).astype(dtype) buffer[data >= 1.0] = 2*factor - 1 else: buffer = np.floor(data * factor).astype(dtype) buffer[data >= 1.0] = factor - 1 try: wf.writeframes(buffer.tobytes()) except AttributeError: wf.writeframes(buffer.tostring()) wf.close()
def formats_ewave()
-
Audio file formats supported by the ewave module.
Returns
formats
:list
ofstrings
- List of supported file formats as strings.
Expand source code
def formats_ewave(): """Audio file formats supported by the ewave module. Returns ------- formats: list of strings List of supported file formats as strings. """ if not audio_modules['ewave']: return [] else: return ['WAV', 'WAVEX']
def encodings_ewave(format)
-
Encodings of an audio file format supported by the ewave module.
Parameters
format
:str
- The file format.
Returns
encodings
:list
ofstrings
- List of supported encodings as strings.
Expand source code
def encodings_ewave(format): """Encodings of an audio file format supported by the ewave module. Parameters ---------- format: str The file format. Returns ------- encodings: list of strings List of supported encodings as strings. """ if not audio_modules['ewave']: return [] elif format.upper() != 'WAV' and format.upper() != 'WAVEX': return [] else: return ['PCM_64', 'PCM_32', 'PCM_16', 'FLOAT', 'DOUBLE']
def write_ewave(filepath, data, samplerate, format=None, encoding=None)
-
Write audio data using the ewave module from pythons standard libray.
Documentation
https://github.com/melizalab/py-ewave
Parameters
filepath
:string
- Full path and name of the file to write.
data
:1-D
or2-D array
offloats
- Array with the data (first index time, second index channel, values within -1.0 and 1.0).
samplerate
:float
- Sampling rate of the data in Hertz.
format
:string
orNone
- File format, only 'WAV' and 'WAVEX' are supported.
encoding
:string
orNone
- Encoding of the data: 'PCM_64', 'PCM_32', PCM_16', 'FLOAT', 'DOUBLE' If None or empty string use 'PCM_16'.
Raises
ImportError
- The ewave module is not installed.
- *
- Writing of the data failed.
ValueError
- File format or encoding not supported.
Expand source code
def write_ewave(filepath, data, samplerate, format=None, encoding=None): """Write audio data using the ewave module from pythons standard libray. Documentation ------------- https://github.com/melizalab/py-ewave Parameters ---------- filepath: string Full path and name of the file to write. data: 1-D or 2-D array of floats Array with the data (first index time, second index channel, values within -1.0 and 1.0). samplerate: float Sampling rate of the data in Hertz. format: string or None File format, only 'WAV' and 'WAVEX' are supported. encoding: string or None Encoding of the data: 'PCM_64', 'PCM_32', PCM_16', 'FLOAT', 'DOUBLE' If None or empty string use 'PCM_16'. Raises ------ ImportError The ewave module is not installed. * Writing of the data failed. ValueError File format or encoding not supported. """ if not audio_modules['ewave']: raise ImportError if not filepath: raise ValueError('no file specified!') if not format: format = format_from_extension(filepath) if format and format.upper() != 'WAV' and format.upper() != 'WAVEX': raise ValueError('file format %s not supported by ewave module' % format) ewave_encodings = {'PCM_64': 'l', 'PCM_32': 'i', 'PCM_16': 'h', 'FLOAT': 'f', 'DOUBLE': 'd' } if not encoding: encoding = 'PCM_16' encoding = encoding.upper() if encoding not in ewave_encodings: raise ValueError('file encoding %s not supported by ewave module' % encoding) channels = 1 if len(data.shape) > 1: channels = data.shape[1] with ewave.open(filepath, 'w', sampling_rate=int(samplerate), dtype=ewave_encodings[encoding], nchannels=channels) as wf: wf.write(data, scale=True)
def formats_wavfile()
-
Audio file formats supported by the scipy.io.wavfile module.
Returns
formats
:list
ofstrings
- List of supported file formats as strings.
Expand source code
def formats_wavfile(): """Audio file formats supported by the scipy.io.wavfile module. Returns ------- formats: list of strings List of supported file formats as strings. """ if not audio_modules['scipy.io.wavfile']: return [] else: return ['WAV']
def encodings_wavfile(format)
-
Encodings of an audio file format supported by the scipy.io.wavfile module.
Parameters
format
:str
- The file format.
Returns
encodings
:list
ofstrings
- List of supported encodings as strings.
Expand source code
def encodings_wavfile(format): """Encodings of an audio file format supported by the scipy.io.wavfile module. Parameters ---------- format: str The file format. Returns ------- encodings: list of strings List of supported encodings as strings. """ if not audio_modules['scipy.io.wavfile']: return [] elif format.upper() != 'WAV': return [] else: return ['PCM_U8', 'PCM_16', 'PCM_32', 'PCM_64', 'FLOAT', 'DOUBLE']
def write_wavfile(filepath, data, samplerate, format=None, encoding=None)
-
Write audio data using the scipy.io.wavfile module.
Documentation
http://docs.scipy.org/doc/scipy/reference/io.html
Parameters
filepath
:string
- Full path and name of the file to write.
data
:1-D
or2-D array
offloats
- Array with the data (first index time, second index channel, values within -1.0 and 1.0).
samplerate
:float
- Sampling rate of the data in Hertz.
format
:string
orNone
- File format, only 'WAV' is supported.
encoding
:string
orNone
- Encoding of the data: 'PCM_64', 'PCM_32', PCM_16', 'PCM_U8', 'FLOAT', 'DOUBLE' If None or empty string use 'PCM_16'.
Raises
ImportError
- The wavfile module is not installed.
ValueError
- File format or encoding not supported.
* Writing of the data failed.
Expand source code
def write_wavfile(filepath, data, samplerate, format=None, encoding=None): """Write audio data using the scipy.io.wavfile module. Documentation ------------- http://docs.scipy.org/doc/scipy/reference/io.html Parameters ---------- filepath: string Full path and name of the file to write. data: 1-D or 2-D array of floats Array with the data (first index time, second index channel, values within -1.0 and 1.0). samplerate: float Sampling rate of the data in Hertz. format: string or None File format, only 'WAV' is supported. encoding: string or None Encoding of the data: 'PCM_64', 'PCM_32', PCM_16', 'PCM_U8', 'FLOAT', 'DOUBLE' If None or empty string use 'PCM_16'. Raises ------ ImportError The wavfile module is not installed. ValueError File format or encoding not supported. * Writing of the data failed. """ if not audio_modules['scipy.io.wavfile']: raise ImportError if not filepath: raise ValueError('no file specified!') if not format: format = format_from_extension(filepath) if format and format.upper() != 'WAV': raise ValueError('file format %s not supported by scipy.io.wavfile module' % format) wave_encodings = {'PCM_U8': [1, 'u1'], 'PCM_16': [2, 'i2'], 'PCM_32': [4, 'i4'], 'PCM_64': [8, 'i8'], 'FLOAT': [4, 'f'], 'DOUBLE': [8, 'd']} if not encoding: encoding = 'PCM_16' encoding = encoding.upper() if encoding not in wave_encodings: raise ValueError('file encoding %s not supported by scipy.io.wavfile module' % encoding) sampwidth = wave_encodings[encoding][0] dtype = wave_encodings[encoding][1] if sampwidth == 1: factor = 2**(sampwidth*8-1) buffer = np.floor((data+1.0) * factor).astype(dtype) buffer[data >= 1.0] = 2*factor - 1 elif dtype[0] == 'i': factor = 2**(sampwidth*8-1) buffer = np.floor(data * factor).astype(dtype) buffer[data >= 1.0] = factor - 1 else: buffer = data.astype(dtype, copy=False) wavfile.write(filepath, int(samplerate), buffer)
def formats_soundfile()
-
Audio file formats supported by the SoundFile module.
Returns
formats
:list
ofstrings
- List of supported file formats as strings.
Expand source code
def formats_soundfile(): """Audio file formats supported by the SoundFile module. Returns ------- formats: list of strings List of supported file formats as strings. """ if not audio_modules['soundfile']: return [] else: return sorted(list(soundfile.available_formats()))
def encodings_soundfile(format)
-
Encodings of an audio file format supported by the SoundFile module.
Parameters
format
:str
- The file format.
Returns
encodings
:list
ofstrings
- List of supported encodings as strings.
Expand source code
def encodings_soundfile(format): """Encodings of an audio file format supported by the SoundFile module. Parameters ---------- format: str The file format. Returns ------- encodings: list of strings List of supported encodings as strings. """ if not audio_modules['soundfile']: return [] else: return sorted(list(soundfile.available_subtypes(format)))
def write_soundfile(filepath, data, samplerate, format=None, encoding=None)
-
Write audio data using the SoundFile module (based on libsndfile).
Documentation
http://pysoundfile.readthedocs.org
Parameters
filepath
:string
- Full path and name of the file to write.
data
:1-D
or2-D array
offloats
- Array with the data (first index time, second index channel, values within -1.0 and 1.0).
samplerate
:float
- Sampling rate of the data in Hertz.
format
:string
orNone
- File format.
encoding
:string
orNone
- Encoding of the data. If None or empty string use 'PCM_16'.
Raises
ImportError
- The SoundFile module is not installed.
* Writing of the data failed.
Expand source code
def write_soundfile(filepath, data, samplerate, format=None, encoding=None): """Write audio data using the SoundFile module (based on libsndfile). Documentation ------------- http://pysoundfile.readthedocs.org Parameters ---------- filepath: string Full path and name of the file to write. data: 1-D or 2-D array of floats Array with the data (first index time, second index channel, values within -1.0 and 1.0). samplerate: float Sampling rate of the data in Hertz. format: string or None File format. encoding: string or None Encoding of the data. If None or empty string use 'PCM_16'. Raises ------ ImportError The SoundFile module is not installed. * Writing of the data failed. """ if not audio_modules['soundfile']: raise ImportError if not filepath: raise ValueError('no file specified!') if not format: format = format_from_extension(filepath) if not format: format = 'WAV' if format: format = format.upper() if not encoding: encoding = 'PCM_16' encoding = encoding.upper() soundfile.write(filepath, data, int(samplerate), format=format, subtype=encoding)
def formats_wavefile()
-
Audio file formats supported by the wavefile module.
Returns
formats
:list
ofstrings
- List of supported file formats as strings.
Expand source code
def formats_wavefile(): """Audio file formats supported by the wavefile module. Returns ------- formats: list of strings List of supported file formats as strings. """ if not audio_modules['wavefile']: return [] formats = [] for attr in dir(wavefile.Format): v = getattr(wavefile.Format, attr) if ( isinstance(v, int) and v & wavefile.Format.TYPEMASK > 0 and v != wavefile.Format.TYPEMASK ): formats.append(attr) return sorted(formats)
def encodings_wavefile(format)
-
Encodings supported by the wavefile module.
Parameters
format
:str
- The file format (ignored).
Returns
encodings
:list
ofstrings
- List of supported encodings as strings.
Expand source code
def encodings_wavefile(format): """Encodings supported by the wavefile module. Parameters ---------- format: str The file format (ignored). Returns ------- encodings: list of strings List of supported encodings as strings. """ if not audio_modules['wavefile']: return [] if not format.upper() in formats_wavefile(): return [] encodings = [] for attr in dir(wavefile.Format): v = getattr(wavefile.Format, attr) if ( isinstance(v, int) and v & wavefile.Format.SUBMASK > 0 and v != wavefile.Format.SUBMASK ): encodings.append(attr) return sorted(encodings)
def write_wavefile(filepath, data, samplerate, format=None, encoding=None)
-
Write audio data using the wavefile module (based on libsndfile).
Documentation
https://github.com/vokimon/python-wavefile
Parameters
filepath
:string
- Full path and name of the file to write.
data
:1-D
or2-D array
offloats
- Array with the data (first index time, second index channel, values within -1.0 and 1.0).
samplerate
:float
- Sampling rate of the data in Hertz.
format
:string
orNone
- File format as in wavefile.Format.
encoding
:string
orNone
- Encoding of the data as in wavefile.Format. If None or empty string use 'PCM_16'.
Raises
ImportError
- The wavefile module is not installed.
ValueError
- File format or encoding not supported.
* Writing of the data failed.
Expand source code
def write_wavefile(filepath, data, samplerate, format=None, encoding=None): """Write audio data using the wavefile module (based on libsndfile). Documentation ------------- https://github.com/vokimon/python-wavefile Parameters ---------- filepath: string Full path and name of the file to write. data: 1-D or 2-D array of floats Array with the data (first index time, second index channel, values within -1.0 and 1.0). samplerate: float Sampling rate of the data in Hertz. format: string or None File format as in wavefile.Format. encoding: string or None Encoding of the data as in wavefile.Format. If None or empty string use 'PCM_16'. Raises ------ ImportError The wavefile module is not installed. ValueError File format or encoding not supported. * Writing of the data failed. """ if not audio_modules['wavefile']: raise ImportError if not filepath: raise ValueError('no file specified!') if not format: format = format_from_extension(filepath) if not format: format = 'WAV' format = format.upper() try: format_value = getattr(wavefile.Format, format) except AttributeError: raise ValueError('file format %s not supported by wavefile module' % format) if not encoding: encodings = encodings_wavefile(format) encoding = encodings[0] if 'PCM_16' in encodings: encoding = 'PCM_16' encoding = encoding.upper() try: encoding_value = getattr(wavefile.Format, encoding) except AttributeError: raise ValueError('file encoding %s not supported by wavefile module' % encoding) channels = 1 if len(data.shape) > 1: channels = data.shape[1] else: data = data.reshape((-1, 1)) with wavefile.WaveWriter(filepath, channels=channels, samplerate=int(samplerate), format=format_value|encoding_value) as w: w.write(data.T)
def formats_pydub()
-
Audio file formats supported by the Pydub module.
Returns
formats
:list
ofstrings
- List of supported file formats as strings.
Expand source code
def formats_pydub(): """Audio file formats supported by the Pydub module. Returns ------- formats: list of strings List of supported file formats as strings. """ if not audio_modules['pydub']: return [] formats = [] command = [pydub.AudioSegment.converter, '-formats'] with open(os.devnull, 'rb') as devnull: p = subprocess.Popen(command, stdin=devnull, stdout=subprocess.PIPE, stderr=subprocess.PIPE, universal_newlines=True) skip = True for line in p.communicate()[0].split('\n'): if '--' in line[:3]: skip = False continue if skip: continue cols = line.split() if len(cols) > 2 and 'E' in cols[0]: formats.append(cols[1].upper()) return formats
def encodings_pydub(format)
-
Encodings of an audio file format supported by the Pydub module.
Parameters
format
:str
- The file format.
Returns
encodings
:list
ofstrings
- List of supported encodings as strings.
Expand source code
def encodings_pydub(format): """Encodings of an audio file format supported by the Pydub module. Parameters ---------- format: str The file format. Returns ------- encodings: list of strings List of supported encodings as strings. """ pydub_encodings = {'pcm_s16le': 'PCM_16', 'pcm_s24le': 'PCM_24', 'pcm_s32le': 'PCM_32', 'pcm_f32le': 'FLOAT', 'pcm_f64le': 'DOUBLE', } if not audio_modules['pydub']: return [] if format.upper() not in formats_pydub(): return [] encodings = [] command = [pydub.AudioSegment.converter, '-encoders'] with open(os.devnull, 'rb') as devnull: p = subprocess.Popen(command, stdin=devnull, stdout=subprocess.PIPE, stderr=subprocess.PIPE, universal_newlines=True) skip = True for line in p.communicate()[0].split('\n'): if '--' in line[:3]: skip = False continue if skip: continue cols = line.split() if len(cols) > 2 and cols[0][0] == 'A': encoding = cols[1] if encoding in pydub_encodings: encoding = pydub_encodings[encoding] encodings.append(encoding.upper()) return encodings
def write_pydub(filepath, data, samplerate, format=None, encoding=None)
-
Write audio data using the Pydub module.
Documentation
https://github.com/jiaaro/pydub
Parameters
filepath
:string
- Full path and name of the file to write.
data
:1-D
or2-D array
offloats
- Array with the data (first index time, second index channel, values within -1.0 and 1.0).
samplerate
:float
- Sampling rate of the data in Hertz.
format
:string
orNone
- File format, everything ffmpeg or avtools are supporting.
encoding
:string
orNone
- Encoding of the data. If None or empty string use 'PCM_16'.
Raises
ImportError
- The Pydub module is not installed.
- *
- Writing of the data failed.
ValueError
- File format or encoding not supported.
Expand source code
def write_pydub(filepath, data, samplerate, format=None, encoding=None): """Write audio data using the Pydub module. Documentation ------------- https://github.com/jiaaro/pydub Parameters ---------- filepath: string Full path and name of the file to write. data: 1-D or 2-D array of floats Array with the data (first index time, second index channel, values within -1.0 and 1.0). samplerate: float Sampling rate of the data in Hertz. format: string or None File format, everything ffmpeg or avtools are supporting. encoding: string or None Encoding of the data. If None or empty string use 'PCM_16'. Raises ------ ImportError The Pydub module is not installed. * Writing of the data failed. ValueError File format or encoding not supported. """ if not audio_modules['pydub']: raise ImportError if not filepath: raise ValueError('no file specified!') if not format: format = format_from_extension(filepath) if format and format.upper() not in formats_pydub(): raise ValueError('file format %s not supported by Pydub module' % format) pydub_encodings = {'PCM_16': 'pcm_s16le', 'PCM_24': 'pcm_s24le', 'PCM_32': 'pcm_s32le', 'DOUBLE': 'pcm_f32le', 'FLOAT': 'pcm_f64le', } if encoding: encoding = encoding.upper() if encoding in pydub_encodings: encoding = pydub_encodings[encoding] if encoding not in encodings_pydub(format): raise ValueError('file encoding %s not supported by Pydub module' % encoding) encoding = encoding.lower() else: encoding = None channels = 1 if len(data.shape) > 1: channels = data.shape[1] int_data = (data*(2**31-1)).astype(np.int32) sound = pydub.AudioSegment(int_data.ravel(), sample_width=4, frame_rate=samplerate, channels=channels) sound.export(filepath, format=format.lower(), codec=encoding)
def available_formats()
-
Audio file formats supported by any of the installed audio modules.
Returns
formats
:list
ofstrings
- List of supported file formats as strings.
Expand source code
def available_formats(): """Audio file formats supported by any of the installed audio modules. Returns ------- formats: list of strings List of supported file formats as strings. """ formats = set() for module, formats_func in audio_formats_funcs: formats |= set(formats_func()) return sorted(list(formats))
def available_encodings(format)
-
Encodings of an audio file format supported by any of the installed audio modules.
Parameters
format
:str
- The file format.
Returns
encodings
:list
ofstrings
- List of supported encodings as strings.
Expand source code
def available_encodings(format): """Encodings of an audio file format supported by any of the installed audio modules. Parameters ---------- format: str The file format. Returns ------- encodings: list of strings List of supported encodings as strings. """ got_sndfile = False encodings = set() for module, encodings_func in audio_encodings_funcs: if got_sndfile and module == 'scipy.io.wavfile': continue encs = encodings_func(format) encodings |= set(encs) if module in ['soundfile', 'wavefile'] and len(encs) > 0: got_sndfile = True return sorted(list(encodings))
def write_audio(filepath, data, samplerate, format=None, encoding=None, verbose=0)
-
Write audio data to file.
Parameters
filepath
:string
- Full path and name of the file to write.
data
:1-D
or2-D array
offloats
- Array with the data (first index time, second index channel, values within -1.0 and 1.0).
samplerate
:float
- Sampling rate of the data in Hertz.
format
:string
orNone
- File format. If None deduce file format from filepath.
See
available_formats()
for possible values. encoding
:string
orNone
- Encoding of the data. See
available_encodings()
for possible values. If None or empty string use 'PCM_16'. verbose
:int
- If >0 show detailed error/warning messages.
Raises
ValueError
filepath
is empty string.IOError
- Writing of the data failed.
Examples
import numpy as np from audioio import write_audio samplerate = 28000.0 freq = 800.0 time = np.arange(0.0, 1.0, 1/samplerate) # one second data = np.sin(2.0*np.p*freq*time) # 800Hz sine wave write_audio('audio/file.wav', data, samplerate)
Expand source code
def write_audio(filepath, data, samplerate, format=None, encoding=None, verbose=0): """Write audio data to file. Parameters ---------- filepath: string Full path and name of the file to write. data: 1-D or 2-D array of floats Array with the data (first index time, second index channel, values within -1.0 and 1.0). samplerate: float Sampling rate of the data in Hertz. format: string or None File format. If None deduce file format from filepath. See `available_formats()` for possible values. encoding: string or None Encoding of the data. See `available_encodings()` for possible values. If None or empty string use 'PCM_16'. verbose: int If >0 show detailed error/warning messages. Raises ------ ValueError `filepath` is empty string. IOError Writing of the data failed. Examples -------- ``` import numpy as np from audioio import write_audio samplerate = 28000.0 freq = 800.0 time = np.arange(0.0, 1.0, 1/samplerate) # one second data = np.sin(2.0*np.p*freq*time) # 800Hz sine wave write_audio('audio/file.wav', data, samplerate) ``` """ if not filepath: raise ValueError('no file specified!') # write audio file by trying available modules: success = False for lib, write_file in audio_writer_funcs: if not audio_modules[lib]: continue try: write_file(filepath, data, samplerate, format, encoding) success = True if verbose > 0: print('wrote data to file "%s" using %s module' % (filepath, lib)) if verbose > 1: print(' sampling rate: %g Hz' % samplerate) print(' channels : %d' % (data.shape[1] if len(data.shape) > 1 else 1)) print(' frames : %d' % len(data)) break except Exception as e: pass if not success: raise IOError('failed to write data to file "%s"' % filepath)
def demo(file_path, channels=2, encoding='')
-
Demo of the audiowriter functions.
Parameters
file_path
:string
- File path of an audio file.
encoding
:string
- Encoding to be used.
Expand source code
def demo(file_path, channels=2, encoding=''): """Demo of the audiowriter functions. Parameters ---------- file_path: string File path of an audio file. encoding: string Encoding to be used. """ print('generate data ...') samplerate = 44100.0 t = np.arange(0.0, 1.0, 1.0/samplerate) data = np.zeros((len(t), channels)) for c in range(channels): data[:,c] = np.sin(2.0*np.pi*(440.0+c*8.0)*t) print("write_audio(%s) ..." % file_path) write_audio(file_path, data, samplerate, encoding=encoding, verbose=2) print('done.')