我希望在后台运行python脚本,并在麦克风的阈值达到某个点时使用pyaudio录制声音文件。这适用于双向无线电网络上的监视器。因此我们只想录制传输的音频。
记住任务:
在n%门限阈值上录制音频输入
经过这么多秒的沉默后停止录音
在音频
第2阶段:将数据输入MySQL数据库以搜索录音
我正在查看类似
的文件结构/home/Recodings/2013/8/23/12-33.wav将于2013年8月23日@12:33.wav
记录传输我使用了
中的代码Detect and record a sound with python
我现在离这里有点不知所措,我会非常感激一点指导
谢谢
答案 0 :(得分:8)
前段时间我写了一些步骤
Record audio input on a n% gate threshold
A:为“Silence”启动布尔变量类型,您可以计算RMS以确定Silence是真还是假,设置一个RMS阈值
stop recording after so many seconds of silence
答:你需要计算一个超时,因为它得到帧速率,块大小和你想要多少秒,计算你的超时时间(FrameRate / chunk * Max_Seconds)
keep recording for so many seconds after audio
答:如果沉默是假的==(RMS>阈值)获取音频的最后一块数据(LastBlock)并且只保留记录:-)
Phase 2: input data into MySQL database to search the recordings
答:这一步由您决定
源代码:
import pyaudio
import math
import struct
import wave
#Assuming Energy threshold upper than 30 dB
Threshold = 30
SHORT_NORMALIZE = (1.0/32768.0)
chunk = 1024
FORMAT = pyaudio.paInt16
CHANNELS = 1
RATE = 16000
swidth = 2
Max_Seconds = 10
TimeoutSignal=((RATE / chunk * Max_Seconds) + 2)
silence = True
FileNameTmp = '/home/Recodings/2013/8/23/12-33.wav'
Time=0
all =[]
def GetStream(chunk):
return stream.read(chunk)
def rms(frame):
count = len(frame)/swidth
format = "%dh"%(count)
# short is 16 bit int
shorts = struct.unpack( format, frame )
sum_squares = 0.0
for sample in shorts:
n = sample * SHORT_NORMALIZE
sum_squares += n*n
# compute the rms
rms = math.pow(sum_squares/count,0.5);
return rms * 1000
def WriteSpeech(WriteData):
stream.stop_stream()
stream.close()
p.terminate()
wf = wave.open(FileNameTmp, 'wb')
wf.setnchannels(CHANNELS)
wf.setsampwidth(p.get_sample_size(FORMAT))
wf.setframerate(RATE)
wf.writeframes(WriteData)
wf.close()
def KeepRecord(TimeoutSignal, LastBlock):
all.append(LastBlock)
for i in range(0, TimeoutSignal):
try:
data = GetStream(chunk)
except:
continue
#I chage here (new Ident)
all.append(data)
print "end record after timeout";
data = ''.join(all)
print "write to File";
WriteSpeech(data)
silence = True
Time=0
listen(silence,Time)
def listen(silence,Time):
print "waiting for Speech"
while silence:
try:
input = GetStream(chunk)
except:
continue
rms_value = rms(input)
if (rms_value > Threshold):
silence=False
LastBlock=input
print "hello ederwander I'm Recording...."
KeepRecord(TimeoutSignal, LastBlock)
Time = Time + 1
if (Time > TimeoutSignal):
print "Time Out No Speech Detected"
sys.exit()
p = pyaudio.PyAudio()
stream = p.open(format = FORMAT,
channels = CHANNELS,
rate = RATE,
input = True,
output = True,
frames_per_buffer = chunk)
listen(silence,Time)
答案 1 :(得分:3)
当前的最佳答案有点过时,仅适用于python 2.这是为python 3更新的版本。它将函数包装到类中,并将所有内容打包成一个简单易用的版本。请注意,最高答案和我的脚本之间存在一个关键区别:
顶部的脚本记录了一个文件,然后停止,而我的脚本会在检测到噪声时继续记录,并在记录中将记录转储到目录中。
这两个脚本的主要思想非常相似:
第1步:'倾听'直到rms变得大于阈值
步骤2:开始录制,设置定时器以停止录制,== TIMEOUT_LENGTH
步骤3:如果在定时器超时之前rms再次中断阈值,则重置定时器
步骤4:现在计时器已过期,将录音写入目录并返回步骤1
import pyaudio
import math
import struct
import wave
import time
import os
Threshold = 10
SHORT_NORMALIZE = (1.0/32768.0)
chunk = 1024
FORMAT = pyaudio.paInt16
CHANNELS = 1
RATE = 16000
swidth = 2
TIMEOUT_LENGTH = 5
f_name_directory = r'C:\Users\Jason\PyCharmProjects\AutoRecorder\records'
class Recorder:
@staticmethod
def rms(frame):
count = len(frame) / swidth
format = "%dh" % (count)
shorts = struct.unpack(format, frame)
sum_squares = 0.0
for sample in shorts:
n = sample * SHORT_NORMALIZE
sum_squares += n * n
rms = math.pow(sum_squares / count, 0.5)
return rms * 1000
def __init__(self):
self.p = pyaudio.PyAudio()
self.stream = self.p.open(format=FORMAT,
channels=CHANNELS,
rate=RATE,
input=True,
output=True,
frames_per_buffer=chunk)
def record(self):
print('Noise detected, recording beginning')
rec = []
current = time.time()
end = time.time() + TIMEOUT_LENGTH
while current <= end:
data = self.stream.read(chunk)
if self.rms(data) >= Threshold: end = time.time() + TIMEOUT_LENGTH
current = time.time()
rec.append(data)
self.write(b''.join(rec))
def write(self, recording):
n_files = len(os.listdir(f_name_directory))
filename = os.path.join(f_name_directory, '{}.wav'.format(n_files))
wf = wave.open(filename, 'wb')
wf.setnchannels(CHANNELS)
wf.setsampwidth(self.p.get_sample_size(FORMAT))
wf.setframerate(RATE)
wf.writeframes(recording)
wf.close()
print('Written to file: {}'.format(filename))
print('Returning to listening')
def listen(self):
print('Listening beginning')
while True:
input = self.stream.read(chunk)
rms_val = self.rms(input)
if rms_val > Threshold:
self.record()
a = Recorder()
a.listen()
答案 2 :(得分:0)
所以你只需要getLevel(data)
功能?
一个快速的黑客将是:
def getLevel(data):
sqrsum = 0
for b in data:
b = ord(b)
sqrsum+=b*b
return sqrsum
这应该随着音量而增加。通过反复试验来适当设置您的阈值。
答案 3 :(得分:0)
对于那些因为缺少portaudio.h而在安装pyaudio时遇到问题的人,您可以这样做:
sudo apt-get install portaudio19-dev python-pyaudio python3-pyaudio