防止"弹出"在Pygame.mixer

时间:2015-09-07 09:17:07

标签: python audio pygame

这已经解决了 - 请参见底部的解决方案。

使用pygame.mixer时,每次声音播放完毕(无论是在频道中排队,不排队但仍然通过频道播放,还是直接通过Sound.play()播放),都会发出声音"弹出&# 34;可以听到噪音。有什么方法可以阻止这种情况吗?

示例代码:

import math
import pygame
import array

pygame.mixer.init()

rawArr=[]
for i in range(41000):
    freq1=int(math.sin(i/220.0*math.pi*2)*32767.0)
    if i>40900: freq1=int(freq1*(41000-i)/100.0) #Solution - see Final Solution
    rawArr.append(freq1)

sndArr=array.array('h',rawArr)

snd=pygame.mixer.Sound(sndArr)

snd.play()

更新:声音消失导致没有明显的差异。使用mixer.fadeout(fadeTime)Sound.fadeout(fadeTime)Sound.play(0,maxTime,fadeTime)fadeTime=1,10,100,200,1000maxTime=0,1,10,100,1000进行测试。

更新2:mixer.stop()mixer.pause()都不会删除弹出声音。

更新3:通过缓慢减小音量来实现手动淡出是有效的,具有足够慢的淡入淡出时间,但是对于小于约0.1秒的淡入淡出时间无效。此外,在淡入淡出时,有一系列较小的点击次数,虽然比原来更安静,但仍然可以听到并且比原来的#34; popping"更多。测试代码,附加到原始代码的末尾:

while snd.get_volume():
     snd.set_volume(snd.get_volume()-0.005)
     pygame.time.wait(5)

最终解决方案:感谢用户msw,能够删除"弹出"通过在原始音频数据中实现手动淡出。 if i>40900: freq1=int(freq1*(41000-i)/100.0)被添加到生成循环中 - 这大约0.0024秒的淡入淡出时间几乎是可以在"弹出"之前使用的最短时间。发生了。示例代码已使用固定代码更新。

1 个答案:

答案 0 :(得分:3)

这被称为“噪音的恐惧音响悬崖”。

如果您的数字信号高于0且突然将其切断,则波形必须直线下降到0.当处理模拟信号的人会告诉您时,数字悬崖(原则上)存在所有频率在一定幅度。这种过渡在发送到扬声器时听起来就像一个“流行音乐”。

几乎所有音频都被掌握,因此在样本结束时幅度会逐渐变为零。如果您的样品没有此特性,请在播放时将样品淡化为零。正如OP所指出的那样,即使2.5毫秒的淡入淡出也足以避免流行音乐。