text: from .ball import Ball
  from .item import Coin, Trap
  from .map_generator import generator
  import random
  
  
  class Stage:
  
      def __init__(self, board, ui):
          self.ui = ui
          self.board = board
          self.board_ui = None
  
      def load(self):
          """Loads a stage correctly depending on the stage id.
          """
          self.ui.reset_canvas()
  
          # self.board = generator.generate()
          self.board_ui = [[None] * len(self.board[0]) for x in self.board]
          self.ball = Ball(self, self.ui, self.get_initial_ball_position())
          self.items = [[None] * len(self.board[0]) for x in self.board]
          self.ball_ui = None
  
          for i in range(len(self.board)):
              for j in range(len(self.board[0])):
                  if self.board[i][j] == '$':
                      self.items[i][j] = Coin((i, j), self, self.ui)
                  elif self.board[i][j] == 't':  # Trap.
                      self.items[i][j] = Trap((i, j), self, self.ui)
  
          def create_board(self, canvas):
              for i in range(len(self.board)):
                  for j in range(len(self.board[0])):
                      width = 1
                      if self.board[i][j] == '#':
                          fill = 'saddle brown'
                      elif self.board[i][j] == 'E':
                          fill = 'gold'
                      else:
                          fill = None
                      bbox = (1+j*32, 1+i*32, 1+j*32+32, 1+i*32+32)
                      self.board_ui[i][j] = canvas.create_rectangle(
                          *bbox, width=width, fill=fill)
  
          def create_ball(self, canvas):
              i, j = self.ball.position
              bbox = (5+j*32, 5+i*32, 1+j*32+32-4, 1+i*32+32-4)
              self.ball_ui = canvas.create_oval(*bbox, fill='white')
  
          self.ui.use_canvas(self, create_board)
          self.ui.use_canvas(self, create_ball)
  
      def get_initial_ball_position(self):
          """Obtains initial ball position from the stage board.
          """
          for x in range(len(self.board)):
              for y in range(len(self.board[0])):
                  if self.board[x][y] == 'S':
                      return (x, y)
          return None
  
      def can_move(self, pos, d):
          return self.board[pos[0] + d[0]][pos[1] + d[1]] != '#'
  
      def check_win(self):
          return self.board[self.ball.position[0]][self.ball.position[1]] == 'E'
  
      def move_ball(self, player_info):
          # Simulate one movement to the ball.
          if self.ball.is_moving == True:
              self.ball.moving_progress += 1
              if self.ball.moving_progress == 4:
                  self.ball.move_one_step(self.ball.moving_direction)
                  if self.can_move(self.ball.position, self.ball.moving_direction) == False:
                      self.ball.is_moving = False
                      self.ball.moving_direction = None
  
          if self.ball.is_moving == True:
              bbox = (5+self.ball.position[1]*32
                      + 8*self.ball.moving_progress *
                      self.ball.moving_direction[1],
                      5+self.ball.position[0]*32
                      + 8*self.ball.moving_progress *
                      self.ball.moving_direction[0],
                      1+self.ball.position[1]*32+32-4
                      + 8*self.ball.moving_progress *
                      self.ball.moving_direction[1],
                      1+self.ball.position[0]*32+32-4
                      + 8*self.ball.moving_progress*self.ball.moving_direction[0])
          else:
              bbox = (5+self.ball.position[1]*32,
                      5+self.ball.position[0]*32,
                      1+self.ball.position[1]*32+32-4,
                      1+self.ball.position[0]*32+32-4)
  
          # Check if the ball hits something.
          if self.ball.moving_progress == 0:
              x, y = self.ball.position
              if self.items[x][y] != None:
                  needs_destroy = self.items[x][y].pass_through(player_info)
                  if needs_destroy == True:
                      self.items[x][y] = None
  
          def update_ball_coords(self, canvas):
              canvas.coords(self.ball_ui, *bbox)
          self.ui.add_update(self, update_ball_coords)
  