import pygame
import random
import sys

# 初始化pygame
pygame.init()
# 窗口设置
WIDTH, HEIGHT = 1000, 600
screen = pygame.display.set_mode((WIDTH, HEIGHT))
pygame.display.set_caption("骑龙勇士历险记")
clock = pygame.time.Clock()
FPS = 60

# 颜色定义
SKY_BLUE = (100, 180, 255)
DRAGON_RED = (220, 30, 30)
WARRIOR_GOLD = (255, 200, 0)
FIRE_ORANGE = (255, 110, 0)
COIN_YELLOW = (255, 240, 0)
ROCK_GRAY = (80, 80, 80)
MONSTER_PURPLE = (130, 20, 160)
BOSS_RED = (120, 0, 0)
WHITE = (255, 255, 255)
BLACK = (0, 0, 0)
GREEN = (0, 220, 0)

# 字体
font = pygame.font.SysFont("simhei", 30)
boss_font = pygame.font.SysFont("simhei", 50)

# 龙类
class Dragon(pygame.sprite.Sprite):
    def __init__(self):
        super().__init__()
        self.width = 120
        self.height = 70
        self.x = 100
        self.y = HEIGHT // 2
        self.speed_x = 0
        self.speed_y = 0
        self.max_speed = 8
        self.hp = 100  # 修改为100血量
        self.fire_cd = 0

    def update(self):
        # 重力模拟
        self.speed_y += 0.2
        # 位置更新
        self.x += self.speed_x
        self.y += self.speed_y
        # 边界限制
        if self.x < 0:
            self.x = 0
        if self.x + self.width > WIDTH:
            self.x = WIDTH - self.width
        if self.y < 0:
            self.y = 0
        if self.y + self.height > HEIGHT:
            self.y = HEIGHT - self.height
        # 开火冷却
        if self.fire_cd > 0:
            self.fire_cd -= 1

    def draw(self):
        # 绘制巨龙身体
        pygame.draw.ellipse(screen, DRAGON_RED, (self.x, self.y, self.width, self.height))
        # 龙头
        pygame.draw.circle(screen, DRAGON_RED, (self.x + self.width, self.y + self.height//2), 30)
        pygame.draw.circle(screen, WHITE, (self.x + self.width + 10, self.y + self.height//2 - 10), 8)
        pygame.draw.circle(screen, BLACK, (self.x + self.width + 12, self.y + self.height//2 - 10), 4)
        # 龙翅膀
        pygame.draw.polygon(screen, (180, 20, 20), [
            (self.x + 30, self.y),
            (self.x - 20, self.y - 30),
            (self.x + 50, self.y + 10)
        ])
        pygame.draw.polygon(screen, (180, 20, 20), [
            (self.x + 30, self.y + self.height),
            (self.x - 20, self.y + self.height + 30),
            (self.x + 50, self.y + self.height - 10)
        ])
        # 勇士
        pygame.draw.rect(screen, WARRIOR_GOLD, (self.x + 40, self.y - 25, 25, 35))
        pygame.draw.circle(screen, WARRIOR_GOLD, (self.x + 52, self.y - 30), 12)

    def shoot_fire(self):
        if self.fire_cd <= 0:
            self.fire_cd = 15
            fire = Fireball(self.x + self.width, self.y + self.height//2)
            fire_group.add(fire)

# 龙火焰子弹
class Fireball(pygame.sprite.Sprite):
    def __init__(self, x, y):
        super().__init__()
        self.radius = 12
        self.x = x
        self.y = y
        self.speed = 12

    def update(self):
        self.x += self.speed
        if self.x > WIDTH:
            self.kill()

    def draw(self):
        pygame.draw.circle(screen, FIRE_ORANGE, (self.x, self.y), self.radius)
        pygame.draw.circle(screen, COIN_YELLOW, (self.x, self.y), self.radius - 5)

# 障碍物山石
class Rock(pygame.sprite.Sprite):
    def __init__(self):
        super().__init__()
        self.w = random.randint(40, 100)
        self.h = random.randint(40, 100)
        self.x = random.randint(WIDTH, WIDTH + 300)
        self.y = random.randint(0, HEIGHT - self.h)
        self.speed = random.randint(3, 6)

    def update(self):
        self.x -= self.speed
        if self.x + self.w < 0:
            self.kill()

    def draw(self):
        pygame.draw.rect(screen, ROCK_GRAY, (self.x, self.y, self.w, self.h))

# 怪物
class Monster(pygame.sprite.Sprite):
    def __init__(self):
        super().__init__()
        self.size = 45
        self.x = random.randint(WIDTH, WIDTH + 400)
        self.y = random.randint(0, HEIGHT - self.size)
        self.speed = random.randint(4, 7)
        self.hp = 2

    def update(self):
        self.x -= self.speed
        if self.x + self.size < 0:
            self.kill()

    def draw(self):
        pygame.draw.rect(screen, MONSTER_PURPLE, (self.x, self.y, self.size, self.size))
        pygame.draw.circle(screen, WHITE, (self.x + 12, self.y + 15), 6)
        pygame.draw.circle(screen, WHITE, (self.x + 32, self.y + 15), 6)

# 金币
class Coin(pygame.sprite.Sprite):
    def __init__(self):
        super().__init__()
        self.r = 18
        self.x = random.randint(WIDTH, WIDTH + 300)
        self.y = random.randint(30, HEIGHT - 30)
        self.speed = 4

    def update(self):
        self.x -= self.speed
        if self.x - self.r < 0:
            self.kill()

    def draw(self):
        pygame.draw.circle(screen, COIN_YELLOW, (self.x, self.y), self.r)
        pygame.draw.circle(screen, (200, 160, 0), (self.x, self.y), self.r - 6)

# BOSS巨龙
class Boss(pygame.sprite.Sprite):
    def __init__(self):
        super().__init__()
        self.w = 220
        self.h = 160
        self.x = WIDTH + 100
        self.y = HEIGHT//2 - 80
        self.hp = 50  # BOSS血量上调，适配玩家100血
        self.speed = 2

    def update(self):
        self.x -= self.speed

    def draw(self):
        pygame.draw.ellipse(screen, BOSS_RED, (self.x, self.y, self.w, self.h))
        pygame.draw.circle(screen, BLACK, (self.x + self.w - 20, self.y + 40), 25)
        pygame.draw.circle(screen, WHITE, (self.x + self.w - 10, self.y + 30), 10)
        # 血条
        bar_w = 180
        bar_h = 12
        pygame.draw.rect(screen, BLACK, (self.x + 20, self.y - 25, bar_w, bar_h))
        pygame.draw.rect(screen, GREEN, (self.x + 20, self.y - 25, bar_w * (self.hp / 50), bar_h))

# 生成精灵组
fire_group = pygame.sprite.Group()
rock_group = pygame.sprite.Group()
monster_group = pygame.sprite.Group()
coin_group = pygame.sprite.Group()
boss_group = pygame.sprite.Group()

# 主游戏函数
def game_loop():
    dragon = Dragon()
    score = 0
    game_over = False
    win = False
    spawn_timer = 0
    boss_spawned = False

    while True:
        clock.tick(FPS)
        screen.fill(SKY_BLUE)

        # 事件监听
        for event in pygame.event.get():
            if event.type == pygame.QUIT:
                pygame.quit()
                sys.exit()
            if event.type == pygame.KEYDOWN:
                if event.key == pygame.K_ESCAPE:
                    pygame.quit()
                    sys.exit()
                if event.key == pygame.K_SPACE and not game_over and not win:
                    dragon.shoot_fire()

        if not game_over and not win:
            # 按键控制龙移动
            keys = pygame.key.get_pressed()
            dragon.speed_x = 0
            dragon.speed_y = 0
            if keys[pygame.K_a] or keys[pygame.K_LEFT]:
                dragon.speed_x = -dragon.max_speed
            if keys[pygame.K_d] or keys[pygame.K_RIGHT]:
                dragon.speed_x = dragon.max_speed
            if keys[pygame.K_w] or keys[pygame.K_UP]:
                dragon.speed_y = -dragon.max_speed
            if keys[pygame.K_s] or keys[pygame.K_DOWN]:
                dragon.speed_y = dragon.max_speed

            # 生成怪物、石头、金币
            spawn_timer += 1
            if spawn_timer % 90 == 0:
                rock_group.add(Rock())
            if spawn_timer % 120 == 0:
                monster_group.add(Monster())
            if spawn_timer % 70 == 0:
                coin_group.add(Coin())

            # 分数达标刷新BOSS
            if score >= 500 and not boss_spawned:
                boss_group.add(Boss())
                boss_spawned = True

            # 更新所有精灵
            dragon.update()
            fire_group.update()
            rock_group.update()
            monster_group.update()
            coin_group.update()
            boss_group.update()

            # 碰撞检测：龙撞石头/怪物扣血
            dragon_rect = pygame.Rect(dragon.x, dragon.y, dragon.width, dragon.height)
            # 山石碰撞
            for rock in rock_group:
                rock_rect = pygame.Rect(rock.x, rock.y, rock.w, rock.h)
                if dragon_rect.colliderect(rock_rect):
                    dragon.hp -= 10  # 碰撞一次扣10点血
                    rock.kill()
            # 怪物碰撞
            for mon in monster_group:
                mon_rect = pygame.Rect(mon.x, mon.y, mon.size, mon.size)
                if dragon_rect.colliderect(mon_rect):
                    dragon.hp -= 10  # 怪物撞击扣10血
                    mon.kill()
            # 金币拾取加分
            for coin in coin_group:
                coin_rect = pygame.Rect(coin.x - coin.r, coin.y - coin.r, coin.r*2, coin.r*2)
                if dragon_rect.colliderect(coin_rect):
                    score += 10
                    coin.kill()
            # 火球打怪物
            for fire in fire_group:
                fire_rect = pygame.Rect(fire.x - fire.radius, fire.y - fire.radius, fire.radius*2, fire.radius*2)
                for mon in monster_group:
                    mon_rect = pygame.Rect(mon.x, mon.y, mon.size, mon.size)
                    if fire_rect.colliderect(mon_rect):
                        mon.hp -= 1
                        fire.kill()
                        if mon.hp <= 0:
                            score += 25
                            mon.kill()
                # 火球打BOSS
                for boss in boss_group:
                    boss_rect = pygame.Rect(boss.x, boss.y, boss.w, boss.h)
                    if fire_rect.colliderect(boss_rect):
                        boss.hp -= 1
                        fire.kill()
                        if boss.hp <= 0:
                            win = True

            # 血量归零游戏结束
            if dragon.hp <= 0:
                game_over = True

        # 绘制所有元素
        dragon.draw()
        for f in fire_group:
            f.draw()
        for r in rock_group:
            r.draw()
        for m in monster_group:
            m.draw()
        for c in coin_group:
            c.draw()
        for b in boss_group:
            b.draw()

        # UI文字
        hp_text = font.render(f"巨龙血量：{dragon.hp}/100", True, BLACK)
        score_text = font.render(f"得分：{score}", True, BLACK)
        screen.blit(hp_text, (20, 10))
        screen.blit(score_text, (20, 45))

        # 游戏结束界面
        if game_over:
            over_text = boss_font.render("游戏结束！勇士陨落", True, (200, 0, 0))
            screen.blit(over_text, (WIDTH//2 - 280, HEIGHT//2 - 40))
        # 胜利界面
        if win:
            win_text = boss_font.render("通关成功！击败恶龙BOSS", True, GREEN)
            screen.blit(win_text, (WIDTH//2 - 320, HEIGHT//2 - 40))

        pygame.display.flip()

if __name__ == "__main__":
    game_loop()