没有终端的Windows或Mac的Python Bell声音

时间:2017-01-25 16:49:44

标签: python audio terminal stdout

我有一个程序,我想使用内部铃声" \ a"因为它可以在Linux,Windows和Mac上运行,而无需额外的文件。当程序以.py运行时工作得很好但是,我也希望我的程序在没有打开的终端窗口的情况下运行,因此当程序以.pyw运行时它不起作用,因为程序没有连接到stdout。

现在我使用sys.stdout.write(' \ a')来发出警报声,但如果程序没有连接到终端,声音就不会发出声音(并最终导致该程序)。

再次,我想做一些默认为所有终端系统的事情,所以我试图避免包含声音文件并播放它。

2 个答案:

答案 0 :(得分:1)

假设platform.system()为您提供了操作系统的名称,您可以在Linux和Windows上使用以下内容。它为您提供了选择特定声音的自由。

if platform.system () == 'Linux':
    import pyaudio
else:
    import winsound

class BeepBase:
    def __init__ (self):
        self.normalPars = (1000, 0.1)
        self.specialPars = (2100, 0.1)
        self.attentionPars = (400, 0.5)

if platform.system () == 'Linux':
    class Beep (BeepBase):
        def __init__ (self):
            BeepBase.__init__ (self)

            self.sampleFreq = 16000
            self.sampleTime = 1. / self.sampleFreq
            self.attackTime = 0.001
            self.decayTime = 0.015

            self.normalWave = self.getWave (*self.normalPars)
            self.specialWave = self.getWave (*self.specialPars) 
            self.attentionWave = self.getWave (*self.attentionPars)

            # self.pyAudio = pyaudio.PyAudio () # Gives errors

        def done (self):    # Never called, may leak resources
            self.pyAudio.terminate ()

        def getWave (self, frequency, duration):
            wave = ''.join ([
                chr (int (128 + 127 * math.sin (2 * math.pi * frequency * time) * max (0, min (1, min (time/self.attackTime, (duration - time)/self.decayTime)))))
                for time in [self.sampleTime * iSample for iSample in xrange (int (duration / self.sampleTime))]
            ])

            return wave

        def any (self, wave):
            self.stream = self.pyAudio.open (
                format = self.pyAudio.get_format_from_width (1),
                channels = 1,
                rate = self.sampleFreq,
                output = True
            )
            sleep (0.025)
            self.stream.write (wave)
            sleep (0.15)
            self.stream.stop_stream ()
            self.stream.close ()

        def normal (self):
            if main.settings.sound:
                self.any (self.normalWave)

        def special (self):
            if main.settings.sound:
                self.any (self.specialWave)

        def attention (self):
            if main.settings.sound:
                self.any (self.attentionWave)
else:
    class Beep (BeepBase):
        def normal (self):
            if main.settings.sound:
                winsound.Beep (self.normalPars [0], int (self.normalPars [1] * 1000))

        def special (self):
            if main.settings.sound:
                winsound.Beep (self.specialPars [0], int (self.specialPars [1] * 1000))     

        def attention (self):
            if main.settings.sound:
                winsound.Beep (self.attentionPars [0], int (self.attentionPars [1] * 1000))

beep = Beep ()

答案 1 :(得分:1)

我发现forum post表示以下代码段可行:

import Tkinter
Tkinter.Tk().bell()

我不确定它是否有效。我在Linux上,我无法让你的命令在我的机器上运行(也许它被管理员或其他东西禁用)。

请注意,上面的代码段会打开一个Tkinter窗口。我认为隐藏窗口并在播放蜂鸣声后将其关闭(等待一秒或钟()有一种事件监听器,这不是一个大问题。

很抱歉没有详细说明。我只是希望我可以给你一个提示,因为我不能自己测试它。祝好运! :)