是否可以在缓冲区完全耗尽之前停止stream.write函数?
当我尝试这样做时,声音会停止,但stream.write函数永远不会返回。
这是一个有效的示例,说明了如何使用小类播放纯净的音调而不阻塞主线程。
import time
import sounddevice as sd
import numpy as np
from threading import Thread
toneduration = 10
samplerate = 44100
frequency = 440
amplitude = 0.5
sd.default.device = 1
sd.default.samplerate = samplerate
sd.default.channels = 2
class Sound(Thread):
def __init__(self):
Thread.__init__(self)
self.stream = sd.OutputStream()
self.stream.start()
vector1 = np.linspace(0, toneduration, toneduration * samplerate)
vector2 = amplitude * np.sin(2 * np.pi * frequency * vector1)
vector3 = np.array([vector2, vector2])
self.soundVector = np.ascontiguousarray(vector3.T, dtype=np.float32)
def run(self):
self.stream.write(self.soundVector)
print('end')
sound = Sound()
sound.start()
time.sleep(3)
sound.stream.close()
我可以播放给定持续时间的声音,但是如果我使用
stream.close()
手动停止流,则该函数不会返回(永远不会显示print('end')
消息,并且线程不会结束)我必须改用回调吗?在那种情况下,我应该如何用numpy数组填充缓冲区?我阅读了文档中的代码示例,但无法弄清楚该怎么做。
最佳答案
我猜最简单的方法是使用play()函数,该函数默认在后台开始播放(使用从底层PortAudio库创建的单独线程调用的回调函数)。
然后,您可以使用stop()函数停止播放。
如果您需要比简单回放NumPy数组更复杂的事情,则可以实现自己的回调函数。
例如,您可以查看play()
函数的实现或examples,例如play_long_file.py。
如前所述,您还可以使用所谓的“阻止” API(使用write()方法)。
无论哪种方式,您通常都会将音频数据分成一系列块。
这样,您可以安排在任何一个块之后停止播放。这也是play()
函数在内部执行的操作。
关于python - 如何在声音设备中停止stream.write函数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/58252258/