window 下python3 Play_mp3或playsound播放音频问题`
本人在win10 python3下 使用Play_mp3 遇到问题并解决,现记录下来解决python3 Play_mp3或playsound播放音频异常问题以及替代的方法。
一、playsound 或 Play_mp3 使用及问题
其实Play_mp3 就是将playsound 封装了一下
1.1 playsound 的使用
pip install playsound
from playsound import playsound
playsound('xxx.mp3')
1.2 Play_mp3的使用
pip install Play_mp3
其实在安装Play_mp3 时会自动安装playsound 这个库
import Play_mp3
play_mp3.play('xxx.mp3')
Play_mp3 就是对playsound 进行了一下简单的封装,点进play方法里看源码可以看到:
import playsound
def play(filename):
try:
playsound.playsound(filename)
except Exception as ide:
print(f'Error: {ide}')
1.3 出现的异常问题
本人最开始直接使用Play_mp3,第一次执行,出现以下错误 然后搜索到的解决办法是将playsound1.3 换成 playsound1.2 切换后没有上面的错误了,第二次执行,还有报错,如下: Error: sequence item 3: expected str instance, bytes found
又在网上搜这种错误的解决方法,找到的是将playsound.py 源码中的
# def winCommand 方法下
#command = ' '.join(command).decode('utf-16') # 注释掉此行
command = ' '.join(command) # 添加此行
# exceptionMessage 里添加 '\n ' + command +
exceptionMessage = ('\n Error ' + str(errorCode) + ' for command:'
- '\n ' + command.decode('utf-16') +
+ '\n ' + command +
'\n ' + errorBuffer.raw.decode('utf-16').rstrip('\0'))
但是 playsound1.2的源码中没有 command = ’ '.join(command).encode(‘utf-16’) 这一行代码,但是这时候看到了代替方法:
第一种解决办法:
pip install pygame
import pygame
pygame.mixer.init()
pygame.mixer.music.load(pathFile)
pygame.mixer.music.play()
while pygame.mixer.music.get_busy() == True:
continue
第三次执行,利用pygame库的这种方法确实可行,但是它要写这么多行代码,属实是有点繁琐,想到还是改playsound源码简单,这时想到了切换回playsound1.3 看看playsound1.3的源码,切换回后习惯性的点了一下执行, 我的代码如下:
import Play_mp3
import pygame
pathFile = '/mp3/xxx.mp3'
Play_mp3.play(pathFile) # 语言提示
第四次执行,这次执行没有任何错误,声音可以播放,这里不禁疑惑,为什么之前第一次执行的时候会报错,看到多了import pygame这个,然后试探性的注释掉 # import pygame, 这个时候又报了第一次执行时的错误。目前未去探测具体原因,但是这里得出:
第二种解决方法 :
导入pygame库,与Play_mp3一起使用,这里使用的playsound3。亲测有效
第三种解决方法:
遂又探测了改动playsound1.3源码的方法,将playsound.py 文件中的winCommand函数修改为如下即可成功,亲测有效:
def winCommand(*command):
bufLen = 600
buf = c_buffer(bufLen)
# command = ' '.join(command).encode('utf-16')
command = ' '.join(command)
errorCode = int(windll.winmm.mciSendStringW(command, buf, bufLen - 1, 0)) # use widestring version of the function
if errorCode:
errorBuffer = c_buffer(bufLen)
windll.winmm.mciGetErrorStringW(errorCode, errorBuffer, bufLen - 1) # use widestring version of the function
exceptionMessage = ('\n Error ' + str(errorCode) + ' for command:'
'\n ' + command.decode('utf-16') +
'\n ' + command +
'\n ' + errorBuffer.raw.decode('utf-16').rstrip('\0'))
logger.error(exceptionMessage)
raise PlaysoundException(exceptionMessage)
return buf.value
总结
这里给出三种解决方法,第一种pygame代替法,第二种导入pygame库合用方法,第三种修改源码法。这里都是使用的playsound1.3 。
|