import pygame
import random
import sys

# 初始化Pygame
pygame.init()

# 游戏基础设置
WIDTH, HEIGHT = 800, 800
screen = pygame.display.set_mode((WIDTH, HEIGHT))
pygame.display.set_caption("Pygame 随机迷宫游戏")
clock = pygame.time.Clock()

# 颜色定义
BLACK = (0, 0, 0)
WHITE = (255, 255, 255)
BLUE = (0, 100, 255)
GREEN = (0, 250, 150)
RED = (255, 80, 80)

# 迷宫大小（格子数量）
CELL_SIZE = 40
cols = WIDTH // CELL_SIZE
rows = HEIGHT // CELL_SIZE

# ----------------------
# 迷宫生成（深度优先）
# ----------------------


class Cell:
    def __init__(self, x, y):
        self.x = x
        self.y = y
        self.walls = [True, True, True, True]  # 上、右、下、左
        self.visited = False

    def draw(self):
        x = self.x * CELL_SIZE
        y = self.y * CELL_SIZE
        if self.walls[0]:
            pygame.draw.line(screen, WHITE, (x, y), (x + CELL_SIZE, y), 2)
        if self.walls[1]:
            pygame.draw.line(screen, WHITE, (x + CELL_SIZE, y),
                             (x + CELL_SIZE, y + CELL_SIZE), 2)
        if self.walls[2]:
            pygame.draw.line(screen, WHITE, (x + CELL_SIZE,
                             y + CELL_SIZE), (x, y + CELL_SIZE), 2)
        if self.walls[3]:
            pygame.draw.line(screen, WHITE, (x, y + CELL_SIZE), (x, y), 2)

        if self.visited:
            pygame.draw.rect(
                screen, BLACK, (x+1, y+1, CELL_SIZE-2, CELL_SIZE-2))


def create_maze():
    grid = []
    for y in range(rows):
        for x in range(cols):
            grid.append(Cell(x, y))

    stack = []
    current = grid[0]
    current.visited = True

    while True:
        next_cell = get_next_cell(current, grid)
        if next_cell:
            next_cell.visited = True
            stack.append(current)
            remove_walls(current, next_cell)
            current = next_cell
        elif stack:
            current = stack.pop()
        else:
            break
    return grid


def get_next_cell(cell, grid):
    neighbors = []
    x = cell.x
    y = cell.y

    if y > 0 and not grid[(y-1)*cols + x].visited:
        neighbors.append(grid[(y-1)*cols + x])
    if x < cols-1 and not grid[y*cols + (x+1)].visited:
        neighbors.append(grid[y*cols + (x+1)])
    if y < rows-1 and not grid[(y+1)*cols + x].visited:
        neighbors.append(grid[(y+1)*cols + x])
    if x > 0 and not grid[y*cols + (x-1)].visited:
        neighbors.append(grid[y*cols + (x-1)])

    return random.choice(neighbors) if neighbors else None


def remove_walls(a, b):
    dx = a.x - b.x
    dy = a.y - b.y
    if dx == 1:
        a.walls[3] = False
        b.walls[1] = False
    elif dx == -1:
        a.walls[1] = False
        b.walls[3] = False
    if dy == 1:
        a.walls[0] = False
        b.walls[2] = False
    elif dy == -1:
        a.walls[2] = False
        b.walls[0] = False

# ----------------------
# 玩家类
# ----------------------


class Player:
    def __init__(self):
        self.x = 0
        self.y = 0
        self.speed = 1

    def move(self, dx, dy, grid):
        new_x = self.x + dx
        new_y = self.y + dy

        if 0 <= new_x < cols and 0 <= new_y < rows:
            current = grid[self.y * cols + self.x]
            if dx == 1 and not current.walls[1]:
                self.x += 1
            if dx == -1 and not current.walls[3]:
                self.x -= 1
            if dy == 1 and not current.walls[2]:
                self.y += 1
            if dy == -1 and not current.walls[0]:
                self.y -= 1

    def draw(self):
        pygame.draw.rect(screen, BLUE, (
            self.x * CELL_SIZE + 5,
            self.y * CELL_SIZE + 5,
            CELL_SIZE - 10,
            CELL_SIZE - 10
        ))

# ----------------------
# 游戏主逻辑
# ----------------------


def main():
    grid = create_maze()
    player = Player()
    font = pygame.font.Font(None, 60)
    win = False

    while True:
        for event in pygame.event.get():
            if event.type == pygame.QUIT:
                pygame.quit()
                sys.exit()

        # 键盘控制
        if not win:
            keys = pygame.key.get_pressed()
            if keys[pygame.K_UP]:
                player.move(0, -1, grid)
            if keys[pygame.K_DOWN]:
                player.move(0, 1, grid)
            if keys[pygame.K_LEFT]:
                player.move(-1, 0, grid)
            if keys[pygame.K_RIGHT]:
                player.move(1, 0, grid)

        # 判断胜利
        if player.x == cols-1 and player.y == rows-1:
            win = True

        # 绘制
        screen.fill(BLACK)
        for cell in grid:
            cell.draw()

        # 起点 & 终点
        pygame.draw.rect(screen, GREEN, (0, 0, CELL_SIZE, CELL_SIZE))
        pygame.draw.rect(screen, RED, ((cols-1)*CELL_SIZE,
                         (rows-1)*CELL_SIZE, CELL_SIZE, CELL_SIZE))

        player.draw()

        # 胜利文字
        if win:
            text = font.render("你赢啦！", True, (255, 255, 0))
            screen.blit(text, (WIDTH//2 - 100, HEIGHT//2))

        pygame.display.flip()
        clock.tick(15)


if __name__ == "__main__":
    main()
