Search code examples
pythonpyaudio

PyAudio not working when trying to record and play on the same device


I'm trying to record some data by connecting an output of audio device, passing it through a guitar pedal and then back into a line in on the same audio device.

In pyAudio I am able to output to the device without any problems but when I either open 2 streams (input/output) or 1 stream with both input/output pyaudio stops working. I don't hear any output when I monitor the audio device and the stream.is_active always returns true

My Code:

from synthesizer import Player, Synthesizer, Waveform
import numpy as np
import time

BITRATE = 44100     #number of frames per second/frameset.  
CHUNK = 8192
FORMAT = pyaudio.paInt16
CHANNELS = 1
RATE = 44100
SAMPLE_LENGTH = 5

# open audio device
py_audio = pyaudio.PyAudio()

# generate audio
synthesizer = Synthesizer(osc1_waveform=Waveform.square, osc1_volume=1.0, use_osc2=False, rate=BITRATE)
out_wave = synthesizer.generate_constant_wave(440.0, SAMPLE_LENGTH)

def stream_callback(wave, frame):
    audio_data = (wave * float(2 ** 15 - 1)).astype(np.int16).tobytes()
    index = 0

    def callback(in_data, frame_count, time_info, status):
        nonlocal audio_data
        nonlocal index
        nonlocal frame

        print("got data!")
        frame.append(in_data)
        data_length = frame_count * CHANNELS * 2
        data = audio_data[index:(index+data_length)]
        index += data_length

        return (data, pyaudio.paContinue)

    return callback


frame_data = []


stream_options = {
    "format": FORMAT,
    "channels": CHANNELS,
    "rate": BITRATE,
    "output_device_index": 7,
    "input_device_index": 2,
    "output": True,
    "input": True,
    "stream_callback": stream_callback(out_wave, frame_data)
}

# Open Streams
stream_out = py_audio.open(**stream_options)

stream_out.start_stream()

# wait for stream to finish (5)
while stream_out.is_active():
    time.sleep(0.1)

print("Done!")


stream_out.stop_stream()
stream_out.close()


py_audio.terminate()

Solution

  • "output": True,
    "input": True,
    

    You have to choose one of them. Pyaudio doesn't support both in the same object.