本帖最后由 racede 于 2016-2-24 21:31 编辑
简单的贪吃蛇游戏,用kivy写的~
一、主要目的
1) 利用kivy显示用户界面,包括游戏窗口,显示得分。 2) 鼠标控制贪吃蛇的方向。 3) 贪吃蛇初始长度为4个方块,每个大小为20*20像素,显示蛇的移动。 4) 在游戏窗口内随机生产食物的位置 5) 蛇碰到自己或者墙结束游戏 8) 游戏有3个难度可供选择 9) 一个食物10分,每吃一个食物速度加快 二、模块的设计与实现 (1)changelevel模块:通过Spinner选择用户难度,调用get_speed模块 (2)get_speed模块:调整游戏速度,通过clock事件改变游戏速度。 (3)draw_food模块:删除屏幕上已经绘制的食物,通过random_food模块获取新的食物食物坐标。 (4)draw_snake模块:删除屏幕上已经绘制的蛇,并通过snakefunc函数设置蛇的坐标列表。通过列表坐标列表绘制蛇。 (5)random_food模块:应用随机数函数生成新的食物坐标,并检测其是否与蛇身相重合(通过for循环结构检索),若重合则重新调用random_food模块。 (6)snakefunc模块:通过iseated模块确定是否吃到食物,若吃到则将食物坐标添加到蛇坐标列表的最前端,若没有吃到,则在添加完之后删去蛇坐标列表后的最后一个元素。 (7)getscore模块:显示获得分数 (8)iseated模块:遍历食物坐标列表,查找是否有坐标与蛇头坐标重合,若存在,则停止遍历,将游戏分数增加10,更改显示分数,并且返回TRUE。 (9)isdead模块:如果蛇头坐标出了墙的范围,则判定为TRUE,用for循环检查蛇头坐标是否和蛇坐标列表内某坐标相同,以判断蛇是否咬到自己。若有,则返回TURE,否则返回FALSE。 (10)on_touch_down模块:接受touch事件,判断点击位置并改变蛇头运动方向。 (11)gameover模块:删除画布中的食物和蛇,在屏幕上显示游戏结束信息。 (12)play_again模块:按钮触发事件,点击则重新开始游戏
- #coding=utf-8
- '''
- python 2.7
- This program is a snake game
- __author__:Lunatic
- version:1.0
- date:2016.2.24
- '''
- from kivy.app import App
- from kivy.uix.widget import Widget
- from kivy.uix.label import Label
- from kivy.clock import Clock
- from kivy.core.window import Window
- from random import random,randrange
- from kivy.graphics import Color, Rectangle
- from kivy.uix.boxlayout import BoxLayout
- from kivy.uix.button import Button
- from functools import partial
- from kivy.graphics.instructions import InstructionGroup
- from kivy.uix.spinner import Spinner, SpinnerOption
- class Mywidget(Widget):
- SnakeX=[300,280,260,240]
- SnakeY=[300,300,300,300]
- direction=[0,20]
- snake = InstructionGroup()
- food = InstructionGroup()
- foodx=randrange(0,200,20)
- foody=randrange(100,300,20)
- score = 0
- count = 1
- speed = 1
- def __init__(self,**kwargs):
- super(Mywidget,self).__init__(**kwargs)
- self.canvas.clear()
- Clock.schedule_once(self.get_speed)
- def get_speed(self,args):
- Clock.unschedule(self.draw_snake)
- Clock.schedule_interval(self.draw_snake,1./(len(self.SnakeX)+self.speed))
- def play_again(self,args):
- print 'play'
- self.canvas.clear()
- self.SnakeX=[300,280,260,240]
- self.SnakeY=[300,300,300,300]
- self.direction=[0,20]
- self.snake = InstructionGroup()
- self.food = InstructionGroup()
- self.foodx=randrange(0,300,20)
- self.foody=randrange(100,300,20)
- self.count=1
- self.score=0
- self.getscore()
- def on_touch_down(self, touch):
- if self.direction[0]==0:
- if self.SnakeX[0]-touch.x>0:
- self.direction=[-20,0]
- else:
- self.direction=[20,0]
- else:
- if self.SnakeY[0]-touch.y>0:
- self.direction=[0,-20]
- else:
- self.direction=[0,20]
- def changelevel(self,instance,value):
- if value == 'level':
- return
- instance.text = value
- if value=='easy':
- self.speed = 5
- self.get_speed(self)
- elif value=='normal':
- self.speed = 30
- self.get_speed(self)
- else:
- self.speed=100
- self.get_speed(self)
-
- def draw_snake(self,args):
-
- if (self.SnakeX[0]+self.direction[0]==self.SnakeX[1] and self.SnakeY[0]+self.direction[1]==self.SnakeY[1]):
- self.direction *= -1
- if self.isdead()==False:
- self.snakefunc(self)
- self.canvas.remove(self.snake)
- self.snake = InstructionGroup()
- for i in range(len(self.SnakeX)):
- self.snake.add(Color(1, 0, 0, 1))
- self.snake.add(Rectangle(pos=(self.SnakeX[i],self.SnakeY[i]), size=(20, 20)))
-
- self.draw_food()
- self.canvas.add(self.snake)
- else:
- self.gameover()
- def draw_food(self):
-
- self.canvas.remove(self.food)
- self.food = InstructionGroup()
- self.food.add(Color(0, 1, 0, 1))
- self.food.add(Rectangle(pos=(self.foodx,self.foody), size=(20, 20)))
- self.canvas.add(self.food)
-
- def random_food(self):
-
- self.foodx=randrange(0,self.width,20)
- self.foody=randrange(100,self.height,20)
- for i in range(0,len(self.SnakeX)-1):
- if self.foodx==self.SnakeX[i] and self.foody==self.SnakeY[i]:
- self.random_food()
- def snakefunc(self,args):
-
- new_X=self.SnakeX[0]+self.direction[0]
- new_Y=self.SnakeY[0]+self.direction[1]
- self.SnakeX.insert(0,new_X)
- self.SnakeY.insert(0,new_Y)
-
- if self.iseated()==True:
- self.random_food()
- self.get_speed(self)
- else:
-
- del self.SnakeX[-1]
- del self.SnakeY[-1]
- def iseated(self):
- if self.foodx==self.SnakeX[0] and self.foody==self.SnakeY[0]:
- self.score+=10
- print self.score
- self.getscore()
- return True
- def isdead(self):
- if self.SnakeX[0]< 0 or self.SnakeX[0]> Window.width or self.SnakeY[0]<self.y or self.SnakeY[0]> Window.height:
- return True
- for i in range(1,len(self.SnakeX)-1):
- if self.SnakeX[i] ==self.SnakeX[0] and self.SnakeY[i]==self.SnakeY[0]:
- return True
- return False
- def gameover(self):
- self.canvas.clear()
- with self.canvas:
- Rectangle(source='mali.jpg', pos=self.pos, size=self.size)
-
- def getscore(self):
-
- self.label.text='score '+str(self.score)
- class SnakeApp(App):
-
- def build(self):
-
- wid = Mywidget()
-
- btn=Button(text='restart',on_press=partial(wid.play_again))
- speedlevel = Spinner(
- text='level',
- values=('easy', 'normal', 'hard'))
- speedlevel.bind(text=wid.changelevel)
-
- layout = BoxLayout(size_hint=(1, None), height=100)
- label=Label(text='score 0')
- wid.label=label
- layout.add_widget(label)
- layout.add_widget(speedlevel)
- layout.add_widget(btn)
- root = BoxLayout(orientation='vertical')
- root.add_widget(wid)
- root.add_widget(layout)
-
- return root
- if __name__=='__main__':
- SnakeApp().run()
复制代码
|