代码运行时会异常退出
self.filebox = [] # 存放歌曲文件夹路径
self.filepath = [] # 存放歌曲路径
self.filename = [] # 存放音乐名称
self.playing = False # 是否正在播放
self.get_mouse = True # 鼠标单击播放
self.num = 0 # 正在播放音乐的ID
self.vol = 100 # 音量控制,默认为100
self.botton_active = 'disable'
self.flag = None # 进度条控制
self.mode_choose = '' # 模式选择,默认为顺序播放
self.default_mode = '顺序播放' # 默认模式
self.muted = True # 静音标志
self.value = 100 # 获取暂停时的音量, 默认为100
self.total_length = 0 # 总时长
self.music_path = "" # 单首歌路径
self.current_time = None
self.tag = False # 是否按了上/下一首和暂停
self.now_time = 0 # 当前时长
self.mark = False # 是否操作了上/下一首
self.lb = None # Listbox存放音乐
self.play_state = None # 播放状态
self.musicName = None # 当前播放的音乐
self.pause_resume = None # 暂停/播放设置
# 按钮 (按钮图片路径)
self.botton_Next_Music = None
self.Next_photo = PhotoImage(file='E:/Py File/音乐组件/下一首.png')
self.botton_Music_pause = None
self.play_photo = PhotoImage(file='E:/Py File/音乐组件/播放.png')
self.pause_photo = PhotoImage(file='E:/Py File/音乐组件/暂停.png')
self.botton_Stop_Music = None
self.stop_photo = PhotoImage(file='E:/Py File/音乐组件/停止.png')
self.botton_Up_Music = None
self.Up_photo = PhotoImage(file='E:/Py File/音乐组件/上一首.png')
self.botton_Music_delete = None
self.delete_photo = PhotoImage(file='E:/Py File/音乐组件/删除.png')
self.add_photo = PhotoImage(file='E:/Py File/音乐组件/打开.png')
self.botton_control_voice = None
self.voice_play_photo = PhotoImage(file='E:/Py File/音乐组件/音量.png')
self.voice_mult_photo = PhotoImage(file='E:/Py File/音乐组件/静音.png')
self.optionals_order_photo = PhotoImage(file='E:/Py File/音乐组件/顺序播放.png')
self.optionals_circle_photo = PhotoImage(file='E:/Py File/音乐组件/循环播放.png')
self.optionals_rant_photo = PhotoImage(file='E:/Py File/音乐组件/随机播放.png')
# 对应组件
self.main_Bottons()
def mult(self): # 静音完成
if self.muted: # True可以静音 False表示恢复音量
self.muted = False
self.value_botton['image'] = self.voice_mult_photo
self.control_voice(0)
self.botton_control_voice.set(0)
else:
self.value_botton['image'] = self.voice_play_photo
self.control_voice(self.value)
self.botton_control_voice.set(self.value)
self.muted = True
def control_voice(self, value): # 音量控制完成
self.vol = value
if self.muted:
self.value = value
try:
val = float(self.vol) / 100
pygame.mixer.music.set_volume(val)
except Exception:
pass
def get_length(self): # 获取音乐时长完成
index = self.filename.index(self.musicName)
self.music_path = self.filepath[index]
total = pygame.mixer.Sound(self.music_path)
self.total_length = total.get_length()
mins, secs = divmod(self.total_length, 60)
mins = round(mins)
secs = round(secs)
timeformat = '0{}:{}'.format(mins, secs)
self.length_label['text'] = "总时长" + ': ' + str(timeformat)
# self.now_time = 0
t1 = threading.Thread(target=self.get_current_time, args=(self.total_length,))
t1.start()
def get_current_time(self, length): # 播放进度完成
condition = self.playing and length > self.now_time and self.tag is False
while condition:
if self.pause_resume.get() == '暂停':
time.sleep(1)
self.now_time += 1
if self.now_time >= 60:
now_time_mins, now_time_secs = divmod(self.now_time, 60)
now_time_mins = round(now_time_mins)
now_time_secs = round(now_time_secs)
self.current_time['text'] = "播放进度:" + str(now_time_mins) + ':' + str(now_time_secs)
else:
self.current_time['text'] = "播放进度:" + ':' + str(self.now_time)
else:
continue
def main_Bottons(self):
pygame.mixer.init()
menbar = Menu(root)
# 创建子菜单
menuFile = Menu(menbar)
menuAboutUs = Menu(menbar)
# 将子菜单加入到主菜单
menbar.add_cascade(label="文件(F)", menu=menuFile)
menbar.add_cascade(label="关于(H)", menu=menuAboutUs)
# 添加菜单项
menuFile.add_command(label="打开文件夹", accelerator="ctrl-a", command=self.Music_Load)
menuFile.add_command(label="清空列表", command=self.Clear_music)
menuAboutUs.add_command(label='帮助', command=self.help_music)
root["menu"] = menbar
'''加载主菜单按键'''
# 可变字符串组件
self.pause_resume = tkinter.StringVar(self.master, value='播放')
# 暂停/播放按键
self.botton_Music_pause = ttk.Button(self.master, textvariable=self.pause_resume, command=self.Music_pause,
padding='-4 -4 0 0')
self.botton_Music_pause['image'] = self.play_photo
self.botton_Music_pause.place(x=200, y=45, width=40, height=40)
self.botton_Music_pause['state'] = self.botton_active
# 上一首按键
self.botton_Up_Music = ttk.Button(self.master, text='上一首', command=self.Up_Music, padding='-4 -4 10 0')
self.botton_Up_Music['image'] = self.Up_photo
self.botton_Up_Music.place(x=170, y=50, width=30, height=30)
self.botton_Up_Music['state'] = self.botton_active
# 下一首按键
self.botton_Next_Music = ttk.Button(self.master, text='下一首', command=self.Next_Music, padding='-4 -4 10 0')
self.botton_Next_Music['image'] = self.Next_photo
self.botton_Next_Music.place(x=240, y=50, width=30, height=30)
self.botton_Next_Music['state'] = self.botton_active
# 添加单首按钮
self.botton_Music_add = ttk.Button(self.master, text="添加", image=self.add_photo, command=self.Music_add,
padding='0 -5 0 30')
self.botton_Music_add.place(x=370, y=110, width=50, height=40)
self.botton_Music_add['state'] = 'normal'
# 删除按键
self.botton_Music_delete = ttk.Button(self.master, text='删除', image=self.delete_photo,
command=self.Music_delete, padding='0 -5 0 30')
self.botton_Music_delete.place(x=430, y=110, width=50, height=40)
self.botton_Music_delete['state'] = self.botton_active
# 停止播放音乐
self.botton_Stop_Music = ttk.Button(self.master, text='停止', command=self.Stop_Music, padding='-1 -2 0 0')
self.botton_Stop_Music['image'] = self.stop_photo
self.botton_Stop_Music.place(x=120, y=48, width=35, height=35)
self.botton_Stop_Music['state'] = self.botton_active
'''播放模式选择'''
# 模式选择符
mode = tkinter.StringVar(self.master)
mode.set('模式')
self.optionals = ttk.OptionMenu(self.master, mode, '', '顺序播放', '随机播放', '循环播放',
command=self.mode_chose)
self.optionals['image'] = self.optionals_order_photo
self.optionals.place(x=280, y=38, width=55, height=55)
self.optionals['state'] = 'normal'
# 音量控制
self.botton_control_voice = ttk.Scale(self.master, from_=0, to=100, orient=tkinter.HORIZONTAL,
command=self.control_voice)
self.botton_control_voice.set(self.vol)
# pygame.mixer.music.set_volume(0.5)
self.botton_control_voice.place(x=40, y=123, width=200)
self.botton_control_voice['state'] = self.botton_active
self.value_botton = ttk.Button(self.master, image=self.voice_play_photo, command=self.mult,
padding='-4 -4 10 0')
self.value_botton.place(x=5, y=115, width=30, height=30)
# 播放器状态
self.play_state = tkinter.StringVar(self.master, value='等待播放...')
stateLabel = ttk.Label(self.master, textvariable=self.play_state, foreground='green', anchor='center',
relief=SUNKEN)
# stateLabel.place(x=10, y=4, width=500, height=15)
stateLabel.pack(side=TOP, fill=X)
# 当前音乐
self.musicName = tkinter.StringVar(self.master, value='')
# labelName = tkinter.Label(self.master, textvariable=self.musicName, font=("微软雅黑", 12), fg='#008c8c')
# labelName.place(x=10, y=500, width=400, height=30)
# 进度条显示
self.length_label = ttk.Label(self.master, text="总时长: --:--")
self.length_label.place(y=90, width=140, height=20)
self.current_time = ttk.Label(self.master, text="播放进度: --:--", relief=GROOVE)
self.current_time.pack(side=BOTTOM, fill=X)
# 音乐播放列表
self.var = tkinter.StringVar()
scrolly = Scrollbar(self.master)
scrolly.pack(side=RIGHT, fill=Y)
self.lb = tkinter.Listbox(self.master, listvariable=self.var, yscrollcommand=scrolly.set)
self.lb.place(y=150, width=480, height=300)
scrolly.config(command=self.lb.yview)
# 快捷键绑定
#root.bind('', lambda event: self.add_voice_value())
#root.bind('', lambda event: self.del_voice_value())
root.bind('' , lambda event: self.Music_delete())
root.bind('' , lambda event: self.Music_delete())
root.bind('' , lambda event: self.Up_Music())
root.bind('' , lambda event: self.Next_Music())
root.bind('' , lambda event: self.Stop_Music())
root.bind('' , lambda event: self.Music_Load())
root.bind('' , lambda event: self.Close_windows())
# root.bind('', lambda event: self.Music_play()) # 左键双击播放
# root.mainloop()
def help_music(self):
messagebox.showinfo('帮助', "我也不知道写了个什么玩意,反正能运行。")
def Music_Load(self): # 加载音乐完成!
self.filebox = filedialog.askdirectory()
if self.filebox:
musics = [self.filebox + "/" + music
for music in os.listdir(self.filebox) if music.endswith(('.mp3', '.m4a', '.wav'))]
for each_music in musics:
name = each_music.split('/')[-1]
self.filename.append(name)
self.filepath.append(each_music)
if not self.filebox:
return
# var = tkinter.StringVar()
self.var.set(self.filename)
# self.lb = tkinter.Listbox(self.master, listvariable=var)
# self.lb.place(y=150, width=500, height=300)
self.botton_active = 'normal'
self.botton_Music_delete['state'] = self.botton_active
self.botton_Music_pause['state'] = self.botton_active
self.botton_control_voice['state'] = self.botton_active
def Music_add(self): # 单曲添加完成!
music_path = filedialog.askopenfilename(filetypes=[('音乐', ('*.m4a', '*.wav', '*.mp3'))])
if music_path:
self.filebox.append(os.path.dirname(music_path))
music_name = os.path.basename(music_path)
self.filename.append(music_name)
self.filepath.append(music_path)
index = len(self.filename)
self.lb.insert(index - 1, music_name)
self.botton_active = 'normal'
self.botton_Music_delete['state'] = self.botton_active
self.botton_Music_pause['state'] = self.botton_active
self.botton_control_voice['state'] = self.botton_active
else:
return
def Clear_music(self): # 清空列表完成!
if self.playing:
self.Stop_Music()
self.lb.delete(0, END)
self.filepath = []
self.filename = []
self.filebox = []
self.filepath.clear()
self.filename.clear()
self.musicName = None
self.num = 0
self.botton_Music_delete['state'] = 'disable'
self.botton_Music_pause['state'] = 'disable'
self.botton_Next_Music['state'] = 'disable'
self.botton_Up_Music['state'] = 'disable'
self.botton_Stop_Music['state'] = 'disable'
def mode_chose(self, event): # 模式选择完成!
if event is not None:
self.default_mode = event
if self.default_mode == '随机播放':
self.mode_choose = self.default_mode
self.optionals['image'] = self.optionals_rant_photo
elif self.default_mode == '循环播放':
self.mode_choose = self.default_mode
self.optionals['image'] = self.optionals_circle_photo
else:
self.mode_choose = self.default_mode
self.optionals['image'] = self.optionals_order_photo
# print("模式选择:", self.mode_choose)
def Music_delete(self): # 删除功能完成!
if len(self.filename):
music = self.lb.get('active')
del_music = music.split('/')[-1]
if self.musicName == del_music and self.playing:
self.filename.remove(del_music) # 需要删除的音乐正在播放
self.Stop_Music()
for i in self.filepath:
if i.split('/')[-1] == del_music:
self.filepath.remove(i)
self.lb.delete('active')
elif self.playing: # 音乐正在播放 删除其他的音乐
self.filename.remove(del_music)
for i in self.filepath:
if i.split('/')[-1] == del_music:
self.filepath.remove(i)
self.lb.delete('active')
else:
self.filename.remove(del_music)
for i in self.filepath:
if i.split('/')[-1] == del_music:
self.filepath.remove(i)
self.lb.delete('active')
else:
self.botton_Music_delete['state'] = 'disable'
self.botton_Music_pause['state'] = 'disable'
def Music_play(self):
self.botton_Next_Music['state'] = self.botton_active
self.botton_Up_Music['state'] = self.botton_active
self.botton_Stop_Music['state'] = self.botton_active
self.mode_choose = self.default_mode
# print("播放模式:", self.mode_choose)
if len(self.filepath) != 0:
self.playing = True
while self.playing:
if not pygame.mixer.music.get_busy():
nextMusic = self.filepath[self.num]
# self.music_path = self.filepath[self.num]
if self.get_mouse: # 鼠标单击选择
nextMusic = self.lb.get('active')
temp_list = nextMusic
current_index = self.filename.index(temp_list)
self.num = current_index
nextMusic = self.filepath[current_index]
self.music_path = self.filepath[self.num]
pygame.mixer.music.load(nextMusic)
pygame.mixer.music.play() # 单次播放
self.get_mouse = False
self.mode_choose = self.default_mode
print(self.mode_choose)
# self.playing = True
nextMusic = nextMusic.split('/')[-1]
self.musicName = nextMusic
self.get_length()
self.play_state.set('正在播放:\n{}'.format(self.musicName))
# 播放模式选则
if self.mode_choose == '随机播放':
self.num = random.randint(0, len(self.filepath) - 1)
if self.filename[self.num] == self.musicName:
self.num += 1
elif self.mode_choose == '循环播放':
self.num = self.num
elif self.mode_choose == '顺序播放':
if len(self.filepath) - 1 == self.num:
self.num = 0
else:
self.num += 1
def Music_pause(self): # 暂停音乐完成!
if self.filepath:
if self.pause_resume.get() == '播放':
self.play_state.set('正在播放:\n{}'.format(self.musicName))
self.botton_Music_pause['image'] = self.pause_photo
if not self.filebox:
self.Music_Load()
if not self.filebox:
return
self.playing = True
t = threading.Thread(target=self.Music_play)
t.start()
self.pause_resume.set('暂停')
elif self.pause_resume.get() == '暂停':
pygame.mixer.music.pause()
self.botton_Music_pause['image'] = self.play_photo
self.playing = False
self.play_state.set('暂停中:\n{}'.format(self.musicName))
self.pause_resume.set('继续播放')
elif self.pause_resume.get() == '继续播放' and self.playing is False:
self.botton_Music_pause['image'] = self.pause_photo
pygame.mixer.music.unpause()
self.playing = True
self.play_state.set('正在播放:\n{}'.format(self.musicName))
self.pause_resume.set('暂停')
def Next_Music(self):
if self.filebox:
pygame.mixer.music.stop()
if self.mode_choose == '顺序播放':
if len(self.filepath) == self.num:
self.num = 0
elif self.mode_choose == '随机播放': # 重复赋值了 在Music_Play里面
self.num = random.randint(0, len(self.filepath) - 1)
if self.filename[self.num] == self.musicName:
self.num += 1
elif self.mode_choose == '循环播放':
if len(self.filepath) == self.num + 1:
self.num = 0
else:
self.num += 1
self.pause_resume.set('暂停')
self.music_path = self.filepath[self.num]
self.tag = True
self.playing = False
t = threading.Thread(target=self.Music_play)
t.start()
def Up_Music(self):
if self.filebox:
pygame.mixer.music.stop()
if self.mode_choose == '顺序播放':
if self.num == 0:
self.num = len(self.filepath) - 2
elif self.num == len(self.filepath) - 1:
self.num -= 2
else:
self.num -= 2
elif self.mode_choose == '随机播放':
self.num = random.randint(0, len(self.filepath))
if self.filename[self.num] == self.musicName:
self.num += 1
elif self.mode_choose == '循环播放':
if self.num == 0:
self.num = len(self.filepath) - 1
elif self.num == len(self.filepath) - 1:
self.num -= 1
else:
self.num -= 1
self.music_path = self.filepath[self.num]
self.pause_resume.set('暂停')
self.playing = False
self.tag = True
t = threading.Thread(target=self.Music_play)
t.start()
def Stop_Music(self): # 停止音乐完成!
if self.filebox:
self.playing = False
pygame.mixer.music.unload()
pygame.mixer.music.stop()
self.pause_resume.set('播放')
self.botton_Music_pause['image'] = self.play_photo
self.play_state.set('等待播放...')
self.get_mouse = True
self.tag = True
self.length_label['text'] = "总时长: --:--"
def Close_windows(self): # 关闭后,后台依然在放 bug
self.playing = False
# self.Stop_Music()
time.sleep(0.1)
try:
pygame.mixer.music.stop()
pygame.mixer.quit()
except Exception:
print("关闭异常!")
root.quit()
root.destroy()
shell打印出来的错误信息是啥