python pygame实现贪食蛇

文章目录

很简单的一个例子,开启小游戏制作大门。

步骤

1、安装依赖

python 复制代码
pip install pygame
2、创建snake.py,然后运行即可

代码:

python 复制代码
import pygame
import time
import random

# --- 1. 初始化 Pygame ---
pygame.init()

# --- 2. 定义颜色 (RGB 格式) ---
WHITE = (255, 255, 255)
YELLOW = (255, 255, 102)
BLACK = (0, 0, 0)
RED = (213, 50, 80)
GREEN = (0, 255, 0)
BLUE = (50, 153, 213)

# --- 3. 设置屏幕尺寸 ---
dis_width = 600
dis_height = 400

dis = pygame.display.set_mode((dis_width, dis_height))
pygame.display.set_caption('Pygame 贪吃蛇案例')

# --- 4. 游戏时钟 (控制帧率) ---
clock = pygame.time.Clock()

# --- 5. 定义蛇的参数 ---
snake_block = 10  # 蛇身每一格的大小
snake_speed = 15  # 游戏速度

# --- 6. 设置字体 ---
# 尝试使用系统默认字体,如果失败则使用备用字体
font_style = pygame.font.SysFont("bahnschrift", 25)
score_font = pygame.font.SysFont("comicsansms", 35)


def your_score(score):
    """显示当前分数"""
    value = score_font.render("分数: " + str(score), True, YELLOW)
    dis.blit(value, [0, 0])


def our_snake(snake_block, snake_list):
    """绘制蛇身"""
    for x in snake_list:
        pygame.draw.rect(dis, GREEN, [x[0], x[1], snake_block, snake_block])


def message(msg, color):
    """显示游戏结束信息"""
    mesg = font_style.render(msg, True, color)
    # 将文字居中显示
    text_rect = mesg.get_rect(center=(dis_width / 2, dis_height / 2))
    dis.blit(mesg, text_rect)


def gameLoop():
    """游戏主循环"""
    game_over = False
    game_close = False

    # 蛇的初始位置 (屏幕中心)
    x1 = dis_width / 2
    y1 = dis_height / 2

    x1_change = 0
    y1_change = 0

    snake_List = []
    Length_of_snake = 1

    # 随机生成第一个食物位置
    foodx = round(random.randrange(0, dis_width - snake_block) / 10.0) * 10.0
    foody = round(random.randrange(0, dis_height - snake_block) / 10.0) * 10.0

    while not game_over:

        # --- 游戏结束界面循环 ---
        while game_close == True:
            dis.fill(BLACK)
            message("游戏结束! 按Q-退出 或 C-重玩", RED)
            your_score(Length_of_snake - 1)
            pygame.display.update()

            for event in pygame.event.get():
                if event.type == pygame.KEYDOWN:
                    if event.key == pygame.K_q:
                        game_over = True
                        game_close = False
                    if event.key == pygame.K_c:
                        gameLoop()

        # --- 事件监听 (按键控制) ---
        for event in pygame.event.get():
            if event.type == pygame.QUIT:
                game_over = True
            if event.type == pygame.KEYDOWN:
                if event.key == pygame.K_LEFT:
                    x1_change = -snake_block
                    y1_change = 0
                elif event.key == pygame.K_RIGHT:
                    x1_change = snake_block
                    y1_change = 0
                elif event.key == pygame.K_UP:
                    y1_change = -snake_block
                    x1_change = 0
                elif event.key == pygame.K_DOWN:
                    y1_change = snake_block
                    x1_change = 0

        # --- 边界检测 ---
        if x1 >= dis_width or x1 < 0 or y1 >= dis_height or y1 < 0:
            game_close = True

        # 更新位置
        x1 += x1_change
        y1 += y1_change
        dis.fill(BLACK)  # 背景色

        # --- 绘制食物 ---
        pygame.draw.rect(dis, RED, [foodx, foody, snake_block, snake_block])

        # --- 蛇身逻辑 ---
        snake_Head = []
        snake_Head.append(x1)
        snake_Head.append(y1)
        snake_List.append(snake_Head)

        if len(snake_List) > Length_of_snake:
            del snake_List[0]

        # --- 自身碰撞检测 (吃到自己) ---
        for x in snake_List[:-1]:
            if x == snake_Head:
                game_close = True

        our_snake(snake_block, snake_List)
        your_score(Length_of_snake - 1)

        pygame.display.update()

        # --- 吃食物检测 ---
        if x1 == foodx and y1 == foody:
            foodx = round(random.randrange(0, dis_width - snake_block) / 10.0) * 10.0
            foody = round(random.randrange(0, dis_height - snake_block) / 10.0) * 10.0
            Length_of_snake += 1

        clock.tick(snake_speed)

    pygame.quit()
    quit()


# 启动游戏
if __name__ == "__main__":
    gameLoop()

操作方式

按方向键即可运行起来。

如果game over了,按q键即可退出(如果q无效,看是否是英文模式)。

解读

1、初始化与设置:

pygame.init():必须首先调用,用于初始化所有 Pygame 模块。

snake_block = 10:定义了蛇身和食物的大小。

snake_speed = 15:控制游戏循环的速度,数值越大蛇跑得越快。
2、游戏主循环 (gameLoop):

这是游戏的心脏。只要 game_over 为 False,循环就会一直运行。

clock.tick(snake_speed):这行代码限制了循环每秒运行的次数,从而控制游戏速度。
3、事件监听:

通过 pygame.event.get() 获取用户的操作。

我们监听 pygame.KEYDOWN 事件来判断用户按下了哪个方向键,并改变蛇的坐标变化量 (x1_change, y1_change)。
4、蛇的移动原理:

蛇其实是一个坐标列表 (snake_List)。

每一帧,我们计算蛇头的新坐标,将其加入列表末尾。

如果蛇没有吃到食物,我们就删除列表的第一个元素(蛇尾),这样蛇看起来就在移动。

如果吃到了食物,就不删除蛇尾,蛇的长度自然就增加了。
5、碰撞检测:

撞墙:判断蛇头的坐标是否超出了屏幕的长宽。

撞自己:遍历蛇身列表,看蛇头坐标是否与身体任何一部分重合。

吃食物:判断蛇头坐标是否与食物坐标完全一致。

相关推荐
CryptoPP6 小时前
快速对接东京证券交易所API数据:实战指南与代码示例
开发语言·人工智能·windows·python·信息可视化·区块链
ZC跨境爬虫6 小时前
跟着 MDN 学JavaScript day_7:数学运算与逻辑判断实战测试
开发语言·前端·javascript·学习·ecmascript
探物 AI6 小时前
把 MambaOut 塞进 YOLOv11:会有什么样的反应
python·yolo·计算机视觉
如竟没有火炬7 小时前
最大矩阵——单调栈
数据结构·python·线性代数·算法·leetcode·矩阵
阳区欠7 小时前
【LangChain】LLM基础介绍
开发语言·python·langchain
Cosolar7 小时前
保姆级 CrewAI 教程:从零构建多智能体协作系统
人工智能·python·架构
Jinkxs7 小时前
Java 跨域14-Java 与区块链(Hyperledger)集成
java·开发语言·区块链
GDAL7 小时前
使用 uv 管理 Python 版本
python·uv·版本
真实的菜7 小时前
Redis 从入门到精通(十二):典型业务场景实战 —— 排行榜、限流器、秒杀系统、Session 共享
数据库·redis·python
cup118 小时前
[开源] Meta Assistant / 告别命令行,我为一堆 Python 脚本做了一个 Windows 任务栏的“家”
windows·python·工具·nuitka·脚本运行