pygame编写音乐播放器的实现代码示例
1、准备工作
ide:pycharm
python:3.7
三方包:pygame、pyinstaller、mutagen
几首mp3格式的歌
2、开始
2.1设计说明
1、包含上一首、下一首、暂停/播放、快进/快退、显示当前播放的歌曲名称、显示播放进度条
2、使用pygame.mixer
3、随机播放磁盘某个目录及其子目录下的mp3文件
4、上一首、下一首用随机选择choice(list)实现
5、进度条用按照一定速度移动进度图片来实现,过程中处理暂停、快进
6、歌曲快进播放用pygame.mixer.music.play(0,d_song_time)实现
7、暂停用pygame.mixer.music.pause()实现
8、播放用pygame.mixer.music.unpause()实现
9、用mutagen.mp3来获取mp3信息
2.2代码逻辑
收集某个目录下的所有mp3
#收集某个目录及子目录下的MP3格式的文件
#返回歌曲路径、歌曲时长
#[['E:\\musics\\Mirror_Yohee_128K.mp3',236],['E:\\musics\\overhere_Nobigdyl_128K.mp3',188],['E:\\musics\\尘_薛之谦_128K.mp3',282],['E:\\musics\\aaa\\尘_薛之谦_128K.mp3',282]]
defcollect_songs(fidir):
musics=[]
forroot,dirs,filesinos.walk(fidir):
forfileinfiles:
tmp=[]
iffile.endswith('mp3'):
file=os.path.join(root,file)
song=MP3(file)
duration=round(song.info.length)
tmp.append(file)
tmp.append(duration)
musics.append(tmp)
returnmusics
显示歌曲名称
#把歌曲名字显示在播放器上
defdraw_song_name(music):
#取歌曲名
music_name=music[0].split("\\")[-1]
#print(music_name)
wbk_obj=font_obj.render(music_name,True,(0,255,255))
k_obj=wbk_obj.get_rect()
k_obj.center=(340,200)
screen.blit(wbk_obj,k_obj)
pygame.display.update()
播放歌曲
#随机播放一首歌
defsing_a_song(musics):
#随机选择一首音乐
music=choice(musics)
print(type(musics))
pygame.mixer.music.load(music[0])
pygame.mixer.music.play()
print('开始播放:%s--%s秒'%(music[0],str(music[1])))
returnmusic
显示播放进度
#播放进度显示 defmove(current_time,start_time,pause_duration_time,c_music): ifpause_end_time==0andpause_start_time!=0: duration_time=round(pause_start_time-start_time-pause_duration_time) else: duration_time=round(current_time-start_time-pause_duration_time) song_total_time=c_music[1] speed=(end_x-begin_x)/song_total_time current_x=begin_x+duration_time*speed try: screen.blit(dian,(current_x,148)) pygame.display.update() except: print(current_time) print(start_time) print(pause_duration_time) exit()
快进快退功能
#快进快退功能 defkuaijin(jindu_x,c_music): #要跳转到的距离d_x d_x=jindu_x-begin_x song_total_time=c_music[1] #要跳转到的时间d_song_time d_song_time=round(song_total_time*(d_x/560),1) #将歌曲快进到d_song_time pygame.mixer.music.play(0,d_song_time)
画播放控件
#画播放控件 defdraw_kongjian(is_sing,is_pause): #画进度条 #画一条宽度为2的线,y高度为149,x从40到600,颜色为(0,100,100) pygame.draw.line(screen,(0,100,100),(40,149),(600,149),2) #画播放、暂停按钮 #先画圆边框,半径20 pygame.draw.circle(screen,(0,255,255),(x+80,100),20,2) #画三角形,开始播放 pygame.draw.line(screen,(0,255,255),(x+73.7,107.5),(x+73.7,93),2)#竖线 #如果正在播放且没有暂停 ifis_singandnotis_pause: #隐藏三角形 pygame.draw.line(screen,(0,89,115),(x+73.7,107.5),(x+87.3,100),2) pygame.draw.line(screen,(0,89,115),(x+73.7,93),(x+87.3,100),2) #显示第二条竖线 pygame.draw.line(screen,(0,255,255),(x+83.7,107.5),(x+83.7,93),2) else: #隐藏第二条竖线 pygame.draw.line(screen,(0,89,115),(x+83.7,107.5),(x+83.7,93),2) #显示三角形 pygame.draw.line(screen,(0,255,255),(x+73.7,107.5),(x+87.3,100),2) pygame.draw.line(screen,(0,255,255),(x+73.7,93),(x+87.3,100),2) #画上一首按钮 pygame.draw.line(screen,(0,255,255),(x-10,110),(x-10,90),2) pygame.draw.line(screen,(0,255,255),(x-10,100),(x+10,115),2) pygame.draw.line(screen,(0,255,255),(x-10,100),(x+10,85),2) pygame.draw.line(screen,(0,255,255),(x+10,115),(x+10,85),2) #画下一首按钮 pygame.draw.line(screen,(0,255,255),(x+170,110),(x+170,90),2) pygame.draw.line(screen,(0,255,255),(x+170,100),(x+150,115),2) pygame.draw.line(screen,(0,255,255),(x+170,100),(x+150,85),2) pygame.draw.line(screen,(0,255,255),(x+150,115),(x+150,85),2)
主逻辑
1、画界面
2、如果没有在播放音乐,播放之
3、如果正在播放音乐,刷新播放进度
4、点击了上一首的处理
5、点击了暂停/播放的处理
6、点击了下一首的处理
7、快进/快退的处理
whileTrue:
#第一步画背景
screen.fill((0,0,0))#----------------新添加
#第二步添加背景图片
bg=pygame.image.load(music_bg)
screen.blit(bg,(0,0))
#第四步,画控件
draw_kongjian(is_sing,is_pause)
#print("status:-------"+str(pygame.mixer.music.get_busy()))
#如果正在播放音乐,有bug==当暂停后返回依旧是1
ifpygame.mixer.music.get_busy()==1:
is_sing=True
else:
is_sing=False
#如果没有在播放音乐
ifnotis_sing:
#第五步,开始唱歌
c_music=sing_a_song(musics)
#记录开始播放时间
start_time=time.time()
#暂停时长置为0
pause_start_time=pause_end_time=pause_duration_time=0
#进度条开始位置重置为40
begin_x=40
#第六步,显示歌名
draw_song_name(c_music)
#更改播放状态
is_sing=notis_sing
#如果正在唱歌
else:
#第六步,显示歌名
draw_song_name(c_music)
current_time=time.time()
move(current_time,start_time,pause_duration_time,c_music)
foreventinpygame.event.get():
ifevent.type==QUIT:
pygame.quit()
exit()
ifevent.type==MOUSEBUTTONDOWN:
#如果点击了鼠标左键,取到当前鼠标的坐标
pressed_array=pygame.mouse.get_pressed()
ifpressed_array[0]==1:
mouse_x,mouse_y=event.pos
print('点击了左键,位置为(%d,%d)'%(mouse_x,mouse_y))
#判断点击了哪个按钮
if80mouse_y>145:
kuaijin(mouse_x,c_music)
begin_x=mouse_x
pause_end_time=pause_start_time=pause_duration_time=0
move(current_time,start_time,pause_duration_time,c_music)
is_kuaijin=True
print("快进")
pygame.display.update()
3、效果图
刺猬牛逼!!!
4、完整代码
#-*-coding:utf-8-*-
importos,time,sys
fromsysimportexit
importpygame
frompygame.localsimport*
frommutagen.mp3importMP3
fromrandomimportchoice
defrp(relative_path):
"""Getabsolutepathtoresource,worksfordevandforPyInstaller"""
try:
#PyInstallercreatesatempfolderandstorespathin_MEIPASS
base_path=sys._MEIPASS
exceptException:
base_path=os.path.abspath(".")
returnos.path.join(base_path,relative_path)
pygame.init()
screen=pygame.display.set_mode((640,480),0,32)
pygame.display.set_caption("music")
#初始化音乐播放器
pygame.mixer.init()
#背景图片
music_bg=rp(os.path.join('src','music_bg.jpg'))
#进度点图片
dian_filename=rp(os.path.join('src','dian.jpg'))
dian=pygame.image.load(dian_filename)
#字体
font_obj=pygame.font.Font('C:\Windows\Fonts\simsun.ttc',20)
#偏移量基础值
x=80
#进度条开始x坐标
begin_x=40
#进度条结束x坐标
end_x=600
#是否正在播放歌曲,默认未播放
is_sing=False
#是否暂停,默认未暂停
is_pause=False
#是否快进了
is_kuaijin=False
#快进后x坐标
jindu_x=-1
#定义当前歌曲变量
globalc_music
#定义歌曲开始播放时间、当前时间、开始暂停时间、结束暂停时间
globalstart_time,current_time,pause_start_time,pause_end_time,pause_duration_time
pause_start_time=0
pause_end_time=0
pause_duration_time=0
#把歌曲名字显示在播放器上
defdraw_song_name(music):
#取歌曲名
music_name=music[0].split("\\")[-1]
#print(music_name)
wbk_obj=font_obj.render(music_name,True,(0,255,255))
k_obj=wbk_obj.get_rect()
k_obj.center=(340,200)
screen.blit(wbk_obj,k_obj)
pygame.display.update()
#收集某个目录及子目录下的MP3格式的文件
#返回歌曲路径、歌曲时长
#[['E:\\musics\\Mirror_Yohee_128K.mp3',236],['E:\\musics\\overhere_Nobigdyl_128K.mp3',188],['E:\\musics\\尘_薛之谦_128K.mp3',282],['E:\\musics\\aaa\\尘_薛之谦_128K.mp3',282]]
defcollect_songs(fidir):
musics=[]
forroot,dirs,filesinos.walk(fidir):
forfileinfiles:
tmp=[]
iffile.endswith('mp3'):
file=os.path.join(root,file)
song=MP3(file)
duration=round(song.info.length)
tmp.append(file)
tmp.append(duration)
musics.append(tmp)
returnmusics
musics=collect_songs('E:\\musics')
print(musics)
#随机播放一首歌
defsing_a_song(musics):
#随机选择一首音乐
music=choice(musics)
print(type(musics))
pygame.mixer.music.load(music[0])
pygame.mixer.music.play()
print('开始播放:%s--%s秒'%(music[0],str(music[1])))
returnmusic
#画代表当前进度的圆点
#画一个直径为5个圆点,放在100,150的位置,颜色为(0,255,255)
#dian=pygame.draw.circle(screen,(0,255,255),(begin_x,150),6)
#画播放控件
defdraw_kongjian(is_sing,is_pause):
#画进度条
#画一条宽度为2的线,y高度为149,x从40到600,颜色为(0,100,100)
pygame.draw.line(screen,(0,100,100),(40,149),(600,149),2)
#画播放、暂停按钮
#先画圆边框,半径20
pygame.draw.circle(screen,(0,255,255),(x+80,100),20,2)
#画三角形,开始播放
pygame.draw.line(screen,(0,255,255),(x+73.7,107.5),(x+73.7,93),2)#竖线
#如果正在播放且没有暂停
ifis_singandnotis_pause:
#隐藏三角形
pygame.draw.line(screen,(0,89,115),(x+73.7,107.5),(x+87.3,100),2)
pygame.draw.line(screen,(0,89,115),(x+73.7,93),(x+87.3,100),2)
#显示第二条竖线
pygame.draw.line(screen,(0,255,255),(x+83.7,107.5),(x+83.7,93),2)
else:
#隐藏第二条竖线
pygame.draw.line(screen,(0,89,115),(x+83.7,107.5),(x+83.7,93),2)
#显示三角形
pygame.draw.line(screen,(0,255,255),(x+73.7,107.5),(x+87.3,100),2)
pygame.draw.line(screen,(0,255,255),(x+73.7,93),(x+87.3,100),2)
#画上一首按钮
pygame.draw.line(screen,(0,255,255),(x-10,110),(x-10,90),2)
pygame.draw.line(screen,(0,255,255),(x-10,100),(x+10,115),2)
pygame.draw.line(screen,(0,255,255),(x-10,100),(x+10,85),2)
pygame.draw.line(screen,(0,255,255),(x+10,115),(x+10,85),2)
#画下一首按钮
pygame.draw.line(screen,(0,255,255),(x+170,110),(x+170,90),2)
pygame.draw.line(screen,(0,255,255),(x+170,100),(x+150,115),2)
pygame.draw.line(screen,(0,255,255),(x+170,100),(x+150,85),2)
pygame.draw.line(screen,(0,255,255),(x+150,115),(x+150,85),2)
#播放进度显示
defmove(current_time,start_time,pause_duration_time,c_music):
ifpause_end_time==0andpause_start_time!=0:
duration_time=round(pause_start_time-start_time-pause_duration_time)
else:
duration_time=round(current_time-start_time-pause_duration_time)
song_total_time=c_music[1]
speed=(end_x-begin_x)/song_total_time
current_x=begin_x+duration_time*speed
try:
screen.blit(dian,(current_x,148))
pygame.display.update()
except:
print(current_time)
print(start_time)
print(pause_duration_time)
exit()
#快进快退功能
defkuaijin(jindu_x,c_music):
#要跳转到的距离d_x
d_x=jindu_x-begin_x
song_total_time=c_music[1]
#要跳转到的时间d_song_time
d_song_time=round(song_total_time*(d_x/560),1)
#将歌曲快进到d_song_time
pygame.mixer.music.play(0,d_song_time)
whileTrue:
#第一步画背景
screen.fill((0,0,0))#----------------新添加
#第二步添加背景图片
bg=pygame.image.load(music_bg)
screen.blit(bg,(0,0))
#第四步,画控件
draw_kongjian(is_sing,is_pause)
#print("status:-------"+str(pygame.mixer.music.get_busy()))
#如果正在播放音乐,有bug==当暂停后返回依旧是1
ifpygame.mixer.music.get_busy()==1:
is_sing=True
else:
is_sing=False
#如果没有在播放音乐
ifnotis_sing:
#第五步,开始唱歌
c_music=sing_a_song(musics)
#记录开始播放时间
start_time=time.time()
#暂停时长置为0
pause_start_time=pause_end_time=pause_duration_time=0
#进度条开始位置重置为40
begin_x=40
#第六步,显示歌名
draw_song_name(c_music)
#更改播放状态
is_sing=notis_sing
#如果正在唱歌
else:
#第六步,显示歌名
draw_song_name(c_music)
current_time=time.time()
move(current_time,start_time,pause_duration_time,c_music)
foreventinpygame.event.get():
ifevent.type==QUIT:
pygame.quit()
exit()
ifevent.type==MOUSEBUTTONDOWN:
#如果点击了鼠标左键,取到当前鼠标的坐标
pressed_array=pygame.mouse.get_pressed()
ifpressed_array[0]==1:
mouse_x,mouse_y=event.pos
print('点击了左键,位置为(%d,%d)'%(mouse_x,mouse_y))
#判断点击了哪个按钮
if80mouse_y>145:
kuaijin(mouse_x,c_music)
begin_x=mouse_x
pause_end_time=pause_start_time=pause_duration_time=0
move(current_time,start_time,pause_duration_time,c_music)
is_kuaijin=True
print("快进")
pygame.display.update()
5、打包为exe
请查看另一篇文章
pyinstaller打包exe踩过的坑
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持毛票票。
声明:本文内容来源于网络,版权归原作者所有,内容由互联网用户自发贡献自行上传,本网站不拥有所有权,未作人工编辑处理,也不承担相关法律责任。如果您发现有涉嫌版权的内容,欢迎发送邮件至:czq8825#qq.com(发邮件时,请将#更换为@)进行举报,并提供相关证据,一经查实,本站将立刻删除涉嫌侵权内容。