import pygame
import random

# 1. 初始化 Pygame
pygame.init()

# 2. 定义屏幕和基础参数
WIDTH, HEIGHT = 600, 800
screen = pygame.display.set_mode((WIDTH, HEIGHT))
pygame.display.set_caption("是男人就下一百层（跳跃优化版）")
clock = pygame.time.Clock()
FPS = 60

# 定义颜色
WHITE = (255, 255, 255)
BLACK = (0, 0, 0)
GREEN = (0, 255, 0)      # 普通踏板
BLUE = (0, 100, 255)     # 传送带
YELLOW = (255, 255, 0)   # 易碎板
RED = (255, 0, 0)        # 钉板

# 3. 玩家类
class Player(pygame.sprite.Sprite):
    def __init__(self, all_sprites_group, platforms_group):
        super().__init__()
        self.image = pygame.Surface((30, 30))
        self.image.fill(WHITE)
        self.rect = self.image.get_rect()
        self.rect.centerx = WIDTH // 2
        self.rect.top = 100
        self.speed_x = 0
        self.vel_y = 0
        self.gravity = 0.6
        self.jump_power = -16  # 【再次优化】从-14提升到-16，跳得更高，确保能踩到慢速踏板
        self.on_ground = False

        # 玩家出生时自动生成保底踏板
        first_platform = Platform(self.rect.bottom - 5, "normal")
        first_platform.rect.centerx = self.rect.centerx
        all_sprites_group.add(first_platform)
        platforms_group.add(first_platform)

    def update(self):
        keys = pygame.key.get_pressed()
        if keys[pygame.K_LEFT] or keys[pygame.K_a]:
            self.speed_x = -5
        elif keys[pygame.K_RIGHT] or keys[pygame.K_d]:
            self.speed_x = 5
        else:
            self.speed_x = 0
        
        self.rect.x += self.speed_x
        if self.rect.right > WIDTH: self.rect.right = WIDTH
        if self.rect.left < 0: self.rect.left = 0

        self.vel_y += self.gravity
        self.rect.y += self.vel_y
        
        if self.rect.top > HEIGHT or self.rect.top < 0:
            return False
        return True

    def jump(self):
        if self.on_ground:
            self.vel_y = self.jump_power
            self.on_ground = False

# 4. 踏板类
class Platform(pygame.sprite.Sprite):
    def __init__(self, y_pos, p_type="normal"):
        super().__init__()
        self.p_type = p_type
        self.width = 100
        self.height = 15
        
        if p_type == "normal":
            self.color = GREEN
            self.speed_y = 2
            self.speed_x = 0
        elif p_type == "spike":
            self.color = RED
            self.speed_y = 2
            self.speed_x = 0
        elif p_type == "fragile":
            self.color = YELLOW
            self.speed_y = 2
            self.speed_x = 0
        elif p_type == "conveyor":
            self.color = BLUE
            self.speed_y = 1.5
            self.speed_x = random.choice([-2, 2])
            self.width = 120

        self.image = pygame.Surface((self.width, self.height))
        self.image.fill(self.color)
        self.rect = self.image.get_rect()
        self.rect.x = random.randrange(0, WIDTH - self.rect.width)
        self.rect.y = y_pos
        self.broken = False

    def update(self):
        self.rect.y += self.speed_y
        self.rect.x += self.speed_x
        
        if self.p_type == "conveyor":
            if self.rect.left < 0 or self.rect.right > WIDTH:
                self.speed_x = -self.speed_x

        if self.rect.top > HEIGHT:
            self.kill()

# 5. 游戏主循环
running = True
game_over = False

all_sprites = pygame.sprite.Group()
platforms = pygame.sprite.Group()

player = Player(all_sprites, platforms)
all_sprites.add(player)

for i in range(1, 7):
    p_type = random.choice(["normal", "normal", "conveyor", "fragile"])
    p = Platform(100 - i * 120, p_type)
    all_sprites.add(p)
    platforms.add(p)

score = 0
font = pygame.font.SysFont("arial", 30)
ADDPLATFORM = pygame.USEREVENT + 1
pygame.time.set_timer(ADDPLATFORM, 600)

while running:
    clock.tick(FPS)
    
    for event in pygame.event.get():
        if event.type == pygame.QUIT:
            running = False
        elif event.type == pygame.KEYDOWN:
            if event.key == pygame.K_SPACE or event.key == pygame.K_UP or event.key == pygame.K_w:
                if not game_over:
                    player.jump()
                else:
                    game_over = False
                    score = 0
                    all_sprites.empty()
                    platforms.empty()
                    player = Player(all_sprites, platforms)
                    all_sprites.add(player)
                    for i in range(1, 7):
                        p_type = random.choice(["normal", "normal", "conveyor", "fragile"])
                        p = Platform(100 - i * 120, p_type)
                        all_sprites.add(p)
                        platforms.add(p)
            elif event.key == pygame.K_r and game_over:
                game_over = False
                score = 0
                all_sprites.empty()
                platforms.empty()
                player = Player(all_sprites, platforms)
                all_sprites.add(player)
                for i in range(1, 7):
                    p_type = random.choice(["normal", "normal", "conveyor", "fragile"])
                    p = Platform(100 - i * 120, p_type)
                    all_sprites.add(p)
                    platforms.add(p)

        elif event.type == ADDPLATFORM and not game_over:
            rand_num = random.random()
            if score > 20 and rand_num < 0.1:
                p_type = "spike"
            elif rand_num < 0.4:
                p_type = "conveyor"
            elif rand_num < 0.6:
                p_type = "fragile"
            else:
                p_type = "normal"
            
            new_platform = Platform(-20, p_type)
            all_sprites.add(new_platform)
            platforms.add(new_platform)

    if not game_over:
        all_sprites.update()
        if not player.update():
            game_over = True

        hits = pygame.sprite.spritecollide(player, platforms, False)
        player.on_ground = False
        
        if hits:
            hit = hits[0]
            if player.vel_y >= 0 and player.rect.bottom <= hit.rect.centery:
                player.rect.bottom = hit.rect.top
                player.vel_y = 0
                player.on_ground = True
                player.rect.y += hit.speed_y

                if hit.p_type == "spike":
                    game_over = True
                elif hit.p_type == "fragile" and not hit.broken:
                    hit.broken = True
                    hit.kill()
                    score += 1
                else:
                    if not hasattr(hit, 'scored'):
                        hit.scored = True
                        score += 1

    screen.fill(BLACK)
    all_sprites.draw(screen)
    
    score_text = font.render(f"Score: {score}", True, WHITE)
    screen.blit(score_text, (10, 10))

    if game_over:
        over_text = font.render("GAME OVER! Final Score: " + str(score), True, RED)
        restart_text = font.render("Press SPACE or R to Restart", True, WHITE)
        screen.blit(over_text, (WIDTH//2 - 200, HEIGHT//2 - 30))
        screen.blit(restart_text, (WIDTH//2 - 150, HEIGHT//2 + 20))

    pygame.display.flip()

pygame.quit()