前言
贪吃蛇游戏是一款经典的电脑游戏,许多人都曾经玩过。今天我们将使用Python和ttkbootstrap库来实现一个具有美观界面的贪吃蛇游戏,并添加一些额外的功能,使其更具吸引力。
项目运行结果
项目简介
我们的贪吃蛇游戏将包括以下功能:
- 游戏场地是一片矩形区域,蛇可以在这片区域中自由移动。
- 使用
tkinter
的Canvas
控件来绘制蛇、食物和游戏区域。 - 游戏开始时会随机生成一条蛇和一个食物,蛇会自动移动。
- 通过方向键控制蛇的移动方向。
- 当蛇吃到食物时,蛇身长度增加,并重新生成一个食物。
- 当蛇撞到墙壁、石块或自己时,游戏结束。
- 随着得分增加,游戏速度逐渐加快。
- 添加游戏菜单,包括暂停、继续、退出等功能。
- 添加查看历史记录、查看当前日期和时间、查看开发者信息、修改主题和窗口大小等功能。
- 使用
ttkbootstrap
来美化游戏界面。
环境配置
在开始编写代码之前,我们需要确保安装了必要的库。我们将使用tkinter
和ttkbootstrap
库。
pip install ttkbootstrap
代码实现
主体结构
我们首先创建一个SnakeGame
类,包含所有游戏逻辑和界面设置。以下是完整的代码实现:
import tkinter as tk
from tkinter import messagebox, Menu, Toplevel, Text, simpledialog, StringVar
import random
import ttkbootstrap as ttk
from ttkbootstrap.constants import *
import datetime
class SnakeGame:
def __init__(self, root):
self.root = root
self.root.title("贪吃蛇游戏")
self.root.geometry("600x400")
# 使用ttkbootstrap主题
self.style = ttk.Style("cosmo")
self.canvas = tk.Canvas(self.root, bg="white", height=400, width=600)
self.canvas.pack()
self.snake = [(20, 20), (20, 40), (20, 60)]
self.food = None
self.direction = "Down"
self.running = True
self.score = 0
self.level = 1
self.speed = 200
self.create_menu()
self.create_food()
self.bind_keys()
self.update()
def create_menu(self):
menubar = Menu(self.root)
self.root.config(menu=menubar)
game_menu = Menu(menubar, tearoff=0)
menubar.add_cascade(label="游戏", menu=game_menu)
game_menu.add_command(label="暂停", command=self.pause)
game_menu.add_command(label="继续", command=self.resume)
game_menu.add_separator()
game_menu.add_command(label="退出", command=self.root.quit)
help_menu = Menu(menubar, tearoff=0)
menubar.add_cascade(label="帮助", menu=help_menu)
help_menu.add_command(label="游戏帮助", command=self.show_help)
# 历史记录菜单
history_menu = Menu(menubar, tearoff=0)
history_menu.add_command(label="查看历史记录", command=self.show_history)
menubar.add_cascade(label="历史记录", menu=history_menu)
# 查看菜单
view_menu = Menu(menubar, tearoff=0)
view_menu.add_command(label="查看日期", command=self.show_date)
view_menu.add_command(label="查看开发者", command=self.show_developer)
menubar.add_cascade(label="查看", menu=view_menu)
# 修改菜单
edit_menu = Menu(menubar, tearoff=0)
# 修改主题子菜单
theme_menu = Menu(edit_menu, tearoff=0)
style = ttk.Style()
theme_names = style.theme_names() # 以列表的形式返回多个主题名
for theme_name in theme_names:
theme_menu.add_command(label=theme_name, command=lambda t=theme_name: self.change_theme(t))
edit_menu.add_cascade(label="修改主题", menu=theme_menu)
# 修改窗口大小功能
edit_menu.add_command(label="修改窗口大小", command=self.change_window_size)
menubar.add_cascade(label="修改", menu=edit_menu)
def change_theme(self, theme_name):
style = ttk.Style()
style.theme_use(theme_name)
def change_window_size(self):
size = simpledialog.askstring("设置窗口大小", "请输入窗口大小(如800x600):")
if size:
self.root.geometry(size)
def create_food(self):
if self.food:
self.canvas.delete(self.food)
x = random.randint(0, 29) * 20
y = random.randint(0, 19) * 20
self.food = self.canvas.create_rectangle(x, y, x 20, y 20, fill="red")
def bind_keys(self):
self.root.bind("<Up>", self.go_up)
self.root.bind("<Down>", self.go_down)
self.root.bind("<Left>", self.go_left)
self.root.bind("<Right>", self.go_right)
self.root.bind("<space>", self.pause_resume)
self.root.bind("j", self.speed_up)
def go_up(self, event):
if self.direction != "Down":
self.direction = "Up"
def go_down(self, event):
if self.direction != "Up":
self.direction = "Down"
def go_left(self, event):
if self.direction != "Right":
self.direction = "Left"
def go_right(self, event):
if self.direction != "Left":
self.direction = "Right"
def pause_resume(self, event):
if self.running:
self.pause()
else:
self.resume()
def speed_up(self, event):
if self.speed > 50:
self.speed -= 50
def pause(self):
self.running = False
def resume(self):
self.running = True
self.update()
def show_help(self):
messagebox.showinfo("游戏帮助", "这是一个贪吃蛇游戏。使用方向键来控制蛇的移动,吃到豆子增加分数和长度。避免撞到墙壁或蛇身。")
def show_history(self):
history_window = Toplevel(self.root)
history_window.title("历史记录")
history_window.geometry("320x420")
history_text = Text(history_window, wrap="word")
history_text.pack(expand=1, fill="both")
for record in self.history:
history_text.insert("end", record "n")
def show_date(self):
current_date = datetime.datetime.now().strftime("%Y-%m-%d %H:%M:%S")
messagebox.showinfo("当前日期和时间", current_date)
def show_developer(self):
messagebox.showinfo("开发者信息", "开发者: B站 优秀稳妥的小光")
def update(self):
if self.running:
self.move_snake()
self.check_collisions()
self.check_food()
self.root.after(self.speed, self.update)
def move_snake(self):
head_x, head_y = self.snake[0]
if self.direction == "Up":
new_head = (head_x, head_y - 20)
elif self.direction == "Down":
new_head = (head_x, head_y 20)
elif self.direction == "Left":
new_head = (head_x - 20, head_y)
elif self.direction == "Right":
new_head = (head_x 20, head_y)
self.snake = [new_head] self.snake[:-1]
self.canvas.delete("snake")
for segment in self.snake:
self.canvas.create_rectangle(segment[0], segment[1], segment[0] 20, segment[1] 20, fill="green", tags="snake")
def check_collisions(self):
head_x, head_y = self.snake[0]
if head_x < 0 or head_x >= 600 or head_y < 0 or head_y >= 400 or len(self.snake) != len(set(self.snake)):
self.game_over()
def check_food(self):
if self.canvas.coords(self.food) == [self.snake[0][0], self.snake[0][1], self.snake[0][0] 20, self.snake[0][1] 20]:
self.snake.append(self.snake[-1])
self.score = 1
if self.score % 5 == 0:
self.level = 1
self.speed -= 20
self.create_food()
def game_over(self):
self.running = False
messagebox.showinfo("游戏结束", f"你的得分是 {self.score}")
self.root.quit()
if __name__ == "__main__":
root = ttk.Window(themename="cosmo")
game = SnakeGame(root)
root.mainloop()
主要功能详解
界面和菜单
我们使用了ttkbootstrap
来创建美观的界面和菜单。菜单栏包含了游戏控制、查看信息、修改主题等功能。以下是创建菜单的代码:
def create_menu(self):
menubar = Menu(self.root)
self.root.config(menu=menubar)
game_menu = Menu(menubar, tearoff=0)
menubar.add_cascade(label="游戏", menu=game_menu)
game_menu.add_command(label="暂停", command=self.pause)
game_menu.add_command(label="继续", command=self.resume)
game_menu.add_separator()
game_menu.add_command(label="退出", command=self.root.quit)
help_menu = Menu(menubar, tearoff=0)
menubar.add_cascade(label="帮助", menu=help_menu)
help_menu.add_command(label="游戏帮助", command=self.show_help)
# 历史记录菜单
history_menu = Menu(menubar, tearoff=0)
history_menu.add_command(label="查看历史记录", command=self.show_history)
menubar.add_cascade(label="历史记录", menu=history_menu)
# 查看菜单
view_menu = Menu(menubar, tearoff=0)
view_menu.add_command(label="查看日期", command=self.show_date)
view_menu.add_command(label="查看开发者", command=self.show_developer)
menubar.add_cascade(label="查看", menu=view_menu)
# 修改菜单
edit_menu = Menu(menubar, tearoff=0)
# 修改主题子菜单
theme_menu = Menu(edit_menu, tearoff=0)
style = ttk.Style()
theme_names = style.theme_names() # 以列表的形式返回多个主题名
for theme_name in theme_names:
theme_menu.add_command(label=theme_name, command=lambda t=theme_name: self.change_theme(t))
edit_menu.add_cascade(label="修改主题", menu=theme_menu)
# 修改窗口大小功能
edit_menu.add_command(label="修改窗口大小", command=self.change_window_size)
menubar.add_cascade(label="修改", menu=edit_menu)
控制蛇的移动
通过绑定键盘事件来控制蛇的移动方向:
代码语言:javascript复制def bind_keys(self):
self.root.bind("<Up>", self.go_up)
self.root.bind("<Down>", self.go_down)
self.root.bind("<Left>", self.go_left)
self.root.bind("<Right>", self.go_right)
self.root.bind("<space>", self.pause_resume)
self.root.bind("j", self.speed_up)
食物生成和碰撞检测
在游戏中,蛇需要不断地吃到食物来增加长度。以下是生成食物和检测碰撞的代码:
代码语言:javascript复制def create_food(self):
if self.food:
self.canvas.delete(self.food)
x = random.randint(0, 29) * 20
y = random.randint(0, 19) * 20
self.food = self.canvas.create_rectangle(x, y, x 20, y 20, fill="red")
def check_food(self):
if self.canvas.coords(self.food) == [self.snake[0][0], self.snake[0][1], self.snake[0][0] 20, self.snake[0][1] 20]:
self.snake.append(self.snake[-1])
self.score = 1
if self.score % 5 == 0:
self.level = 1
self.speed -= 20
self.create_food()
游戏结束
当蛇撞到墙壁或自身时,游戏结束:
代码语言:javascript复制def game_over(self):
self.running = False
messagebox.showinfo("游戏结束", f"你的得分是 {self.score}")
self.root.quit()
运行游戏
将上述代码保存为一个Python文件并运行,即可开始玩贪吃蛇游戏。通过菜单栏可以进行暂停、继续、退出等操作,也可以查看历史记录、当前日期和开发者信息等。
总结
通过本项目,我们不仅实现了一个功能完整的贪吃蛇游戏,还学会了如何使用ttkbootstrap
来美化界面。希望这个项目对你有所帮助,享受编程的乐趣吧!