代码4
上篇博文中实现方块在网格线中移动,但我们发现方块并没有刚好在网格线边缘移动(会在线上),同时方块如果比作蛇头的话,一般老的贪吃蛇游戏只会90度转弯,此前的代码左右或上下相当于180度,加以修改(判断如果方块左或右移动,只允许按键上下移动,同理...),改完后方块会按照网格线移动
90
import pygame
import sys
import random
pygame.init() # 初始化pygame
clock = pygame.time.Clock()
size = width, height = 960, 640 # 窗口大小
screen = pygame.display.set_mode(size)
game_speed = 120
color = 0, 0, 0 # 设置背景颜色
color2 = 33, 33, 33
square_color = 33, 255, 33 # 小方块颜色
square_color2 = 0, 0, 0
# square_x, square_y = 0, 0 # 小方块坐标
# speed=0.05 # 方块速度
# square_speed_x,square_speed_y=speed,0
# square_size = 20 # 小方块大小
CELL_SIZE = 20
square_rect = pygame.Rect(0, 0, CELL_SIZE, CELL_SIZE)
UP, DOWN, LEFT, RIGHT = (0, -1), (0, 1), (-1, 0), (1, 0)
square_direction = RIGHT # 定义一个初始方向
square_turn = RIGHT
while True:
for event in pygame.event.get(): # 遍历所有事件
if event.type == pygame.QUIT: # 如果单击关闭窗口,则退出
sys.exit() # 执行退出操作
elif event.type == pygame.KEYDOWN:
if square_direction in [LEFT, RIGHT]:
if event.key == pygame.K_UP:
square_turn = UP
elif event.key == pygame.K_DOWN:
square_turn = DOWN
elif square_direction in [UP, DOWN]:
if event.key == pygame.K_LEFT:
square_turn = LEFT
elif event.key == pygame.K_RIGHT:
square_turn = RIGHT
if square_rect.x % CELL_SIZE == 0 and square_rect.y % CELL_SIZE == 0:
square_direction = square_turn
square_rect = square_rect.move(square_direction)
# 防止小方块移出左右边界
if square_rect.left < 0:
square_rect.left = 0
elif square_rect.right > width:
square_rect.right = width
if square_rect.top < 0:
square_rect.top = 0
elif square_rect.bottom > height:
square_rect.bottom = height
# 终端看坐标
print(square_rect.x, square_rect.y, square_direction[0], square_direction[1])
screen.fill(color) # 填充颜色
# pygame.draw.rect(screen, square_color,square_rect)
for i in range(CELL_SIZE, width, CELL_SIZE):
pygame.draw.line(screen, color2, (i, 0), (i, height))
for i in range(CELL_SIZE, height, CELL_SIZE):
pygame.draw.line(screen, color2, (0, i), (width, i))
screen.fill(square_color, square_rect)
screen.fill(square_color2, square_rect.inflate(-4, -4)) # 可以放大或缩小图形
pygame.display.flip() # 更新显示
clock.tick(game_speed)
pygame.quit()
代码5
要生成蛇的身体,为了更加精准的控制移动的时间间隔,继续优化代码
终端显示游戏结束
蛇身
咬到蛇身或撞墙也显示游戏结束
import pygame
import sys
import random
# 设置常数
CELL_SIZE = 20
UP, DOWN, LEFT, RIGHT = (0, -CELL_SIZE), (0, CELL_SIZE), (-CELL_SIZE, 0), (CELL_SIZE, 0)
# 初始化
pygame.init() # 初始化pygame
pygame.display.set_caption('贪吃蛇')
# 窗口对象
clock = pygame.time.Clock()
size = width, height = 960, 640 # 窗口大小
screen = pygame.display.set_mode(size)
game_field = screen.get_rect() # <rect(0,0,960,640)>蛇能运行的整个范围
game_speed = 60
color = 0, 0, 0 # 设置背景颜色
color2 = 33, 33, 33
playing=True
# Snake蛇
square_color = 33, 255, 33 # 小方块颜色
square_color2 = 0, 0, 0
square_color3=255,0,0
square_rect = pygame.Rect(0, 0, CELL_SIZE, CELL_SIZE)
square_direction = RIGHT # 定义一个初始方向
square_turn = RIGHT
square_speed = 10 # 每秒走几个格子
square_delay = 1000 / square_speed # 蛇运动的间隔
square_time2move = pygame.time.get_ticks() + square_delay
square_body=[pygame.Rect(0,0,0,0)]*40 # 蛇的身体
while True:
for event in pygame.event.get(): # 遍历所有事件
if event.type == pygame.QUIT: # 如果单击关闭窗口,则退出
sys.exit() # 执行退出操作
elif event.type == pygame.KEYDOWN:
if square_direction in [LEFT, RIGHT]:
if event.key == pygame.K_UP:
square_turn = UP
elif event.key == pygame.K_DOWN:
square_turn = DOWN
elif square_direction in [UP, DOWN]:
if event.key == pygame.K_LEFT:
square_turn = LEFT
elif event.key == pygame.K_RIGHT:
square_turn = RIGHT
# 更新数据
#1.移动蛇
if pygame.time.get_ticks() >= square_time2move:
square_time2move = pygame.time.get_ticks() + square_delay
square_body=[square_rect]+square_body #增加一节身体
square_body.pop() #截取尾部
square_direction = square_turn
square_rect = square_rect.move(square_direction)
#2.判断游戏是否结束
if playing:
#撞墙
if not game_field.contains(square_rect):
playing=False
#撞身体
for cell in square_body:
if square_rect==cell:
playing = False
if not playing:
print('游戏结束!!!')
# 更新画面
if playing:
# 终端看坐标
output = "坐标:%r 速度:%r 范围:%r FPS:%0.2f 时间:%r"
print(output % (
square_rect, square_direction, game_field.contains(square_rect), clock.get_fps(), pygame.time.get_ticks()))
# 填充颜色
screen.fill(color)
# 画格子
for i in range(CELL_SIZE, width, CELL_SIZE):
pygame.draw.line(screen, color2, (i, 0), (i, height))
for i in range(CELL_SIZE, height, CELL_SIZE):
pygame.draw.line(screen, color2, (0, i), (width, i))
# 画蛇
# 1.画头
screen.fill(square_color, square_rect)
screen.fill(square_color3, square_rect.inflate(-4, -4)) # 可以放大或缩小图形
# 2.画身体
for cell in square_body:
screen.fill(square_color,cell)
screen.fill(square_color2, cell.inflate(-4,-4))
# 更新窗口内容
pygame.display.flip() # 更新显示
clock.tick(game_speed)
# 退出
pygame.quit()
至此我们已经实现蛇身移动
我们可以想象到后续代码量很多,这种编程方式面向过程,不便于理解和代码的重复利用率,灵活性
所以我们将重新打乱面向对象去编程,这里不要感到繁琐,
面向对象去写后更加便于我们理解和后续学习
面向过程
面向对象
后续会发布面向对象的代码,制作不易,点个关注
本人也是根据哔哩哔哩视频学习