用Python和Pygame打造绚丽烟花效果
摘要
一年一度的春节即将到来,为了渲染节日气氛,绚丽的烟花表演是必不可少的。本文介绍了一款基于Python和Pygame库实现的烟花效果程序。该程序通过模拟烟花的发射、爆炸和粒子轨迹,结合动态文本显示,营造出逼真的烟花表演效果。文章详细解析了程序的核心代码逻辑、关键技术和实现细节,旨在帮助读者理解如何利用Pygame库实现复杂的视觉效果。
1.引言
烟花表演一直是节日庆典中不可或缺的视觉盛宴。如今,通过计算机图形学和编程技术,我们可以在屏幕上重现这种绚丽多彩的效果。本文将通过一个完整的Python程序,展示如何利用Pygame库实现烟花效果,并结合动态文本展示,为用户带来沉浸式的视觉体验。
2.程序概述
该程序的核心功能是模拟烟花的发射、爆炸和粒子轨迹。程序的主要组成部分包括:
• 烟花类(Firework):负责模拟烟花的发射和爆炸效果。
• 粒子类(Particle):模拟烟花爆炸后产生的粒子运动。
• 痕迹类(Trail):用于绘制粒子运动轨迹,增强视觉效果。
• 动态文本显示:在烟花表演过程中动态显示祝福语。
程序运行时,用户将看到烟花从屏幕底部发射、上升并在空中爆炸,同时伴随粒子轨迹和动态文本的显示。
3.核心代码解析
3.1 烟花类(Firework)
烟花类是程序的核心,负责模拟烟花的发射和爆炸效果。以下是其主要功能:
• 初始化:随机生成烟花的颜色和发射位置。
• 更新状态(update):模拟烟花的上升和爆炸过程。当烟花达到最高点时,触发爆炸效果。
• 爆炸(explode):生成大量粒子,模拟烟花爆炸的效果。同时播放烟花音效。
• 显示(show):绘制烟花的当前位置。
• 移除(remove):检查烟花是否已经完全消失,如果是,则从列表中移除。
class Firework:
def __init__(self):
self.colour = (ra.randint(10, 255), ra.randint(10, 255), ra.randint(10, 255))
self.firework = Particle(ra.randint(0, screenWidth), screenHeight, True, self.colour)
self.exploded = False
self.particles = []
self.min_max_particles = vector(666, 999)
def update(self, win):
g = vector(0, ra.uniform(0.15, 0.4))
if not self.exploded:
self.firework.apply_force(g)
self.firework.move()
for tf in self.firework.trails:
tf.show(win)
self.show(win)
if self.firework.vel.y >= 0:
self.exploded = True
self.explode()
else:
for particle in self.particles:
particle.apply_force(vector(g.x + ra.uniform(-1, 1) / 20, g.y / 2 + (ra.randint(1, 8) / 100)))
particle.move()
for t in particle.trails:
t.show(win)
particle.show(win)
def explode(self):
amount = ra.randint(int(self.min_max_particles.x), int(self.min_max_particles.y))
firework_sound.play() # 播放烟花声音
for i in range(amount):
self.particles.append(Particle(self.firework.pos.x, self.firework.pos.y, False, self.colours))
3.2 粒子类(Particle)
粒子类用于模拟烟花爆炸后产生的碎片。以下是其主要功能:
• 初始化:根据是否为烟花主体,设置粒子的初始位置、速度和颜色。
• 应用力(apply_force):模拟重力和空气阻力对粒子的影响。
• 移动(move):更新粒子的位置,并根据其生命周期决定是否移除。
• 显示(show):绘制粒子的当前位置。
• 轨迹更新(trail_update):记录粒子的运动轨迹。
class Particle:
def __init__(self, x, y, firework, colour):
self.firework = firework
self.pos = vector(x, y)
self.vel = vector(ra.uniform(-1, 1), ra.uniform(-1, 1))
self.size = ra.randint(2, 4)
self.colour = colour
self.trails = [Trail(i, self.size, False) for i in range(5)]
def move(self):
self.vel.x *= 0.8
self.vel.y *= 0.8
self.vel += self.acc
self.pos += self.vel
self.acc *= 0
self.decay()
self.trail_update()
def show(self, win):
pg.draw.circle(win, self.colour, (int(self.pos.x), int(self.pos.y)), self.size)
3.3 痕迹类(Trail)
痕迹类用于记录和绘制粒子的运动轨迹,增强视觉效果。其核心功能是根据粒子的当前位置动态更新轨迹。
class Trail:
def __init__(self, n, size, dynamic):
self.pos = vector(-10, -10)
self.dynamic = dynamic
self.colour = trail_colors[n]
self.size = int(size - n / 2)
def get_pos(self, x, y):
self.pos = vector(x, y)
def show(self, win):
pg.draw.circle(win, self.colour, (int(self.pos.x), int(self.pos.y)), self.size)
3.4 动态文本显示
程序在烟花表演过程中动态显示祝福语。通过逐字符渲染文本,实现文本的动态显示效果。
font = pg.font.Font("/System/Library/Fonts/PingFang.ttc", 99)
text1 = "蛇 年 大 吉 ! "
displayed_text1 = ""
for char in text1:
displayed_text1 += char
rendered_text1 = font.render(displayed_text1, True, (255, 10, 20))
screen.blit(rendered_text1, (x, y))
完整源码:
import random
import pygame as pg
import random as ra
import math
pg.init()
pg.display.set_caption("
标签:randint,Python,self,pos,烟花,text1,ra,Pygame
From: https://blog.csdn.net/weixin_41905135/article/details/145321672