Beispiel #1
0
def read(name, end=None, start=0, dtype=np.float64, return_format=False) :
    """read samples from arbitrary sound files.
    return data, samplerate and encoding string

    returns subset of samples as specified by start and end arguments (Def all samples)
    normalizes samples to [-1,1] if the datatype is a floating point type
    """
    sf  = PySndfile(name)
    enc = sf.encoding_str()

    nf = sf.seek(start, 0)
    if not nf == start:
        raise IOError("sndio.read::error:: while seeking at starting position")
    
    if end == None:
        ff = sf.read_frames(dtype=dtype)
    else:
        ff = sf.read_frames(end-start, dtype=dtype)
        
    # if norm and (enc not in ["float32" , "float64"]) :
    #     if enc in enc_norm_map :
    #         ff = ff / enc_norm_map[sf.encoding_str()]
    #     else :
    #         raise IOError("sndio.read::error::normalization of compressed pcm data is not supported")

    if return_format:
        return ff, sf.samplerate(), enc, sf.major_format_str()
    return ff, sf.samplerate(), enc
Beispiel #2
0
def synthesize_trial(wavFileMatrix, indexes):
    '''
    Using the matrix of alternative words and the selected words for each
    column, generate samples from audio files
    Returns an array of samples generated by concatenating the selected audio
    files
    '''
    columnNames = ['a', 'b', 'c', 'd', 'e']
    indexes = np.pad(indexes, ((0, 1)), 'constant', constant_values=0)
    indexes = rolling_window_lastaxis(indexes, 2)
    offset = 10
    y = np.array([])
    filenames = []
    for name, ind in zip(columnNames, indexes):
        if name == 'e':
            offset = 1
        wavFilename, wavFilepath = wavFileMatrix[name][(ind[0] * offset) +
                                                       ind[1]]
        wav = PySndfile(wavFilepath)
        fs = wav.samplerate()
        x = wav.read_frames()
        y = np.append(y, x)
        filenames.append(wavFilename)
    return (y, {
        'rate': fs,
        'format': wav.major_format_str(),
        'enc': wav.encoding_str()
    }, filenames)
Beispiel #3
0
def block_mix_wavs(wavpath_a,
                   wavpath_b,
                   out_wavpath,
                   a_gain=1.,
                   b_gain=1.,
                   block_size=4096,
                   mute_left=False):
    '''
    Mix two wav files, applying gains to each
    '''
    wav_a = PySndfile(wavpath_a, 'r')
    wav_b = PySndfile(wavpath_b, 'r')

    out_wav = PySndfile(out_wavpath, 'w', construct_format('wav', 'pcm16'),
                        wav_a.channels(), wav_a.samplerate())

    i = 0
    while i < wav_a.frames():
        if i + block_size > wav_a.frames():
            block_size = wav_a.frames() - i
        x1 = wav_a.read_frames(block_size)
        x2 = wav_b.read_frames(block_size)
        x1[:, :2] *= a_gain
        x2 *= b_gain
        if x1.shape[1] == 3:
            y = np.zeros(x1.shape)
            y[:, 0] = x1[:, 0] + x2
            y[:, 1] = x1[:, 1] + x2
            y[:, 2] = x1[:, 2]
            if mute_left:
                y[:, 0] = 0.0
        else:
            y = x1 + x2
        out_wav.write_frames(y)
        i += block_size
Beispiel #4
0
def main():
    wavs = globDir('./out/stim/', '*.wav')
    rmss = globDir('./out/stim/', 'stim_*_env.npy')
    outDir = "./out/stim/"
    for wav, rms in zip(wavs, rmss):
        print("Detecting silence in wav file: {}".format(wav))
        snd = PySndfile(wav, 'r')
        fs = int(snd.samplerate())
        silences = detect_silences(rms, fs)

        head, tail = os.path.split(wav)
        tail = os.path.splitext(tail)[0]
        tail = tail + "_silence.npy"
        silence_filepath = os.path.join(outDir, tail)
        np.save(silence_filepath, silences)
Beispiel #5
0
def main():
    wavs = globDir('./out/stim/', '*.wav')
    silences = globDir('./out/stim/', 'stim_*_silence.npy')
    outDir = "./out/stim/"
    for wav, sil in zip(wavs, silences):
        snd = PySndfile(wav, 'r')
        fs = int(snd.samplerate())
        s = np.load(sil)
        sil_bool = slice_to_bool(s, snd.frames())

        rms = np.sqrt(np.mean(np.abs(snd.read_frames()[~sil_bool]**2)))

        head, tail = os.path.split(wav)
        tail = os.path.splitext(tail)[0]
        tail = tail + "_rms.npy"
        rms_filepath = os.path.join(outDir, tail)
        np.save(rms_filepath, rms)
Beispiel #6
0
def main():
    wavs = globDir('./out/stim/', '*.wav')
    envs = globDir('./out/stim/', 'stim_*_env.npy')
    silences = globDir('./out/stim/', 'stim_*_silence.npy')
    for wavfp, envfp, silfp in zip(wavs, envs, silences):
        snd = PySndfile(wavfp, 'r')
        fs = int(snd.samplerate())
        env = np.load(envfp)
        sil_slices = np.load(silfp)
        sil = np.zeros(env.size)
        for sil_slice in sil_slices:
            sil[sil_slice[0]:sil_slice[1]] = 1
        pdb.set_trace()

        plt.plot(snd.read_frames(fs*60))
        plt.plot(sil[:fs*60])
        plt.show()
Beispiel #7
0
def block_process_wav(wavpath, out_wavpath, func, block_size=4096, **args):
    '''
    Mix two wav files, applying gains to each
    '''
    wav = PySndfile(wavpath, 'r')

    out_wav = PySndfile(out_wavpath, 'w', construct_format('wav', 'pcm16'),
                        wav.channels(), wav.samplerate())

    i = 0
    while i < wav.frames():
        if i + block_size > wav.frames():
            block_size = wav.frames() - i
        x = wav.read_frames(block_size)
        y = func(x, **args)
        out_wav.write_frames(y)
        i += block_size
    del out_wav
Beispiel #8
0
outfile = vendor + "_" + mic + "_" + opts.outfile
print "Creating {} ...".format(outfile)

with open(outfile, "w") as f:
    f.write("/// Impulse response header, generated by ir_wav2h.py\n")
    f.write("/// Input file: {}\n\n".format(filename))
    f.write("#ifndef IR_{}_H\n#define IR_{}_H\n\n".format(
        nsname.upper(), nsname.upper()))
    f.write("#include <vector>\n\n".format(nsname))
    f.write("namespace {} {{\n\n".format(nsname))
    f.write("static const char* name = \"{}\";\n".format(name))
    f.write("static const char* vendor = \"{}\";\n".format(
        vendor.replace("_", " ")))
    f.write("static const char* mic = \"{}\";\n".format(mic.replace("_", " ")))
    f.write("static int samplerate =  {};\n\n".format(wav.samplerate()))
    f.write("static std::vector<double> frames = {{\n".format(nsname))
    first = True
    i = 0
    for s in wav.read_frames():
        if first:
            first = False
            f.write("    ")
        else:
            if i % 6 == 0:
                f.write(",\n    ")
            else:
                f.write(", ")
        f.write(str(s))
        i = i + 1
Beispiel #9
0
def read_audio(name_audio):
    soundIO = PySndfile(name_audio)

    frames = soundIO.read_frames()
    s_rate = soundIO.samplerate()
    return frames, s_rate
Beispiel #10
0
    def __init__(self, fn, sr=None, chns=None, blksz=2**16, dtype=np.float32):
        fnd = False

        if not fnd and (PySndfile is not None):
            try:
                sf = PySndfile(fn, mode='r')
            except IOError:
                pass
            else:
                if (sr is None or sr == sf.samplerate()) and (
                        chns is None or chns == sf.channels()):
                    # no resampling required
                    self.channels = sf.channels()
                    self.samplerate = sf.samplerate()
                    self.frames = sf.frames()

                    self.rdr = sndreader(sf, blksz, dtype=dtype)
                    fnd = True

        if not fnd:
            ffmpeg = findfile('ffmpeg') or findfile('avconv')
            if ffmpeg is not None:
                pipe = sp.Popen([ffmpeg, '-i', fn, '-'],
                                stdin=sp.PIPE,
                                stdout=sp.PIPE,
                                stderr=sp.PIPE)
                fmtout = pipe.stderr.read()
                if (sys.version_info > (3, 0)):
                    fmtout = fmtout.decode()
                m = re.match(
                    r"^(ffmpeg|avconv) version.*Duration: (\d\d:\d\d:\d\d.\d\d),.*Audio: (.+), (\d+) Hz, (.+), (.+), (\d+) kb/s",
                    " ".join(fmtout.split('\n')))
                if m is not None:
                    self.samplerate = int(m.group(4)) if not sr else int(sr)
                    chdef = m.group(5)
                    if chdef.endswith(" channels") and len(chdef.split()) == 2:
                        self.channels = int(chdef.split()[0])
                    else:
                        try:
                            self.channels = {
                                'mono': 1,
                                '1 channels (FL+FR)': 1,
                                'stereo': 2,
                                'hexadecagonal': 16
                            }[chdef] if not chns else chns
                        except:
                            print(f"Channel definition '{chdef}' unknown")
                            raise
                    dur = reduce(lambda x, y: x * 60 + y,
                                 list(map(float,
                                          m.group(2).split(':'))))
                    self.frames = int(
                        dur * self.samplerate
                    )  # that's actually an estimation, because of potential resampling with round-off errors
                    pipe = sp.Popen(
                        [
                            ffmpeg, '-i', fn, '-f', 'f32le', '-acodec',
                            'pcm_f32le', '-ar',
                            str(self.samplerate), '-ac',
                            str(self.channels), '-'
                        ],
                        #                    bufsize=self.samplerate*self.channels*4*50,
                        stdin=sp.PIPE,
                        stdout=sp.PIPE,
                        stderr=sp.PIPE)

                    def rdr():
                        bufsz = (blksz // self.channels) * self.channels * 4
                        while True:
                            data = pipe.stdout.read(bufsz)
                            if len(data) == 0:
                                break
                            data = np.fromstring(data, dtype=dtype)
                            yield data.reshape((-1, self.channels)).T

                    self.rdr = rdr()
                    fnd = True

        if not fnd:
            raise IOError("Format not usable")
Beispiel #11
0
def get_info(name) :
    """
    retrieve samplerate, encoding (str) and format informationfor sndfile name
    """
    sf  = PySndfile(name)
    return sf.samplerate(), sf.encoding_str(), sf.major_format_str()
Beispiel #12
0
def concatenateStimuli(MatrixDir, OutDir, Length, n):
    # Get matrix wav file paths
    wavFiles = globDir(MatrixDir, '*.wav')

    stim_parts = os.path.join(MatrixDir, "stim_parts.csv")
    stim_words = os.path.join(MatrixDir, "stim_words.csv")
    stim_part_rows = []
    with open(stim_parts, 'r') as csvfile:
        stim_part_rows = [line for line in csv.reader(csvfile)]
    with open(stim_words, 'r') as csvfile:
        stim_word_rows = [line for line in csv.reader(csvfile)]

    wavFiles = natsorted(wavFiles)
    totalSize = 0
    y = []
    parts = []
    questions = []
    i = 0
    gapSize = np.uniform(0.8, 1.2, len(wavFiles))
    for wav, gap in zip(wavFiles, gapSize):
        if i == n:
            break
        wavObj = PySndfile(wav)
        fs = wavObj.samplerate()
        size = wavObj.frames()
        totalSize += size
        totalSize += int(gap * fs)
        if (totalSize / fs) > Length:
            # total size + 2 second silence at start
            y.append(np.zeros((totalSize + 2 * fs, 3)))
            parts.append([])
            questions.append([])
            i += 1
            totalSize = 0

    writePtr = 2 * fs
    idx = np.arange(0, writePtr)
    chunk = np.zeros(idx.size)
    chunk = np.vstack([chunk, chunk, chunk]).T
    trigger = gen_trigger(idx, 2., 0.01, fs)
    chunk[:, 2] = trigger
    for i, _ in enumerate(y):
        y[i][0:writePtr, :] = chunk

    i = 0
    for wav, word, part in zip(wavFiles, stim_word_rows, stim_part_rows):
        if writePtr >= y[i].shape[0]:
            i += 1
            writePtr = fs * 2
        if i == n:
            break
        x, fs, encStr, fmtStr = sndio.read(wav, return_format=True)
        threeMs = int(0.1 * fs)
        silence = np.zeros(threeMs)
        chunk = np.append(x, silence)

        idx = np.arange(writePtr, writePtr + chunk.shape[0])
        chunk = np.vstack([chunk, chunk, np.zeros(chunk.shape[0])]).T
        trigger = gen_trigger(idx, 2., 0.01, fs)
        chunk[:, 2] = trigger

        y[i][writePtr:writePtr + chunk.shape[0], :] = chunk
        questions[i].append(word)
        parts[i].append(part)

        writePtr += chunk.shape[0]

    for ind, (data, q, p) in enumerate(zip(y, questions, parts)):
        pysndfile.sndio.write(os.path.join(OutDir, 'stim_{}.wav'.format(ind)),
                              data,
                              format=fmtStr,
                              enc=encStr)
        with open('./out/stim/stim_words_{}.csv'.format(ind), 'w') as csvfile:
            writer = csv.writer(csvfile)
            writer.writerows(q)
        with open('./out/stim/stim_parts_{}.csv'.format(ind), 'w') as csvfile:
            writer = csv.writer(csvfile)
            writer.writerows(p)