当前位置: 首页 > news >正文

端午编程小游戏--艾草驱邪

刚刚过去的端午,参加了学校的一个活动,用python做了一个小游戏,当然这个小游戏还可以继续改进,可以加个bgm什么的......

可以小玩一下

import pygame
import random
import math
import sys
import timepygame.init()
pygame.mixer.init()# 屏幕设置
WIDTH, HEIGHT = 800, 600
screen = pygame.display.set_mode((WIDTH, HEIGHT))
pygame.display.set_caption("端午节:艾草驱邪")
WHITE = (255, 255, 255)
BLACK = (0, 0, 0)
GREEN = (0, 200, 0)
LIGHT_GREEN = (144, 238, 144, 100)
RED = (255, 0, 0)
BLUE = (0, 0, 255)
YELLOW = (255, 255, 0)
PURPLE = (128, 0, 128)
GRAY = (150, 150, 150)font_small = pygame.font.SysFont('SimHei', 20)
font_medium = pygame.font.SysFont('SimHei', 30)
font_large = pygame.font.SysFont('SimHei', 50)FPS = 60
clock = pygame.time.Clock()MENU = 0
PLAYING = 1
GAME_OVER = 2
INSTRUCTIONS = 3
game_state = MENUNORMAL_MODE = 0
SURVIVAL_MODE = 1
TIME_ATTACK_MODE = 2
current_mode = NORMAL_MODEscore = 0
max_moxa = 30
start_time = 0
time_limit = 60
survival_time = 0class Moxa:def __init__(self, x, y, moxa_type="normal"):self.x = xself.y = yself.type = moxa_typeself.radius = 10self.effect_radius = 80 if moxa_type == "normal" else (120 if moxa_type == "strong" else 60) # 不同类型艾草效果范围self.color = GREEN if moxa_type == "normal" else BLUE if moxa_type == "strong" else YELLOW # 不同类型艾草颜色self.active = Truedef draw(self, surface):if self.active:effect_surface = pygame.Surface((self.effect_radius*2, self.effect_radius*2), pygame.SRCALPHA)pygame.draw.circle(effect_surface, (*self.color[:3], 50), (self.effect_radius, self.effect_radius), self.effect_radius)surface.blit(effect_surface, (self.x - self.effect_radius, self.y - self.effect_radius))pygame.draw.circle(surface, self.color, (self.x, self.y), self.radius)class Evil:def __init__(self, x, y, evil_type="normal"):self.x = xself.y = yself.type = evil_typeself.radius = 8 if evil_type == "normal" else (12 if evil_type == "strong" else 6) # 不同类型邪气大小self.color = RED if evil_type == "normal" else PURPLE if evil_type == "strong" else (200, 100, 0) # 不同类型邪气颜色self.speed = 1.5 if evil_type == "normal" else 2.5 if evil_type == "strong" else 1.0 # 不同类型邪气速度self.direction = random.uniform(0, 2 * math.pi)self.change_dir_counter = 0self.change_dir_interval = random.randint(30, 90)self.being_repelled = Falseself.repulsion_strength = 0self.alpha = 255def move(self, moxas):if self.being_repelled and self.repulsion_strength > 0:self.x += math.cos(self.direction) * self.repulsion_strengthself.y += math.sin(self.direction) * self.repulsion_strengthself.repulsion_strength *= 0.95self.radius *= 0.98self.alpha -= 5if self.repulsion_strength < 0.1 or self.alpha <= 0:return Falsereturn Trueself.change_dir_counter += 1if self.change_dir_counter >= self.change_dir_interval:self.direction = random.uniform(0, 2 * math.pi)self.change_dir_counter = 0self.change_dir_interval = random.randint(30, 90)self.x += math.cos(self.direction) * self.speedself.y += math.sin(self.direction) * self.speedif self.x < self.radius:self.x = self.radiusself.direction = math.pi - self.directionelif self.x > WIDTH - self.radius:self.x = WIDTH - self.radiusself.direction = math.pi - self.directionif self.y < self.radius:self.y = self.radiusself.direction = -self.directionelif self.y > HEIGHT - self.radius:self.y = HEIGHT - self.radiusself.direction = -self.directionfor moxa in moxas:if moxa.active:distance = math.sqrt((self.x - moxa.x)**2 + (self.y - moxa.y)**2)if distance < moxa.effect_radius + self.radius:self.being_repelled = Trueself.direction = math.atan2(self.y - moxa.y, self.x - moxa.x)repel_force = 3 if moxa.type == "normal" else (5 if moxa.type == "strong" else 2)self.repulsion_strength = repel_forcereturn Truereturn Truedef draw(self, surface):color_with_alpha = (*self.color, self.alpha)evil_surface = pygame.Surface((self.radius*2, self.radius*2), pygame.SRCALPHA)pygame.draw.circle(evil_surface, color_with_alpha, (self.radius, self.radius), self.radius)surface.blit(evil_surface, (self.x - self.radius, self.y - self.radius))moxas = []
evils = []
evil_spawn_timer = 0
evil_spawn_interval = 60selected_moxa_type = "normal"
show_type_selection = False
type_selection_timer = 0for _ in range(5):x = random.randint(50, WIDTH - 50)y = random.randint(50, HEIGHT - 50)evil_type = random.choice(["normal", "normal", "strong", "weak"]) # 初始邪气以普通为主evils.append(Evil(x, y, evil_type))running = True
while running:for event in pygame.event.get():if event.type == pygame.QUIT:running = Falseif event.type == pygame.KEYDOWN:if event.key == pygame.K_ESCAPE:if game_state == PLAYING:game_state = MENUelif game_state == INSTRUCTIONS:game_state = MENUelif game_state == GAME_OVER:game_state = MENUelse:running = Falseif event.key == pygame.K_r and game_state == GAME_OVER:game_state = PLAYINGscore = 0moxas = []evils = []for _ in range(5):x = random.randint(50, WIDTH - 50)y = random.randint(50, HEIGHT - 50)evils.append(Evil(x, y, "normal"))start_time = time.time()if current_mode == TIME_ATTACK_MODE:start_time = time.time()elif current_mode == SURVIVAL_MODE:survival_time = 0if event.key == pygame.K_1:selected_moxa_type = "normal"show_type_selection = Truetype_selection_timer = 60if event.key == pygame.K_2:selected_moxa_type = "strong"show_type_selection = Truetype_selection_timer = 60if event.key == pygame.K_3:selected_moxa_type = "weak"show_type_selection = Truetype_selection_timer = 60if event.type == pygame.MOUSEBUTTONDOWN and event.button == 1:if game_state == MENU:mouse_x, mouse_y = pygame.mouse.get_pos()button_width, button_height = 200, 50button_y = HEIGHT // 2 - 75if WIDTH // 2 - button_width // 2 <= mouse_x <= WIDTH // 2 + button_width // 2 and button_y <= mouse_y <= button_y + button_height:current_mode = NORMAL_MODEmax_moxa = 30game_state = PLAYINGscore = 0moxas = []evils = []for _ in range(5):x = random.randint(50, WIDTH - 50)y = random.randint(50, HEIGHT - 50)evils.append(Evil(x, y, "normal"))start_time = time.time()button_y += 75if WIDTH // 2 - button_width // 2 <= mouse_x <= WIDTH // 2 + button_width // 2 and button_y <= mouse_y <= button_y + button_height:current_mode = SURVIVAL_MODEmax_moxa = 999game_state = PLAYINGscore = 0moxas = []evils = []for _ in range(5):x = random.randint(50, WIDTH - 50)y = random.randint(50, HEIGHT - 50)evils.append(Evil(x, y, "normal"))survival_time = time.time()button_y += 75if WIDTH // 2 - button_width // 2 <= mouse_x <= WIDTH // 2 + button_width // 2 and button_y <= mouse_y <= button_y + button_height:current_mode = TIME_ATTACK_MODEmax_moxa = 999game_state = PLAYINGscore = 0moxas = []evils = []for _ in range(5):x = random.randint(50, WIDTH - 50)y = random.randint(50, HEIGHT - 50)evils.append(Evil(x, y, "normal"))start_time = time.time()button_y += 75if WIDTH // 2 - button_width // 2 <= mouse_x <= WIDTH // 2 + button_width // 2 and button_y <= mouse_y <= button_y + button_height:game_state = INSTRUCTIONSelif game_state == INSTRUCTIONS:game_state = MENUelif game_state == PLAYING:if current_mode == NORMAL_MODE and len(moxas) >= max_moxa:continue# 放置艾草mouse_x, mouse_y = pygame.mouse.get_pos()moxas.append(Moxa(mouse_x, mouse_y, selected_moxa_type))show_type_selection = Truetype_selection_timer = 60if game_state == PLAYING:evil_spawn_timer += 1if evil_spawn_timer >= evil_spawn_interval:evil_spawn_timer = 0if current_mode == SURVIVAL_MODE:spawn_interval_factor = max(0.5, 1 - survival_time / 300)evil_spawn_interval = int(60 * spawn_interval_factor)if survival_time > 120:evil_type_weights = {"normal": 3, "strong": 5, "weak": 2}else:evil_type_weights = {"normal": 5, "strong": 3, "weak": 2}elif current_mode == TIME_ATTACK_MODE:spawn_interval_factor = max(0.7, 1 - (time.time() - start_time) / time_limit)evil_spawn_interval = int(60 * spawn_interval_factor)if (time.time() - start_time) > time_limit * 0.6:evil_type_weights = {"normal": 4, "strong": 4, "weak": 2}else:evil_type_weights = {"normal": 6, "strong": 2, "weak": 2}else: # NORMAL_MODEevil_type_weights = {"normal": 7, "strong": 2, "weak": 1}evil_type_choices = []for evil_type, weight in evil_type_weights.items():evil_type_choices.extend([evil_type] * weight)new_evil_type = random.choice(evil_type_choices)side = random.randint(0, 3)if side == 0:x = random.randint(0, WIDTH)y = 0elif side == 1:x = WIDTHy = random.randint(0, HEIGHT)elif side == 2:x = random.randint(0, WIDTH)y = HEIGHTelse:x = 0y = random.randint(0, HEIGHT)evils.append(Evil(x, y, new_evil_type))evils_to_remove = []for evil in evils:if not evil.move(moxas):evils_to_remove.append(evil)score += 1for evil in evils_to_remove:evils.remove(evil)if current_mode == SURVIVAL_MODE:survival_time = time.time() - survival_time_start if 'survival_time_start' in locals() else 0if 'survival_time_start' not in locals():survival_time_start = time.time()if current_mode == TIME_ATTACK_MODE:elapsed_time = time.time() - start_timeif elapsed_time >= time_limit:game_state = GAME_OVERif current_mode == NORMAL_MODE and len(moxas) >= max_moxa:game_state = GAME_OVERif show_type_selection:type_selection_timer -= 1if type_selection_timer <= 0:show_type_selection = Falsescreen.fill(BLACK)if game_state == MENU:title_text = font_large.render("端午节:艾草驱邪模拟器", True, WHITE)screen.blit(title_text, (WIDTH // 2 - title_text.get_width() // 2, HEIGHT // 4))button_width, button_height = 200, 50button_x = WIDTH // 2 - button_width // 2button_y = HEIGHT // 2 - 75# 正常模式按钮pygame.draw.rect(screen, GREEN, (button_x, button_y, button_width, button_height))normal_text = font_medium.render("正常模式", True, WHITE)screen.blit(normal_text, (button_x + button_width // 2 - normal_text.get_width() // 2, button_y + button_height // 2 - normal_text.get_height() // 2))# 生存模式按钮button_y += 75pygame.draw.rect(screen, BLUE, (button_x, button_y, button_width, button_height))survival_text = font_medium.render("生存模式", True, WHITE)screen.blit(survival_text, (button_x + button_width // 2 - survival_text.get_width() // 2, button_y + button_height // 2 - survival_text.get_height() // 2))# 限时模式按钮button_y += 75pygame.draw.rect(screen, YELLOW, (button_x, button_y, button_width, button_height))time_text = font_medium.render("限时模式", True, BLACK)screen.blit(time_text, (button_x + button_width // 2 - time_text.get_width() // 2, button_y + button_height // 2 - time_text.get_height() // 2))# 说明按钮button_y += 75pygame.draw.rect(screen, GRAY, (button_x, button_y, button_width, button_height))instructions_text = font_medium.render("游戏说明", True, WHITE)screen.blit(instructions_text, (button_x + button_width // 2 - instructions_text.get_width() // 2, button_y + button_height // 2 - instructions_text.get_height() // 2))elif game_state == INSTRUCTIONS:# 绘制游戏说明title_text = font_large.render("游戏说明", True, WHITE)screen.blit(title_text, (WIDTH // 2 - title_text.get_width() // 2, 50))instructions = ["- 点击屏幕放置艾草,驱散邪气。","- 按数字键 1、2、3 选择不同类型的艾草:","  1: 普通艾草 (绿色,中等效果)","  2: 强效艾草 (蓝色,范围大,驱散力强)","  3: 弱效艾草 (黄色,范围小,驱散力弱)","","- 邪气 (红色/紫色/橙色小点) 会随机移动。","- 当邪气进入艾草的清香范围时,会被驱散。","","- **正常模式**: 限制艾草数量,驱散所有邪气后继续生成,直到放置满艾草数量。","- **生存模式**: 无限艾草,邪气会随时间变强,坚持时间越长分数越高。","- **限时模式**: 无限艾草,在限定时间内驱散尽可能多的邪气。","","按 ESC 返回主菜单。"]y_offset = 120for line in instructions:text = font_small.render(line, True, WHITE)screen.blit(text, (WIDTH // 2 - text.get_width() // 2, y_offset))y_offset += 30elif game_state == PLAYING:for moxa in moxas:moxa.draw(screen)for evil in evils:evil.draw(screen)score_text = font_medium.render(f"得分: {score}", True, WHITE)screen.blit(score_text, (10, 10))if current_mode == NORMAL_MODE:moxa_count_text = font_small.render(f"艾草: {len(moxas)}/{max_moxa}", True, WHITE)screen.blit(moxa_count_text, (10, 50))if show_type_selection:type_names = {"normal": "普通艾草", "strong": "强效艾草", "weak": "弱效艾草"}type_text = font_small.render(f"已选择: {type_names[selected_moxa_type]}", True, WHITE)screen.blit(type_text, (WIDTH - type_text.get_width() - 10, 10))mode_names = {NORMAL_MODE: "正常模式", SURVIVAL_MODE: "生存模式", TIME_ATTACK_MODE: "限时模式"}mode_text = font_small.render(f"模式: {mode_names[current_mode]}", True, WHITE)screen.blit(mode_text, (10, HEIGHT - 30))if current_mode == TIME_ATTACK_MODE:elapsed_time = time.time() - start_timeremaining_time = max(0, time_limit - elapsed_time)time_text = font_small.render(f"剩余时间: {int(remaining_time)}秒", True, WHITE)screen.blit(time_text, (WIDTH - time_text.get_width() - 10, HEIGHT - 30))elif current_mode == SURVIVAL_MODE:survival_time_text = font_small.render(f"生存时间: {int(survival_time)}秒", True, WHITE)screen.blit(survival_time_text, (WIDTH - survival_time_text.get_width() - 10, HEIGHT - 30))elif game_state == GAME_OVER:game_over_text = font_large.render("游戏结束", True, WHITE)screen.blit(game_over_text, (WIDTH // 2 - game_over_text.get_width() // 2, HEIGHT // 3))score_text = font_medium.render(f"最终得分: {score}", True, WHITE)screen.blit(score_text, (WIDTH // 2 - score_text.get_width() // 2, HEIGHT // 2))if current_mode == SURVIVAL_MODE:survival_time_text = font_medium.render(f"生存时间: {int(survival_time)}秒", True, WHITE)screen.blit(survival_time_text, (WIDTH // 2 - survival_time_text.get_width() // 2, HEIGHT // 2 + 50))restart_text = font_small.render("按 R 键重新开始,按 ESC 返回主菜单", True, WHITE)screen.blit(restart_text, (WIDTH // 2 - restart_text.get_width() // 2, HEIGHT * 2 // 3))pygame.display.flip()clock.tick(FPS)pygame.quit()
sys.exit()

相关文章:

  • Unity使用代码分析Roslyn Analyzers
  • 【动画】Unity2D骨骼动画-Animation2D
  • Linux系统编程中的_GNU_SOURCE宏
  • 【Blender】Blender 基础:导入导出
  • Unity中如何播放视频
  • WEB3全栈开发——面试专业技能点P1Node.js / Web3.js / Ethers.js
  • webrtc 在线测试, 如何在线拉流测试
  • 建造者模式深度解析与实战应用
  • Framework开发之IMS逻辑浅析1--关键线程及作用
  • 软件工程的软件生命周期通常分为以下主要阶段
  • [论文阅读] 人工智能+软件工程 | 结对编程中的知识转移新图景
  • 基于 Transformer robert的情感分类任务实践总结之三——FGM
  • day 18进行聚类,进而推断出每个簇的实际含义
  • Boost ASIO 库深入学习(3)
  • Unity VR/MR开发-VR/开发SDK选型对比分析
  • 服务器 | Centos 9 系统中,如何部署SpringBoot后端项目?
  • debian12拒绝海外ip连接
  • DHCP / DHCPv6 原理 / 报文解析 / 配置示例
  • 对比传统引擎,Unity3D 在生产配套中的独特优势
  • 前端打包工具简单介绍
  • 企业网站建设框架图/seo品牌
  • 母婴网站开发/网络营销与直播电商是干什么的
  • 网站建设方式有哪些/今日国内新闻头条
  • 企业手机网站建设市场分析/竞价推广账户竞价托管收费
  • 邢台移动网站建设服务/seo一键优化
  • 寿光专业做网站的公司/西安优化排名推广