国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁(yè) > 編程 > Python > 正文

新年快樂(lè)! python實(shí)現(xiàn)絢爛的煙花綻放效果

2020-02-16 01:00:38
字體:
來(lái)源:轉(zhuǎn)載
供稿:網(wǎng)友

做了一個(gè)Python的小項(xiàng)目。利用了一點(diǎn)python的可視化技巧,做出煙花綻放的效果,文章的靈感來(lái)自網(wǎng)絡(luò)上一位大神。

一.編譯環(huán)境

Pycharm

二.模塊

1.tkinter:這個(gè)小項(xiàng)目的主角,是一個(gè)python圖形模塊。且Python3已經(jīng)自帶了該模塊,不用另外安裝。它有點(diǎn)像java中的swing圖形模塊(由眾多組件集成,組件通過(guò)創(chuàng)建實(shí)例添加,組件通過(guò)坐標(biāo)定位在窗口上)。

2.PIL:Python Imaging Library,是Python平臺(tái)的圖像處理標(biāo)準(zhǔn)模塊。在Python3也是自帶的,在這個(gè)項(xiàng)目中用于背景圖片的導(dǎo)入。

3.time:相信這個(gè)模塊大家都不會(huì)陌生,導(dǎo)入它用來(lái)控制煙花的綻放,墜落及消失時(shí)間。

4.random:隨機(jī)數(shù)模塊,用于生成煙花隨機(jī)坐標(biāo)點(diǎn),隨機(jī)綻放速度,隨機(jī)消失時(shí)間。

5.math:這個(gè)模塊大家應(yīng)該也很熟悉了,導(dǎo)入它的目的是使煙花綻放的粒子以一定角度散開(kāi)。

三.效果


項(xiàng)目最終實(shí)現(xiàn)的效果就跟上面一樣了。

四.代碼

以下是我學(xué)習(xí)(copy)了那位大神的代碼,再添加了一些淺顯的注解。

import tkinter as tkfrom PIL import Image,ImageTkfrom time import time,sleepfrom random import choice,uniform,randintfrom math import sin,cos,radians#重力變量GRAVITY=0.5#listof colors,can choose randomly or use as queue(FIFOcolors=['red','blue','yellow','white','green','orange','purple','seagreen','indigo','cornflowerblue']'''create a class for particles粒子particles are emitted almost randomly on the sky,forming around(組成一個(gè)圈) of circle(a star)before falling and getting removed from canvasAttributes(屬性):id:每個(gè)特定煙花的標(biāo)識(shí)符x,y:煙花的綻放坐標(biāo)vx,vy:煙花的綻放速度total:一顆煙花里的星星總數(shù)age:一顆星星會(huì)在畫布上停留多久color:自我移植cv:畫布lifespan:星星在畫布上停留的最后時(shí)間'''class part:#為每一個(gè)煙花綻放出來(lái)的粒子單獨(dú)構(gòu)建一個(gè)類的對(duì)象  def __init__(self,cv,idx,total,explosion_speed,x=0.,y=0.,vx=0.,vy=0.,size=2.,color='red',lifespan=2,**kwargs):    self.id=idx#每個(gè)煙花的特定標(biāo)識(shí)符    self.x=x#煙花的綻放x軸    self.y=y#煙花的綻放x軸    self.initial_speed=explosion_speed#初速度    self.vx=vx#外放x軸速度    self.vy=vy#外放y軸速度    self.total=total#綻放的粒子數(shù)    self.age=0#已停留時(shí)間    self.color=color#顏色    self.cv=cv#畫布    self.cid=self.cv.create_oval(x-size,y-size,x+size,y+size,fill=self.color)#create_oval()創(chuàng)建一個(gè)橢圓,參數(shù)為左上x,左上y,右下x,右下y,填滿的顏色,該函數(shù)返回一個(gè)id    self.lifespan=lifespan#應(yīng)該停留時(shí)間  def update(self,dt):#更新數(shù)據(jù),已停留時(shí)間增加    self.age+=dt    #粒子膨脹    if self.alive() and self.expand():#如果停留時(shí)間(2s)足夠&&膨脹時(shí)間(1.2s)足夠      move_x=cos(radians(self.id*360/self.total))*self.initial_speed#粒子的x軸繼續(xù)膨脹      move_y=sin(radians(self.id*360/self.total))*self.initial_speed#粒子的y軸繼續(xù)膨脹      self.cv.move(self.cid, move_x, move_y)#根據(jù)id把畫布上的粒子移動(dòng)x和y個(gè)距離      self.vx=move_x/(float(dt)*1000)    #以自由落體墜落    elif self.alive():#如果只是停留時(shí)間足夠,說(shuō)明膨脹到最大了,應(yīng)該準(zhǔn)備下墜      move_x=cos(radians(self.id*360/self.total))#x軸繼續(xù)膨脹      self.cv.move(self.cid,self.vx+move_x,self.vy+GRAVITY*dt)#而y軸按照重力因素做落體運(yùn)動(dòng),但實(shí)際上這個(gè)重力是v而不是a      self.vy+=GRAVITY*dt#更新一下y軸    elif self.cid is not None:#如果粒子的生命周期已過(guò),就將其移除      cv.delete(self.cid)#刪除該粒子對(duì)象      self.cid=None  #定義膨脹效果的時(shí)間幀  def expand(self):    return self.age<=1.2#膨脹時(shí)間小于1.2s  #檢查粒子是否仍在生命周期內(nèi)  def alive(self):#已停留時(shí)間是不是比應(yīng)該停留時(shí)間短    return self.age<=self.lifespan'''煙花模擬回路:遞歸調(diào)用來(lái)在畫布上重復(fù)發(fā)出新的煙火通過(guò)每個(gè)“部件”對(duì)象內(nèi)部的更新協(xié)議,每次調(diào)用時(shí)都要在畫布上創(chuàng)建并繪制列表(星列表,每個(gè)星列表成員都是粒子列表)來(lái)重復(fù)地在畫布上發(fā)出新的焰火'''#生成新的一輪爆炸def simulate(cv):  t=time()#time()函數(shù)返回自1970年后經(jīng)過(guò)的浮點(diǎn)秒數(shù),精確到小數(shù)點(diǎn)后6位  explode_points=[]#爆炸點(diǎn)列表--煙花列表  wait_time=randint(10,100)#隨機(jī)生成一個(gè)int n,10<=n<=100  numb_explode=randint(6,10)#爆炸的個(gè)數(shù)是6~10  #為所有模擬煙花綻放的全部例子創(chuàng)建一列列表  for point in range(numb_explode):#遍歷爆炸的個(gè)數(shù)    objects=[]#這是每個(gè)點(diǎn)的爆炸粒子列表    x_cordi=randint(50,550)#每個(gè)點(diǎn)的爆炸x軸    y_cordi=randint(50,150)#爆炸y軸    speed=uniform(0.5,1.5)#隨機(jī)生成一個(gè)float speed,0.5<=speed<1.5    size=uniform(0.5,3)#隨機(jī)生成一個(gè)float size,0.5<=size<3    color=choice(colors)#choice()是python內(nèi)置函數(shù),隨機(jī)返回元組,列表,或字符串的一個(gè)成員    explosion_speed=uniform(0.2,1)#爆炸的綻放速度也要隨機(jī)出來(lái)    total_particles=randint(10,50)#爆炸出來(lái)的粒子數(shù)半徑也隨機(jī)    for i in range(1,total_particles):#同一個(gè)煙花爆炸出來(lái)的粒子的大小,速度,坐標(biāo)都是相同的      r = part(cv, idx=i, total=total_particles, explosion_speed=explosion_speed, x=x_cordi, y=y_cordi,        vx=speed, vy=speed, color=color, size=size, lifespan=uniform(0.6, 1.75))#把上述參數(shù)帶入,但他們每個(gè)粒子的生存時(shí)間是自己獨(dú)立的      objects.append(r)#添加進(jìn)粒子列表里    explode_points.append(objects)#把該粒子列表添加進(jìn)煙花列表里  total_time=.0#先把時(shí)間置0  #在1.8秒時(shí)間幀內(nèi)保持更新  while total_time<1.8:    sleep(0.01)#讓畫面暫停0.01s    tnew=time()#刷新時(shí)間    t,dt=tnew,tnew-t#時(shí)間等于新時(shí)間,與上次時(shí)間間隔為tnew-t    for point in explode_points:#遍歷煙花列表      for item in point:#遍歷煙花里的粒子列表        item.update(dt)#更新時(shí)間    cv.update()#刷新頁(yè)面    total_time+=dt#為上面的while循環(huán)增加時(shí)間  root.after(wait_time,simulate,cv)#將組件置于其他組件之后,就是放在最頂層,覆蓋下面的,這里遞歸第哦啊用了自己,形成新的一輪爆炸def close(*ignore):  #打開(kāi)模擬循環(huán)并關(guān)閉窗口  global root  root.quit()if __name__=="__main__":  root=tk.Tk()  cv=tk.Canvas(root,height=600,width=700)#繪制一個(gè)畫布  #繪制一個(gè)黑色背景  #cv.create_rectangle(0,0,600,600,fill="black")  #use a nice background image  image=Image.open("L:/PyCharm Community Edition 2018.2.2/Python_program/image.jpg")  photo=ImageTk.PhotoImage(image)  cv.create_image(0,0,image=photo,anchor='nw')#在畫板上繪制一張圖片  cv.pack()#把cv添加進(jìn)去  root.protocol("WM_DELETE_WINDOW",close)  #在0.1s后才開(kāi)始調(diào)用stimulate()  root.after(100,simulate,cv)#調(diào)用stimulate生成一輪煙花綻放效果  root.mainloop()#執(zhí)行root,生成窗口#讓我更加明白了python的一切皆對(duì)象            
發(fā)表評(píng)論 共有條評(píng)論
用戶名: 密碼:
驗(yàn)證碼: 匿名發(fā)表
主站蜘蛛池模板: 浪卡子县| 通榆县| 苏尼特右旗| 星子县| 灌南县| 新郑市| 明星| 绵阳市| 武宣县| 永嘉县| 平安县| 师宗县| 南乐县| 定边县| 敖汉旗| 双峰县| 大埔区| 香格里拉县| 石棉县| 澄迈县| 赣州市| 靖远县| 新郑市| 东海县| 通辽市| 成武县| 乌海市| 桃园市| 余江县| 旬邑县| 德江县| 石台县| 泾源县| 平邑县| 枣阳市| 扶绥县| 建宁县| 顺平县| 广水市| 高唐县| 靖江市|