LoginSignup
2
3

More than 3 years have passed since last update.

【Raspi4;サウンド入門】pythonで音入力を安定して記録する♪

Posted at

音入力は何度か取り上げてきたが、今回Rasipi4でも安定してずーっと入出力出来るようになったので、まとめることとしました。
肝心なことは以下の参考1.のとおりです。なお、昨年は参考2.のようなことやって遊んでいました。
今年はこのあと少し違うことやろうと思っています。
【参考】
1.PyAudio Input overflowed
2.【Scipy】FFT、STFTとwavelet変換で遊んでみた♬~⑦リアルタイム・スペクトログラム;高速化

肝心なこと

つまり、読み込むとき以下のおまじないを記載するとオーバーフローが発生しなくなり、延々記録できるようになりました.
※この記事はRasipi4でもこれが解決できたというお話です

# -*- coding:utf-8 -*-
import pyaudio
import matplotlib.pyplot as plt
import numpy as np
import wave
import struct

読み込んだ音を以下の関数でwavファイルで保存する。

def savewav(sig,sk):
    RATE = 44100 #サンプリング周波数
    #サイン波を-32768から32767の整数値に変換(signed 16bit pcmへ)
    swav = [(int(32767*x)) for x in sig] #32767
    #バイナリ化
    binwave = struct.pack("h" * len(swav), *swav)
    #サイン波をwavファイルとして書き出し
    w = wave.Wave_write("./wine/"+str(sk)+".wav")
    params = (1, 2, RATE, len(binwave), 'NONE', 'not compressed')
    w.setparams(params)
    w.writeframes(binwave)
    w.close()

音の入出力をTrueにしています。
音声(センテンス)を入力するので、長め(102400/44100=2.3sec)に録音します。

RATE=44100
p=pyaudio.PyAudio()
N=100
CHUNK=1024*N
stream=p.open(format = pyaudio.paInt16,
        channels = 1,
        rate = RATE,
        frames_per_buffer = CHUNK,
        input = True,
        output = True) # inputとoutputを同時にTrueにする

そしていよいよ連続録音開始です。exception_on_overflowをFalseにしています。sigを32768で除しています。

sk=0
while stream.is_active():
    input = stream.read(CHUNK, exception_on_overflow = False)
    print(len(input))
    sig =[]
    sig = np.frombuffer(input, dtype="int16") / 32768
    savewav(sig,sk)
    fig, (ax1,ax2) = plt.subplots(2,1,figsize=(1.6180 * 4, 4*2))
    lns1=ax1.plot(sig[0:1024] ,".-",color="red")
    ax1.set_xticks(np.linspace(0, 882, 3))
    ax1.set_ylabel("sig0")
    ax1.set_title('short plot')
    lns2=ax2.plot(sig[0:CHUNK], "-",color="blue")
    ax2.set_xticks(np.linspace(0, 44100*2, 5))
    ax2.set_ylabel("sig1")
    ax2.set_title('long plot')
    ax1.grid()
    ax2.grid()
    plt.pause(0.5)
    plt.savefig("./wine/sound_{}.png".format(sk))
    plt.close()
    sk+=1
    output = stream.write(input)

あー、えー、いー。。の連続測定結果
x-軸のメモリ;44100=1sec
sound_1.png
sound_4.png

まとめ

・連続測定が可能になった

・音関係でR-python連携をしたいと思う

2
3
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
2
3