根据摩托罗拉C289手机的同名游戏写成,使用了Python的curses,因此最好在linux下面运行。最近又用tkinter改写了界面,从而不在受限于curses的支持,还重写的游戏的算法,比以前的运行效率好多了。
curses
_curses
thread
time sleep
string split
random randint
brick_width = 7
brick_gap_x = 1
brick_gap_y = 1
speed = 0.05
pause = 1
stdscr = curses.initscr()
curses.noecho()
curses.cbreak()
curses.curs_set(0)
stdscr.keypad(1)
screen_height, screen_width = stdscr.getmaxyx()
screen_height = screen_height - 1
screen_width = screen_width - 1
brick_rows = screen_height / 4
brick_rows > 7: brick_rows = 7
brick_cols = (screen_width + brick_gap_x) / (brick_width + brick_gap_x)
brick_margin = (screen_width - brick_cols * (brick_width + brick_gap_x) + brick_gap_x)/2
pad_position = randint(0, screen_width - brick_width)
ball_position = [screen_height - 3, randint(0, screen_width - brick_width)]
ball_direction = [-1, 1]
char =
bricks = []
game_score = 0
ScreenSizeError =
tStart =
tExit =
tOver =
tGoon =
():
bricks
row range(brick_rows):
y = row * (1 + brick_gap_y)
col range(brick_cols):
x = col * (brick_gap_x + brick_width) + brick_margin
stdscr.addstr(y, x, * brick_width, curses.A_REVERSE)
bricks.append([y, x])
stdscr.addstr(screen_height - 1, pad_position, * brick_width, curses.A_REVERSE)
stdscr.addstr(ball_position[0], ball_position[1], , curses.A_REVERSE)
stdscr.addstr(screen_height, 0, + ( % game_score) + * 4, curses.A_REVERSE)
stdscr.addstr(screen_height, 15, + * (screen_width - 28), curses.A_REVERSE)
stdscr.refresh()
(lock):
char, pad_position
char = stdscr.getch()
char == ord(): quit_game(lock)
char == curses.KEY_LEFT: pad_position = pad_position - 1
char == curses.KEY_RIGHT: pad_position = pad_position + 1
pad_position < 0: pad_position = 0
pad_position >= screen_width - brick_width: pad_position = screen_width - brick_width
stdscr.addstr(screen_height - 1, 0, * screen_width)
stdscr.addstr(screen_height - 1, pad_position, * brick_width, curses.A_REVERSE)
stdscr.refresh()
(lock):
ball_position, ball_direction
ball_position[0] != screen_height - 1:
stdscr.addstr(ball_position[0], ball_position[1], )
ball_position[0] = ball_position[0] + ball_direction[0]
ball_position[1] = ball_position[1] + ball_direction[1]
stdscr.addstr(ball_position[0], ball_position[1], , curses.A_REVERSE)
detect_collision(lock)
stdscr.refresh()
sleep(speed)
(lock):
bricks, ball_direction, game_score
ball_position[0] == 0 :
ball_direction = [- ball_direction[0], ball_direction[1]]
ball_position[1] == 0 ball_position[1] == screen_width:
ball_direction = [ball_direction[0], - ball_direction[1]]
brick bricks:
brick[1] <= ball_position[1] + ball_direction[1] <= brick[1] + brick_width
ball_position[0] + ball_direction[0] == brick[0]:
ball_direction[0] = - ball_direction[0]
stdscr.addstr(brick[0], brick[1], * brick_width)
game_score = game_score + 10
stdscr.addstr(screen_height, 8, % game_score, curses.A_REVERSE)
bricks.remove(brick)
len(bricks): another_level()
ball_position[0] == screen_height - 2 pad_position <= ball_position[1] <= pad_position + brick_width:
ball_direction[0] = - ball_direction[0]
ball_position[0] == screen_height - 1:
ball_direction[0] = - ball_direction[0]
ball_position[1] == pad_position char == curses.KEY_LEFT ball_direction[1]:
ball_direction[1] = - ball_direction[1]
ball_position[1] == pad_position + brick_width char == curses.KEY_RIGHT ball_direction[1]:
ball_direction[1] = - ball_direction[1]
ball_position[0] == screen_height - 1 pad_position <= ball_position[1] <= pad_position + brick_width:
line_num = 0
line split(tOver, ):
stdscr.addstr(screen_height / 2 + line_num, 10, line)
line_num = line_num + 1
stdscr.refresh()
curses.flash()
sleep(1)
curses.flash()
sleep(1)
lock.release()
(lock):
char, speed
char != ord():
speed_old = speed
speed = pause
line_num = 0
line split(tExit, ):
stdscr.addstr(screen_height / 2 + line_num, 10, line)
line_num = line_num + 1
stdscr.addstr(screen_height, 15, + * (screen_width - 40), curses.A_REVERSE)
stdscr.refresh()
char == ord():
speed = speed_old
line_num = 0
line split(tExit, ):
stdscr.addstr(screen_height / 2 + line_num, 10, * len(line) )
line_num = line_num + 1
stdscr.refresh()
:
lock.release()
():
speed, char
speed_old = speed
speed = pause
line_num = 0
line split(tGoon, ):
stdscr.addstr(screen_height / 2 + line_num, 10, line)
line_num = line_num + 1
stdscr.addstr(screen_height, 15, + * (screen_width - 40), curses.A_REVERSE)
stdscr.refresh()
char == ord():
lock.release()
:
stdscr.erase()
speed = speed / 2
init_game()
(fun, lock):
:
lock.locked(): globals()[fun](lock)
_curses.error, diag:
lock.locked(): lock.release()
__name__ == :
:
line_num = 0
line split(tStart, ):
stdscr.addstr(screen_height /4 + line_num, 10, line)
line_num = line_num + 1
stdscr.refresh()
sleep(1)
stdscr.erase()
init_game()
locks = []
i range(2):
lock = thread.allocate_lock()
lock.acquire()
locks.append(lock)
thread.start_new_thread(looper, (, locks[0]))
thread.start_new_thread(looper, (, locks[1]))
locks[0].locked() locks[1].locked:
_curses.error, diag:
msg = + str(diag)
:
msg =
:
msg =
i range(2):
locks[i].locked(): locks[i].release()
height, width = stdscr.getmaxyx()
height - 1 < screen_height width - 1 < screen_width:
msg =
curses.curs_set(1)
stdscr.keypad(0)
curses.nocbreak()
curses.echo()
curses.endwin()
msg