在Python中,使用pygame库可以轻松地创建图形和动画效果,非常适合制作各种游戏和视觉展示。今天,我们将一起探索如何使用pygame来制作一个简单的烟花展示程序。这个程序将模拟烟花在夜空中绽放的壮丽景象,通过随机生成的粒子来模拟烟花的爆炸效果。
准备工作
首先,确保你已经安装了pygame库。如果还没有安装,可以通过pip命令来安装:
pip install pygame
导入必要的库
import pygame # 导入pygame库,用于处理图形和事件
import random # 导入random库,用于生成随机数
import math # 导入math库,用于数学运算
import sys # 导入sys库,用于控制程序的退出
初始化pygame和设置窗口
# 初始化pygame
pygame.init()
# 设置窗口
WIDTH, HEIGHT = 640, 480 # 设置窗口的宽度和高度
screen = pygame.display.set_mode((WIDTH, HEIGHT)) # 创建一个窗口对象
pygame.display.set_caption('Python 烟花展示') # 设置窗口的标题
定义颜色和粒子类
# 定义新的颜色列表,并打乱它
COLORS = [(255, 165, 0), (128, 0, 128), (0, 255, 127), (255, 140, 0), (0, 191, 255), (255, 32, 128), (64, 224, 208)]
random.shuffle(COLORS)
# 定义粒子类
class Particle:
def __init__(self, x, y, dx, dy, color, size=3, alpha=255):
self.x = x # 粒子的x坐标
self.y = y # 粒子的y坐标
self.dx = dx # 粒子在x方向上的速度
self.dy = dy # 粒子在y方向上的速度
self.color = color # 粒子的颜色(RGB格式)
self.size = size # 粒子的大小
self.alpha = alpha # 粒子的透明度
def update(self):
self.x += self.dx # 更新粒子的x坐标
self.y += self.dy # 更新粒子的y坐标
self.dy += 0.1 # 粒子受到重力的影响,y方向速度增加
self.alpha -= 5 # 粒子的透明度逐渐降低
def draw(self, surface):
# 注意:pygame的draw函数不支持直接的RGBA颜色,所以这里仅使用RGB并忽略alpha值,通过透明度处理实现淡出效果
pygame.draw.circle(surface, (self.color[0], self.color[1], self.color[2]), (int(self.x), int(self.y)), self.size)
定义烟花类
# 定义烟花类
class Firework:
def __init__(self, x, y, color, particle_count=50):
self.x = x # 烟花的x坐标
self.y = y # 烟花的y坐标
self.color = color # 烟花的颜色
self.particles = [self.create_particle() for _ in range(particle_count)] # 初始化烟花的粒子列表
def create_particle(self):
angle = random.uniform(0, 2 * math.pi) # 随机生成一个角度
speed = random.uniform(1, 6) # 随机生成一个速度
dx = speed * math.cos(angle) # 计算x方向上的速度分量
dy = speed * math.sin(angle) # 计算y方向上的速度分量
size = random.randint(2, 6) # 随机生成粒子的大小
return Particle(self.x, self.y, dx, dy, self.color, size)
def update(self):
self.particles = [p for p in self.particles if p.alpha > 0] # 过滤出仍然可见的粒子
for particle in self.particles:
particle.update() # 更新每个粒子的状态
def draw(self):
for particle in self.particles:
particle.draw(screen) # 将粒子绘制到屏幕上
主循环和烟花生成
# 烟花列表
fireworks = []
# 主循环
clock = pygame.time.Clock()
running = True
while running:
for event in pygame.event.get():
if event.type == pygame.QUIT:
running = False
screen.fill((0, 0, 0)) # 清屏
if random.random() < 0.05: # 以较低的概率生成新的烟花
x = random.randint(0, WIDTH)
y = random.randint(HEIGHT // 2, HEIGHT)
color = random.choice(COLORS)
fireworks.append(Firework(x, y, color, particle_count=random.randint(30, 70)))
for firework in fireworks[:]: # 遍历烟花列表的副本
firework.update()
if not firework.particles:
fireworks.remove(firework)
firework.draw()
pygame.display.flip() # 更新屏幕
clock.tick(60) # 设置帧率为60帧/秒
pygame.quit() # 退出pygame
sys.exit() # 退出程序
完整代码
import pygame # 导入pygame库,用于处理图形和事件
import random # 导入random库,用于生成随机数
import math # 导入math库,用于数学运算
import sys # 导入sys库,用于控制程序的退出
# 初始化pygame
pygame.init() # 初始化pygame模块,为使用pygame功能做准备
# 设置窗口
WIDTH, HEIGHT = 640, 480 # 设置窗口的宽度和高度
screen = pygame.display.set_mode((WIDTH, HEIGHT)) # 创建一个窗口对象
pygame.display.set_caption('Python 烟花展示') # 设置窗口的标题
# 定义新的颜色列表,并打乱它
COLORS = [(255, 165, 0), (128, 0, 128), (0, 255, 127), (255, 140, 0), (0, 191, 255), (255, 32, 128), (64, 224, 208)]
random.shuffle(COLORS) # 使用random.shuffle函数打乱颜色列表
# 定义粒子类
class Particle:
def __init__(self, x, y, dx, dy, color, size=3, alpha=255):
"""初始化粒子对象,包括位置、速度、颜色、大小和透明度"""
self.x = x # 粒子的x坐标
self.y = y # 粒子的y坐标
self.dx = dx # 粒子在x方向上的速度
self.dy = dy # 粒子在y方向上的速度
self.color = color # 粒子的颜色(RGBA格式,但这里只使用RGB)
self.size = size # 粒子的大小
self.alpha = alpha # 粒子的透明度
def update(self):
"""更新粒子的位置和透明度"""
self.x += self.dx # 更新粒子的x坐标
self.y += self.dy # 更新粒子的y坐标
self.dy += 0.1 # 粒子受到重力的影响,y方向速度增加
self.alpha -= 5 # 粒子的透明度逐渐降低
def draw(self, surface):
"""绘制粒子到指定的表面上,考虑透明度"""
# 注意:pygame的draw函数不支持直接的RGBA颜色,所以这里仅使用RGB并忽略alpha值,通过透明度处理实现淡出效果
pygame.draw.circle(surface, (self.color[0], self.color[1], self.color[2]), (int(self.x), int(self.y)), self.size)
# 定义烟花类
class Firework:
def __init__(self, x, y, color, particle_count=50):
"""初始化烟花对象,包括位置、颜色、粒子数量,并创建初始粒子"""
self.x = x # 烟花的x坐标
self.y = y # 烟花的y坐标
self.color = color # 烟花的颜色
self.particles = [self.create_particle() for _ in range(particle_count)] # 初始化烟花的粒子列表
def create_particle(self):
"""创建一个新的粒子,随机确定其初始速度和方向"""
angle = random.uniform(0, 2 * math.pi) # 随机生成一个角度
speed = random.uniform(1, 6) # 随机生成一个速度
dx = speed * math.cos(angle) # 计算x方向上的速度分量
dy = speed * math.sin(angle) # 计算y方向上的速度分量
size = random.randint(2, 6) # 随机生成粒子的大小
return Particle(self.x, self.y, dx, dy, self.color, size)
def update(self):
"""更新烟花的所有粒子,并移除已经完全透明的粒子"""
self.particles = [p for p in self.particles if p.alpha > 0] # 过滤出仍然可见的粒子
for particle in self.particles:
particle.update() # 更新每个粒子的状态
def draw(self):
"""绘制烟花的所有粒子"""
for particle in self.particles:
particle.draw(screen) # 将粒子绘制到屏幕上
# 烟花列表
fireworks = []
# 主循环
clock = pygame.time.Clock() # 创建一个Clock对象用于控制帧率
running = True # 控制主循环的标志位
while running:
for event in pygame.event.get(): # 遍历所有事件
if event.type == pygame.QUIT: # 如果事件是关闭窗口
running = False # 退出主循环
screen.fill((0, 0, 0)) # 用黑色填充整个屏幕,清屏
if random.random() < 0.05: # 以较低的概率生成新的烟花
x = random.randint(0, WIDTH) # 随机生成烟花的x坐标
y = random.randint(HEIGHT // 2, HEIGHT) # 随机生成烟花的y坐标(从屏幕中间偏上到顶部)
color = random.choice(COLORS) # 从打乱后的颜色列表中随机选择一个颜色
fireworks.append(Firework(x, y, color, particle_count=random.randint(30, 70))) # 创建一个新的烟花对象并添加到列表中
for firework in fireworks[:]: # 遍历烟花列表的副本(避免在迭代过程中修改列表)
firework.update() # 更新烟花的状态
if not firework.particles: # 如果烟花的粒子列表为空(即所有粒子都已消失)
fireworks.remove(firework) # 从列表中移除该烟花
firework.draw() # 绘制烟花
pygame.display.flip() # 更新整个屏幕的内容
clock.tick(60) # 设置帧率为60帧/秒
pygame.quit() # 退出pygame
sys.exit() # 退出程序
推荐阅读
Python基础
Python全网最全基础课程笔记(一)——基础入门
Python全网最全基础课程笔记(二)——变量
Python全网最全基础课程笔记(三)——所有运算符+运算符优先级
Python全网最全基础课程笔记(四)——基本数据类型
Python全网最全基础课程笔记(五)——选择结构+Python新特性Match
Python全网最全基础课程笔记(六)——循环结构
Python全网最全基础课程笔记(七)——列表,跟着思维导图和图文来学习,爆肝2w字,无数代码案例!
Python全网最全基础课程笔记(八)——字典,跟着思维导图和图文来学习,爆肝2w字,无数代码案例!
Python全网最全基础课程笔记(九)——集合,跟着思维导图和图文来学习,爆肝2w字,无数代码案例!
Python全网最全基础课程笔记(十)——元组,跟着思维导图和图文来学习,爆肝2w字,无数代码案例!
Python全网最全基础课程笔记(十一)——字符串所有操作,跟着思维导图和图文来学习,爆肝2w字,无数代码案例!
Python全网最全基础课程笔记(十二)——函数,跟着思维导图和图文来学习,爆肝2w字,无数代码案例!
Python全网最全基础课程笔记(十三)——作用域,跟着思维导图和图文来学习,爆肝2w字,无数代码案例!
Flink入门到就业
2024年最新Flink教程,从基础到就业,大家一起学习–基础篇
2024年最新Flink教程,从基础到就业,大家一起学习–入门篇
2024年最新Flink教程,从基础到就业,大家一起学习–Flink集群部署
2024年最新Flink教程,从基础到就业,大家一起学习–flink部署和集群部署(从本地测试到公司生产环境如何部署项目源码)
2024年最新Flink教程,从基础到就业,大家一起学习–Flink运行架构底层源码详解+实战
2024年最新Flink教程,从基础到就业,大家一起学习–Flink DataStream API-第一篇+源码讲解