Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP
Newer
Older
100755 217 lines (185 sloc) 6.381 kB
e3601cf @fmoo Use /usr/bin/env python
fmoo authored
1 #!/usr/bin/env python
316122c Create a mysterious new workflow
Alan Huang authored
2 import sys
3 import time
4 import select
5 import curses
6 import curses.wrapper
7
8 entities = []
9 grid = []
10
11 class Wall:
12 def collide(self, ball):
13 return False
14
15 class Block:
16 killed = 0
17 total = 0
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
18
316122c Create a mysterious new workflow
Alan Huang authored
19 def __init__(self, x, y, w, h, c):
20 self.x = x
21 self.y = y
22 self.w = w
23 self.h = h
24 self.fmt = curses.A_BOLD | curses.color_pair(c)
25 self.alive = True
26 for i in range(self.x, self.x + self.w):
27 for j in range(self.y, self.y + self.h):
28 grid[j + 1][i + 1] = self
29 Block.total += 1
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
30
316122c Create a mysterious new workflow
Alan Huang authored
31 def collide(self, ball):
32 self.alive = False
33 for i in range(self.x, self.x + self.w):
34 for j in range(self.y, self.y + self.h):
35 grid[j + 1][i + 1] = None
36 Block.killed += 1
37 return False
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
38
316122c Create a mysterious new workflow
Alan Huang authored
39 def tick(self, win):
40 if self.alive:
41 for i in range(self.x, self.x + self.w):
42 for j in range(self.y, self.y + self.h):
43 win.addch(j, i, curses.ACS_BLOCK, self.fmt)
44 return self.alive
45
46 class Ball:
47 alive = False
48 killed = 0
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
49
316122c Create a mysterious new workflow
Alan Huang authored
50 def __init__(self, x, y, vx, vy):
51 self.x = x
52 self.y = y
53 self.vx = vx
54 self.vy = vy
55 Ball.alive = True
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
56
316122c Create a mysterious new workflow
Alan Huang authored
57 def collide(self, ball):
58 return True
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
59
316122c Create a mysterious new workflow
Alan Huang authored
60 def encounter(self, dx, dy):
61 ent = grid[self.y + dy + 1][self.x + dx + 1]
62 if ent and not ent.collide(self):
63 self.vx -= 2 * dx
64 self.vy -= 2 * dy
65 return ent
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
66
316122c Create a mysterious new workflow
Alan Huang authored
67 def tick(self, win):
68 while self.y < ship.y:
69 if self.encounter((self.vx + self.vy) / 2, (self.vy - self.vx) / 2):
70 continue
71 if self.encounter((self.vx - self.vy) / 2, (self.vy + self.vx) / 2):
72 continue
73 if self.encounter(self.vx, self.vy):
74 continue
75 break
76 self.x += self.vx
77 self.y += self.vy
78 try:
79 win.addch(self.y, self.x, 'O')
80 except curses.error:
81 Ball.alive = False
82 Ball.killed += 1
83 return Ball.alive
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
84
316122c Create a mysterious new workflow
Alan Huang authored
85 class Ship:
86 def __init__(self, x, y):
87 self.x = x
88 self.y = y
89 self.hw = 10
90 self.v = 4
91 self.last = 1
92 self.update()
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
93
316122c Create a mysterious new workflow
Alan Huang authored
94 def update(self):
95 grid[self.y + 1] = (
96 [ None ] * (self.x - self.hw + 1) +
97 [ self ] * (self.hw * 2 + 1) +
98 [ None ] * (width - self.x - self.hw)
99 )
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
100
316122c Create a mysterious new workflow
Alan Huang authored
101 def collide(self, ball):
102 ball.vy = -1
103 if ball.x > self.x + self.hw / 2:
104 ball.vx = 1
105 elif ball.x < self.x - self.hw / 2:
106 ball.vx = -1
107 return True
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
108
316122c Create a mysterious new workflow
Alan Huang authored
109 def shift(self, i):
110 self.last = i
111 self.x += self.v * i
112 if self.x - self.hw < 0:
113 self.x = self.hw
114 elif self.x + self.hw >= width:
115 self.x = width - self.hw - 1
116 self.update()
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
117
316122c Create a mysterious new workflow
Alan Huang authored
118 def spawn(self):
119 if not Ball.alive:
120 entities.append(Ball(self.x, self.y - 1, self.last, -1))
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
121
316122c Create a mysterious new workflow
Alan Huang authored
122 def tick(self, win):
123 if not Ball.alive:
124 win.addch(self.y - 1, self.x, 'O')
125 win.addch(self.y, self.x - self.hw, curses.ACS_LTEE)
126 for i in range(-self.hw + 1, self.hw):
127 win.addch(curses.ACS_HLINE)
128 win.addch(curses.ACS_RTEE)
129 return True
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
130
c0c78c2 @epriestley Raise exception instead of returning magical number from 'arc anoid'
epriestley authored
131 class PowerOverwhelmingException(Exception):
132 pass
133
316122c Create a mysterious new workflow
Alan Huang authored
134 def main(stdscr):
135 global height, width, ship
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
136
316122c Create a mysterious new workflow
Alan Huang authored
137 for i in range(1, 8):
138 curses.init_pair(i, i, 0)
139 curses.curs_set(0)
140 curses.raw()
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
141
316122c Create a mysterious new workflow
Alan Huang authored
142 height, width = stdscr.getmaxyx()
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
143
144 if height < 15 or width < 30:
c0c78c2 @epriestley Raise exception instead of returning magical number from 'arc anoid'
epriestley authored
145 raise PowerOverwhelmingException(
146 "Your computer is not powerful enough to run 'arc anoid'. "
147 "It must support at least 30 columns and 15 rows of next-gen "
148 "full-color 3D graphics.")
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
149
316122c Create a mysterious new workflow
Alan Huang authored
150 status = curses.newwin(1, width, 0, 0)
151 height -= 1
152 game = curses.newwin(height, width, 1, 0)
153 game.nodelay(1)
154 game.keypad(1)
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
155
316122c Create a mysterious new workflow
Alan Huang authored
156 grid[:] = [ [ None for x in range(width + 2) ] for y in range(height + 2) ]
157 wall = Wall()
158 for x in range(width + 2):
159 grid[0][x] = wall
160 for y in range(height + 2):
161 grid[y][0] = grid[y][-1] = wall
162 ship = Ship(width / 2, height - 5)
163 entities.append(ship)
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
164
316122c Create a mysterious new workflow
Alan Huang authored
165 colors = [ 1, 3, 2, 6, 4, 5 ]
166 h = height / 10
167 for x in range(1, width / 7 - 1):
168 for y in range(1, 7):
169 entities.append(Block(x * 7, y * h + x / 2 % 2, 7, h, colors[y - 1]))
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
170
316122c Create a mysterious new workflow
Alan Huang authored
171 while True:
172 while select.select([ sys.stdin ], [], [], 0)[0]:
173 key = game.getch()
174 if key == curses.KEY_LEFT or key == ord('a') or key == ord('A'):
175 ship.shift(-1)
176 elif key == curses.KEY_RIGHT or key == ord('d') or key == ord('D'):
177 ship.shift(1)
178 elif key == ord(' '):
179 ship.spawn()
180 elif key == 0x1b or key == 3 or key == ord('q') or key == ord('Q'):
181 return
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
182
316122c Create a mysterious new workflow
Alan Huang authored
183 game.resize(height, width)
184 game.erase()
185 entities[:] = [ ent for ent in entities if ent.tick(game) ]
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
186
316122c Create a mysterious new workflow
Alan Huang authored
187 status.hline(0, 0, curses.ACS_HLINE, width)
188 status.addch(0, 2, curses.ACS_RTEE)
189 status.addstr(' SCORE: ', curses.A_BOLD | curses.color_pair(4))
190 status.addstr('%s/%s ' % (Block.killed, Block.total), curses.A_BOLD)
191 status.addch(curses.ACS_VLINE)
192 status.addstr(' DEATHS: ', curses.A_BOLD | curses.color_pair(4))
193 status.addstr('%s ' % Ball.killed, curses.A_BOLD)
194 status.addch(curses.ACS_LTEE)
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
195
316122c Create a mysterious new workflow
Alan Huang authored
196 if Block.killed == Block.total:
197 message = ' A WINNER IS YOU!! '
198 i = int(time.time() / 0.8)
199 for x in range(width):
200 for y in range(6):
201 game.addch(height / 2 + y - 3 + (x / 8 + i) % 2, x,
202 curses.ACS_BLOCK,
203 curses.A_BOLD | curses.color_pair(colors[y]))
204 game.addstr(height / 2, (width - len(message)) / 2, message,
205 curses.A_BOLD | curses.color_pair(7))
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
206
316122c Create a mysterious new workflow
Alan Huang authored
207 game.refresh()
208 status.refresh()
209 time.sleep(0.05)
210
c0c78c2 @epriestley Raise exception instead of returning magical number from 'arc anoid'
epriestley authored
211 try:
212 curses.wrapper(main)
6b0af26 @epriestley Fix serious problems with 'arc anoid'
epriestley authored
213 print ('You destroyed %s blocks out of %s with %s deaths.' %
214 (Block.killed, Block.total, Ball.killed))
c0c78c2 @epriestley Raise exception instead of returning magical number from 'arc anoid'
epriestley authored
215 except PowerOverwhelmingException as e:
216 print e
Something went wrong with that request. Please try again.