PyAudioで録音再生する(2018.5.5)

Summary
portaudioとPyAudioをインストールして録音再生ができるようにした。PyAudioのサイトにあったサンプルコードで再生は問題なくできるが、録音は録音開始時にブチッというノイズが録音される。 別のサイトにあったcallbackを使ったnon-blockingなサンプルコードを参考にした結果、雑音も混入することなく録音できた。

PyAudioのインストール

PyAudioのインストールは簡単 以下のようにしてmacOS側にインストールしてからPyCharmのvirtualenv環境にもpyaudioをインストール

$ brew install portaudio
$ pip install pyaudio

$ brew info portaudio
portaudio: stable 19.6.0 (bottled), HEAD
Cross-platform library for audio I/O
http://www.portaudio.com
/usr/local/Cellar/portaudio/19.6.0 (33 files, 452KB) *
  Poured from bottle on 2018-05-05 at 15:46:57
From: https://github.com/Homebrew/homebrew-core/blob/master/Formula/portaudio.rb
==> Dependencies
Build: pkg-config ✔
==> Options
--HEAD
    Install HEAD version

$ pip3 show pyaudio
Name: PyAudio
Version: 0.2.11
Summary: PortAudio Python Bindings
Home-page: http://people.csail.mit.edu/hubert/pyaudio/
Author: Hubert Pham
Author-email: UNKNOWN
License: UNKNOWN
Location: /Library/Frameworks/Python.framework/Versions/3.6/lib/python3.6/site-packages
Requires: 
Required-by: 

sounddeviceパッケージを使うと、どんなサウンドデバイスが存在するか確認できる。

$ pip3 install sounddevice --user

$ pip3 show sounddevice
Name: sounddevice
Version: 0.3.10
Summary: Play and Record Sound with Python
Home-page: http://python-sounddevice.readthedocs.io/
Author: Matthias Geier
Author-email: Matthias.Geier@gmail.com
License: MIT
Location: /Users/harada/Library/Python/3.6/lib/python/site-packages
Requires: CFFI
Required-by: 

$ python3 -m sounddevice
> 0 Built-in Microphone, Core Audio (2 in, 0 out)
< 1 Built-in Output, Core Audio (0 in, 2 out)

wavファイルの再生と録音

wavファイルの再生

wavファイルの再生では、PyAudioのページのサンプルがそのまま動作した。

wavファイル再生のサンプルコード


#!/usr/bin/env python3
# -*- coding: utf-8 -*-

# PyAudio Example: Play a WAVE file
# https://people.csail.mit.edu/hubert/pyaudio/

import pyaudio
import wave
import sys

CHUNK = 1024

if len(sys.argv) < 2:
    print("Plays a wave file.\n\nUsage: %s filename.wav" % sys.argv[0])
    sys.exit(-1)

wf = wave.open(sys.argv[1], 'rb')

p = pyaudio.PyAudio()

stream = p.open(format=p.get_format_from_width(wf.getsampwidth()),
                channels=wf.getnchannels(),
                rate=wf.getframerate(),
                output=True)

data = wf.readframes(CHUNK)

while data != '':
    stream.write(data)
    data = wf.readframes(CHUNK)

stream.stop_stream()
stream.close()

p.terminate()

wavファイルへの録音

wavファイルへの録音では、PyAudioのページのサンプルでは録音されたファイルの先頭にブチッというノイズが入ってしまう結果となった。(これで結構ハマった。)別のサイトにあったcallbackを使ったnon-blockingなサンプルコードを参考にした結果、雑音も混入することなく録音できるようになった。 以下がノイズの入らないコード。

録音のサンプルコード

#!/usr/bin/env python3
# -*- coding: utf-8 -*-

# PyAudio example: Record a few seconds of audio and save to output.wav (callback version)
# https://blog.goo.ne.jp/m4g/m/201411

import pyaudio
import wave
import time

wf = wave.open('./output.wav', 'w')
wf.setsampwidth(2)
wf.setframerate(44100)
wf.setnchannels(2)

p = pyaudio.PyAudio()

input_device_index = 0

def callback(in_data, frame_count, time_info, status):
    wf.writeframes(in_data)
    return (None, pyaudio.paContinue)

stream = p.open( format = p.get_format_from_width(wf.getsampwidth()),\
            channels = wf.getnchannels(),\
            rate = wf.getframerate(),\
            input_device_index = input_device_index,\
            input = True,\
            stream_callback = callback)

stream.start_stream()

time.sleep(5)

stream.stop_stream()
stream.close()

wf.close()
p.terminate()

参考

Back to Index