Документ взят из кэша поисковой машины. Адрес оригинального документа : http://kodomo.fbb.msu.ru/hg/snake/annotate/21dca2c88275/engine.py
Дата изменения: Unknown
Дата индексирования: Fri Feb 28 22:54:04 2014
Кодировка:
snake: engine.py annotate

snake

annotate engine.py @ 136:21dca2c88275

UI documentation
author Alex Martynov <martiran@kodomo.fbb.msu.ru>
date Mon, 20 Dec 2010 17:09:41 +0300
parents b7d2bfd5860d
children 8b5bc7bda225
rev   line source
martiran@12 1 import random as rnd
martiran@15 2 import Tkinter as tk
Alex@66 3 import snake
martiran@12 4
martiran@6 5 directions = [(0,1), (1,0), (0,-1), (-1,0)]
martiran@1 6
martiran@111 7 class Dict(dict):
martiran@111 8 pass
martiran@111 9
martiran@5 10 class Cell(object):
martiran@15 11 def __init__(self, x, y, canvas = None):
martiran@1 12 self.x = x
martiran@1 13 self.y = y
martiran@1 14 self.canvas = canvas
martiran@1 15 self.snake = None
martiran@28 16 self.type = 'empty'
martiran@1 17 return
martiran@113 18 def redraw(self, offset, c_size):
martiran@113 19 x0=offset[0] + self.x*c_size
martiran@113 20 y0=offset[1] + self.y*c_size
martiran@113 21 x1=offset[0] + (self.x+1)*c_size
martiran@113 22 y1=offset[1] + (self.y+1)*c_size
martiran@113 23 x2=offset[0] + (self.x+1/2.0)*c_size
martiran@15 24 if self.type == 'wall':
Alex@101 25 self.canvas.create_rectangle(x0, y0, x1, y1, fill="grey")
martiran@15 26 pass
martiran@15 27 elif self.type == 'empty':
Alex@101 28 self.canvas.create_rectangle(x0, y0, x1, y1, fill="black")
martiran@15 29 pass
martiran@15 30 elif self.type == 'body':
Alex@101 31 self.canvas.create_rectangle(x0, y0, x1, y1, fill=self.snake.color)
martiran@15 32 pass
martiran@15 33 elif self.type == 'head':
Alex@101 34 self.canvas.create_oval(x0, y0, x1, y1, fill=self.snake.color)
martiran@15 35 pass
martiran@15 36 elif self.type == 'tail':
Alex@101 37 self.canvas.create_polygon(x0, y0, x1, y0, x2, y1, fill=self.snake.color)
martiran@15 38 pass
martiran@15 39 return
martiran@6 40 def __eq__(self, pattern):
martiran@52 41 if pattern.type == 'any':
martiran@6 42 return True
martiran@52 43 if pattern.type != self.type:
martiran@6 44 return False
martiran@52 45 if pattern.snake_type == 'my' and pattern.snake != self.snake:
martiran@52 46 return False
martiran@52 47 elif pattern.snake_type == 'enemy' and pattern.snake == self.snake:
martiran@52 48 return False
martiran@52 49 return True
martiran@126 50
martiran@126 51 def __ne__(self, pattern):
martiran@126 52 return not self == pattern
martiran@126 53
martiran@6 54 def clear(self):
martiran@1 55 self.snake = None
martiran@1 56 self.type = 'empty'
martiran@1 57 return
martiran@1 58
martiran@2 59
martiran@5 60 class Engine(object):
martiran@6 61 def __init__(self, canvas):
martiran@1 62 self.canvas = canvas
martiran@54 63 self.w = min(canvas.winfo_height(), canvas.winfo_width())
martiran@54 64 self.h = min(canvas.winfo_height(), canvas.winfo_width())
martiran@12 65 self.snakes = [None, None, None, None]
martiran@9 66 self.init_field()
martiran@111 67 self.start_snake_length = 10
martiran@9 68 return
martiran@9 69 def init_field (self):
martiran@111 70 self.field = Dict()
martiran@117 71 self.field.w = 31
martiran@117 72 self.field.h = 31
martiran@113 73 f_w = self.field.w
martiran@113 74 f_h = self.field.h
martiran@113 75 for x in range(f_w):
martiran@113 76 for y in range(f_h):
martiran@9 77 self.field[x, y] = Cell(x, y, self.canvas)
martiran@113 78 for y in range(f_h):
martiran@9 79 self.field[0, y].type = 'wall'
martiran@113 80 self.field[f_w-1, y].type = 'wall'
martiran@113 81 for x in range(1,f_w-1):
martiran@9 82 self.field[x, 0].type = 'wall'
martiran@113 83 self.field[x, f_h-1].type = 'wall'
Alex@103 84 self.refill()
Alex@93 85 self.redraw()
martiran@1 86 return
martiran@6 87 def step(self):
Alex@62 88 for i, snake in enumerate(self.snakes):
Alex@103 89 if snake != None:
Alex@103 90 if len(snake.cells) == 0:
Alex@103 91 self.snakes[i] = None
Alex@103 92 continue
Alex@66 93 self.legal_moves(snake)
martiran@12 94 self.move_snake(snake)
martiran@12 95 self.refill()
martiran@9 96 self.redraw()
martiran@9 97 return
martiran@9 98 def move_snake(self, snake):
martiran@105 99 head = snake.cells[0]
martiran@12 100 for rule in snake.rules:
martiran@105 101 for direction in snake.legal_dir:
martiran@105 102 rule.rotate(direction)
martiran@105 103 if rule.applies(self.field, head.x, head.y) == True:
martiran@105 104 self.move_do(snake, direction)
martiran@105 105 return
martiran@105 106 if snake.legal_dir != []:
Alex@99 107 self.move_do(snake, snake.legal_dir[0])
martiran@12 108 pass
martiran@14 109 return
Alex@94 110 def move_do(self, snake, applied_dir):
martiran@107 111 head = snake.cells[0]
martiran@107 112 dir_cell = self.field[head.x + applied_dir[0], head.y + applied_dir[1]]
Alex@90 113 if dir_cell.type == 'empty':
Alex@90 114 snake.cells.insert(0,dir_cell)
Alex@90 115 del snake.cells[-1]
Alex@90 116 pass
Alex@90 117 elif (dir_cell.type == 'tail' and dir_cell.snake != snake):
Alex@90 118 snake.cells.insert(0,dir_cell)
Alex@90 119 del dir_cell.snake.cells[-1]
Alex@90 120 pass
Alex@90 121
martiran@6 122 def create_snake(self, snake_number):
martiran@46 123 cells_id = []
martiran@113 124 f_h = self.field.h
martiran@113 125 f_w = self.field.w
martiran@111 126 for y in range(self.start_snake_length):
martiran@114 127 cells_id.append(((f_w-1)/2, y+1))
martiran@46 128 for rot_num in range(snake_number - 1):
Alex@62 129 for i, cell in enumerate(cells_id):
martiran@122 130 cells_id[i] = (min(f_h, f_w)-1-cell[1],cell[0])
martiran@46 131 cells = []
martiran@46 132 for cell in cells_id:
Alex@60 133 cells.append(self.field[cell])
martiran@46 134 color_dic = {
martiran@46 135 1:'blue',
martiran@46 136 2:'green',
martiran@46 137 3:'yellow',
martiran@46 138 4:'red',}
martiran@46 139 self.snakes[snake_number-1] = snake.Snake(cells, color_dic[snake_number])
Alex@77 140 return self.snakes[snake_number-1]
martiran@6 141 def refill(self):
martiran@113 142 f_w = self.field.w
martiran@113 143 f_h = self.field.h
martiran@113 144 for x in range(1,f_w-1):
martiran@113 145 for y in range(1,f_h-1):
martiran@12 146 self.field[x, y].type = 'empty'
martiran@31 147 self.field[x, y].snake = None
martiran@12 148 pass
martiran@12 149 for snake in self.snakes:
martiran@12 150 if snake == None:
martiran@12 151 pass
martiran@12 152 else:
martiran@31 153 snake.fill()
martiran@12 154 pass
martiran@14 155 return
martiran@9 156 def redraw(self):
martiran@117 157 self.canvas.delete("all")
martiran@113 158 w = self.canvas.winfo_width()
martiran@113 159 h = self.canvas.winfo_height()
martiran@113 160 cw = w/float(self.field.w)
martiran@113 161 ch = h/float(self.field.h)
martiran@113 162 c = min(cw, ch)
martiran@113 163 field_geometry = (self.field.w*c,self.field.h*c)
martiran@113 164 offset = ((w - field_geometry[0])/2.0, (h - field_geometry[1])/2.0)
martiran@32 165 for cell_coord in self.field:
martiran@113 166 self.field[cell_coord].redraw(offset, c)
martiran@15 167 return
martiran@6 168 def legal_moves(self, snake):
martiran@6 169 snake.legal_dir = []
martiran@108 170 head = snake.cells[0]
martiran@6 171 for direction in directions:
martiran@108 172 dir_cell = self.field[head.x + direction[0], head.y + direction[1]]
martiran@12 173 if (dir_cell.type == 'empty' or (dir_cell.type == 'tail' and dir_cell.snake != snake)):
martiran@6 174 snake.legal_dir.append(direction)
Alex@90 175 rnd.shuffle(snake.legal_dir)
martiran@6 176 return
martiran@6 177