python - 在 Python 中使用 Pyglet 和 Tkinter 播放音乐

标签 python user-interface playback pyglet

我想创建一个带有播放和停止按钮的简单图形用户界面,以便在 python 中播放 mp3 文件。我使用包含 2 个按钮(停止和播放)的 Tkinter 创建了一个非常简单的图形用户界面。

我创建了一个执行以下操作的函数:

def playsound () :
    sound = pyglet.media.load('music.mp3')
    sound.play()
    pyglet.app.run()

我将该函数添加为按钮播放的命令。我还做了一个不同的功能来停止音乐:

def stopsound ():
    pyglet.app.exit

我将此功能作为命令添加到第二个按钮。但问题是,当我点击播放时,python 和 gui 卡住了。我可以尝试关闭窗口但它没有关闭,并且停止按钮没有响应。我知道这是因为 pyglet.app.run() 一直执行到歌曲结束,但我该如何防止这种情况呢?当我点击按钮时,我希望 gui 停止播放音乐。关于在哪里可以找到解决方案的任何想法?

最佳答案

您将两个 UI 库混合在一起 - 这本质上并没有什么坏处,但存在一些问题。值得注意的是,他们都需要一个自己的主循环来处理他们的事件。 TKinter 使用它来与桌面和用户生成的事件通信,在这种情况下,pyglet 使用它来播放您的音乐。

这些循环中的每一个都阻止了正常的“自上而下”程序流,正如我们在学习非 GUI 编程时所习惯的那样,程序应该基本上从主循环回调。在这种情况下,在 Tkinter 回调的中间,您启动了 pyglet 主循环(调用 pyglet.app.run),并且控件永远不会返回到 Tkinter 库。

有时,不同库的循环可以在同一进程中共存,不会发生冲突——当然,您要么运行其中一个,要么运行另一个。如果是这样,则可以在不同的 Python 线程中运行每个库的主循环。

如果它们不能一起存在,你将不得不在不同的进程中处理每个库。

因此,让音乐播放器在另一个线程中启动的一种方法可能是:

from threading import Thread

def real_playsound () :
    sound = pyglet.media.load('music.mp3')
    sound.play()
    pyglet.app.run()

def playsound():
    global player_thread
    player_thread = Thread(target=real_playsound)
    player_thread.start()

如果 Tkinter 和 pyglet 可以共存,那应该足以让您的音乐开始。 但是,为了能够控制它,您需要执行更多操作。我的建议是在 pyglet 线程上有一个回调,由 pyglet 大约每秒调用一次——这个回调检查一些全局变量的状态,并根据它们选择停止音乐、更改正在播放的文件等等上。

关于python - 在 Python 中使用 Pyglet 和 Tkinter 播放音乐,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10283067/

相关文章:

python - 将 Pandas 数据框转换为列表列表以输入到 RNN

python - 将代码的基本部分从 C++ 转换为 Python

java - 动态地将 JTable 添加到 JScrollPane

Java GUI - 删除所有组件并重绘

user-interface - Oneiric Ubuntu Server Cloud Guest 11.10 (Ocelot) 如何在亚马逊 AWS 中远程桌面

跨多项 Activity 的 Android 全面防故障音乐服务

android - 每次接听电话时声音都不一样

python - 将字典保存到 json 或从 json 加载字典时出现意外输出

python - 如何反转Python中PriorityQueue的顺序?

flutter - 如何将数据传递到Flutter中的小部件?