1.. currentmodule:: sounddevice 2 3Usage 4===== 5 6First, import the module: 7 8.. code:: python 9 10 import sounddevice as sd 11 12Playback 13-------- 14 15Assuming you have a NumPy array named ``myarray`` holding audio data with a 16sampling frequency of ``fs`` (in the most cases this will be 44100 or 48000 17frames per second), you can play it back with `play()`: 18 19.. code:: python 20 21 sd.play(myarray, fs) 22 23This function returns immediately but continues playing the audio signal in the 24background. You can stop playback with `stop()`: 25 26.. code:: python 27 28 sd.stop() 29 30If you want to block the Python interpreter until playback is finished, 31you can use `wait()`: 32 33.. code:: python 34 35 sd.wait() 36 37If you know that you will use the same sampling frequency for a while, you can 38set it as default using `default.samplerate`: 39 40.. code:: python 41 42 sd.default.samplerate = fs 43 44After that, you can drop the *samplerate* argument: 45 46.. code:: python 47 48 sd.play(myarray) 49 50.. note:: 51 52 If you don't specify the correct sampling frequency, 53 the sound might be played back too slow or too fast! 54 55Recording 56--------- 57 58To record audio data from your sound device into a NumPy array, 59you can use `rec()`: 60 61.. code:: python 62 63 duration = 10.5 # seconds 64 myrecording = sd.rec(int(duration * fs), samplerate=fs, channels=2) 65 66Again, for repeated use you can set defaults using `default`: 67 68.. code:: python 69 70 sd.default.samplerate = fs 71 sd.default.channels = 2 72 73After that, you can drop the additional arguments: 74 75.. code:: python 76 77 myrecording = sd.rec(int(duration * fs)) 78 79This function also returns immediately but continues recording in the background. 80In the meantime, you can run other commands. 81If you want to check if the recording is finished, you should use `wait()`: 82 83.. code:: python 84 85 sd.wait() 86 87If the recording was already finished, this returns immediately; 88if not, it waits and returns as soon as the recording is finished. 89 90By default, the recorded array has the data type ``'float32'`` 91(see `default.dtype`), but this can be changed with the *dtype* argument: 92 93.. code:: python 94 95 myrecording = sd.rec(int(duration * fs), dtype='float64') 96 97Simultaneous Playback and Recording 98----------------------------------- 99 100To play back an array and record at the same time, you can use `playrec()`: 101 102.. code:: python 103 104 myrecording = sd.playrec(myarray, fs, channels=2) 105 106The number of output channels is obtained from ``myarray``, 107but the number of input channels still has to be specified. 108 109Again, default values can be used: 110 111.. code:: python 112 113 sd.default.samplerate = fs 114 sd.default.channels = 2 115 myrecording = sd.playrec(myarray) 116 117In this case the number of output channels is still taken from ``myarray`` 118(which may or may not have 2 channels), 119but the number of input channels is taken from `default.channels`. 120 121Device Selection 122---------------- 123 124In many cases, the default input/output device(s) will be the one(s) you want, 125but it is of course possible to choose a different device. 126Use `query_devices()` to get a list of supported devices. 127The same list can be obtained from a terminal by typing the command :: 128 129 python3 -m sounddevice 130 131You can use the corresponding device ID to select a desired device by assigning 132to `default.device` or by passing it as *device* argument to 133`play()`, `Stream()` etc. 134 135Instead of the numerical device ID, you can also use a space-separated list of 136case-insensitive substrings of the device name 137(and the host API name, if needed). 138See `default.device` for details. 139 140.. code:: python 141 142 import sounddevice as sd 143 sd.default.samplerate = 44100 144 sd.default.device = 'digital output' 145 sd.play(myarray) 146 147Callback Streams 148---------------- 149 150The aforementioned convenience functions `play()`, `rec()` and `playrec()` 151(as well as the related functions `wait()`, `stop()`, `get_status()` and 152`get_stream()`) are designed for small scripts and interactive use 153(e.g. in a Jupyter_ notebook). 154They are supposed to be simple and convenient, 155but their use cases are quite limited. 156 157If you need more control (e.g. continuous recording, realtime processing, ...), 158you should use the lower-level "stream" classes 159(e.g. `Stream`, `InputStream`, `RawInputStream`), 160either with the "non-blocking" callback interface or with the "blocking" 161`Stream.read()` and `Stream.write()` methods, see `Blocking Read/Write Streams`_. 162 163As an example for the "non-blocking" interface, 164the following code creates a `Stream` with a callback function 165that obtains audio data from the input channels 166and simply forwards everything to the output channels 167(be careful with the output volume, because this might cause acoustic feedback 168if your microphone is close to your loudspeakers): 169 170.. code:: python 171 172 import sounddevice as sd 173 duration = 5.5 # seconds 174 175 def callback(indata, outdata, frames, time, status): 176 if status: 177 print(status) 178 outdata[:] = indata 179 180 with sd.Stream(channels=2, callback=callback): 181 sd.sleep(int(duration * 1000)) 182 183The same thing can be done with `RawStream` 184(NumPy_ doesn't have to be installed): 185 186.. code:: python 187 188 import sounddevice as sd 189 duration = 5.5 # seconds 190 191 def callback(indata, outdata, frames, time, status): 192 if status: 193 print(status) 194 outdata[:] = indata 195 196 with sd.RawStream(channels=2, dtype='int24', callback=callback): 197 sd.sleep(int(duration * 1000)) 198 199.. note:: We are using 24-bit samples here for no particular reason 200 (just because we can). 201 202You can of course extend the callback functions 203to do arbitrarily more complicated stuff. 204You can also use streams without inputs (e.g. `OutputStream`) 205or streams without outputs (e.g. `InputStream`). 206 207See :doc:`examples` for more examples. 208 209Blocking Read/Write Streams 210--------------------------- 211 212Instead of using a callback function, 213you can also use the "blocking" methods `Stream.read()` and `Stream.write()` 214(and of course the corresponding methods in `InputStream`, `OutputStream`, 215`RawStream`, `RawInputStream` and `RawOutputStream`). 216 217.. _Jupyter: https://jupyter.org/ 218.. _NumPy: https://numpy.org/ 219