20193312 2021-6 《Python程序设计》综合实验报告
课程:《Python程序设计》
班级: 1933
姓名: 朱文昱
学号:20193312
实验教师:王志强
实验日期:2020年6月24日
必修/选修: 公选课
1.实验内容
内容:
贪吃蛇小游戏制作
要求:
能用电脑的方向键控制蛇的移动
在蛇移动的过程中随机生成食物
当蛇吃到食物后会变长
如果蛇头触碰到了自己的身体则判定死亡, 游戏结束
2. 实验过程及结果
引用库:pygame(游戏套件库)、random
定义消息窗口大小、窗口色调、窗口显示的标题、游戏区域网格大小划分
蛇的出生位置和蛇头的定义、初始时随机生成的食物位置:
caption_width = 500 # 宽度500像素点
caption_height = 500 # 高度500像素点
white_color = (255, 255, 255) # 白色rgb
black_color = (0, 0, 0)
game_title = '贪吃蛇小游戏实现' # 消息窗口主标题
cell = 10 # 网格大小为10×10
snake_init_pos = [[250, 250], [240, 250], [230, 250], [220, 250]] # 蛇的初始位置(初始时长度为四格)
food_pos = [random.randrange(1, 50) * 10, random.randrange(1, 50) * 10] # 食物初始随机位置
head_pos = [250, 250] #蛇头位置
将定义好的构建消息窗口大小导入变量中:
caption = pygame.display.set_mode((caption_width, caption_height))
pygame.display.set_caption(game_title)
再采用主循环捕获键盘控制消息的方式实现用户对蛇的控制:
while 1:
for event in pygame.event.get():
if event.type == pygame.QUIT:
pygame.quit()
if event.type == pygame.KEYDOWN:
if event.key == pygame.K_LEFT:
head_pos[0] -= cell
change_direction(head_pos)
elif event.key == pygame.K_RIGHT:
head_pos[0] += cell
change_direction(head_pos)
elif event.key == pygame.K_UP:
head_pos[1] -= cell
change_direction(head_pos)
elif event.key == pygame.K_DOWN:
head_pos[1] += cell
change_direction(head_pos)
此时蛇能够在用户的操作下进行三个方向的移动了,但是在第一个食物被吃掉后,无法随机生成新的食物,故需要进一步加入食物的循环随机生成,但考虑到食物的生成和用户的操作有关,既在蛇吃掉了上一个食物,新的食物才能生成,不然界面马上就会被食物填满了,所以将食物生成语句放在了蛇头的位置判断中,这里的位置判断同时实现了蛇咬到自己和蛇头撞到墙壁上的死亡判断:
def change_direction(head_pos):
global food_pos
snake_init_pos.insert(0, list(head_pos))
if head_pos != food_pos:
snake_init_pos.pop()
else:
food_pos = [random.randrange(1, 50) * 10, random.randrange(1, 50) * 10]
if hit_the_self() or hit_the_wall(head_pos):
# 判定死亡,直接退出游戏
pygame.quit()
游戏运行:
蛇和食物的初始位置:
当蛇吃了一定量的食物后:
则游戏功能基本实现。
以下为游戏的完整源代码:
#!/usr/bin/python3
# -*- coding: utf-8 -*-
# @Time : 2021/6/20 22:07
# @Author : 朱文昱
# @FileName: final test1.py
# @Software: PyCharm
import pygame
import random
caption_width = 500 # 宽度500像素点
caption_height = 500 # 高度500像素点
white_color = (255, 255, 255) # 白色rgb
black_color = (0, 0, 0)
game_title = '贪吃蛇小游戏实现' # 消息窗口主标题
cell = 10 # 网格大小为10×10
snake_init_pos = [[250, 250], [240, 250], [230, 250], [220, 250]] # 蛇的初始位置(初始时长度为四格)
food_pos = [random.randrange(1, 50) * 10, random.randrange(1, 50) * 10] # 食物初始随机位置
head_pos = [250, 250] #蛇头位置
pygame.init() # 初始化 pygame
clock = pygame.time.Clock()
caption = pygame.display.set_mode((caption_width, caption_height))
pygame.display.set_caption(game_title)
def draw_rect(color, position):
pygame.draw.rect(caption, color, pygame.Rect(position[0], position[1], cell, cell))
def hit_the_self():
if snake_init_pos[0] in snake_init_pos[1:]:
return True
else:
return False
def hit_the_wall(head_pos):
if head_pos[0] >= caption_width or head_pos[0] < 0 or head_pos[1] >= caption_height or head_pos[1] < 0:
return True
else:
return False
def change_direction(head_pos):
global food_pos
snake_init_pos.insert(0, list(head_pos))
if head_pos != food_pos:
snake_init_pos.pop()
else:
food_pos = [random.randrange(1, 50) * 10, random.randrange(1, 50) * 10]
if hit_the_self() or hit_the_wall(head_pos):
# 判定死亡,直接退出游戏
pygame.quit()
def main():
for pos in snake_init_pos:
draw_rect(white_color, pos)
draw_rect(white_color, food_pos)
pygame.display.update()
while 1:
for event in pygame.event.get():
if event.type == pygame.QUIT:
pygame.quit()
if event.type == pygame.KEYDOWN:
if event.key == pygame.K_LEFT:
head_pos[0] -= cell
change_direction(head_pos)
elif event.key == pygame.K_RIGHT:
head_pos[0] += cell
change_direction(head_pos)
elif event.key == pygame.K_UP:
head_pos[1] -= cell
change_direction(head_pos)
elif event.key == pygame.K_DOWN:
head_pos[1] += cell
change_direction(head_pos)
caption.fill(black_color)
draw_rect(white_color, food_pos)
for pos in snake_init_pos:
draw_rect(white_color, pos)
pygame.display.update()
clock.tick(10)
if __name__ == '__main__':
main()
3. 实验过程中遇到的问题和解决过程
- 问题1:小蛇在游戏中无法自己朝着蛇头方向前进
- 问题1解决方案:在主循环中加入对小蛇的位置刷新,并使用计时设置好前进的速度
- 问题2:在误触到与蛇头前进方向相反的按键时会直接判定死亡退出游戏
- 问题2解决方案:在判断按键操作时加入对蛇头方向的识别,将与蛇头方向相反的按键无效化
其他(感悟、思考、建议等)
python使我受益良多,王老师很多的时候的教学方式是以自学为主的,通过观看云班课中的视频自学完成内容,我可以此每次顺利完成作业。回顾整学期,循环、列表、类、元组、函数、正则表达等等我都熟悉了知识点,而且每次作业虽然会遇到困难,但是通过自己查资料解决也使我有了自主学习的能力和解决问题的能力。我还是很喜欢老师这样的教学方式的,因为我现在越来越体会到自学的重要性,老师不是一直存在的,通过自己的资源和能力获取知识才是最可靠的。
希望老师可以继续这样教学下去,通过独特的教学方式也让之后报这门选修的同学们领悟到自学的重要性。同时也希望老师在以后的课程中更多的安排些有趣的实践项目让同学们去做,毕竟我们在使用python的时候是能记住更多的知识点的,也像某位大佬说的那样,想在一个领域上有所收获,就应该在该领域上完成一个项目。
最后说一下这次实验的感想吧,这次实验其实我是完全自学的,游戏中很多的点都是云班课里没有讲过的,收益于互联网时代,许多知识都可以在各种博客论坛甚至是bilibili上找到答案。很感谢记笔记的自己,之前的知识我也通过笔记运用到了这次实验中。