小格格1125 2025-06-17 21:55 采纳率: 60%
浏览 7
已结题

我奇葩的Pygame代码出错了

我想用Pygame做一个游戏,这个游戏是一个小人在一大堆石头中间有一个隧道在里面走,具体的我也讲不清,直接放源码吧:

#!/usr/bin/python3
# Filename: Game_constant_file.py

import pygame as pg
import sys
import os
import Game_constant_file as constant

pg.init()
pg.key.set_repeat(10, 15)

# 设置窗口大小
screen_width, screen_height = constant.SCREEN_SIZE
screen = pg.display.set_mode((screen_width, screen_height))

# 设置窗口标题
pg.display.set_caption(constant.TITLE)

def change_brightness(nimage, bright):
    image = nimage.copy()

    # 循环遍历图像的每个像素
    for x in range(image.get_width()):
        for y in range(image.get_height()):
            # 获取当前像素的颜色值
            color = image.get_at((x, y))
            # 修改亮度
            new_color = [min(int(c * bright), 255) for c in color[:3]]
            new_color.append(color.a)
            # 设置修改后的颜色值
            image.set_at((x, y), tuple(new_color))

    return image

# 图像加载函数(带错误处理)
def load_image(filename, brightness=1.0):
    """加载图像并调整亮度,带错误处理"""
    try:
        # 确保在正确目录
        os.chdir(os.path.dirname(os.path.abspath(__file__)))
        
        # 加载图像并转换格式
        image = pg.image.load(filename).convert_alpha()
        
        # 调整亮度
        if brightness != 1.0:
            return change_brightness(image, brightness)
        return image
    except pg.error as e:
        print(f"无法加载图像: {filename}")
        print(f"错误信息: {e}")
        # 创建替代图像
        temp_surface = pg.Surface((50, 50), pg.SRCALPHA)
        pg.draw.rect(temp_surface, (255, 0, 0), (0, 0, 50, 50))
        pg.draw.line(temp_surface, (0, 0, 0), (0, 0), (50, 50), 2)
        pg.draw.line(temp_surface, (0, 0, 0), (50, 0), (0, 50), 2)
        return temp_surface

# 玩家类(优化版)
class Player(pg.sprite.Sprite):
    def __init__(self):
        super().__init__()
        
        # 预加载所有图像
        self.images = {
            'stand': load_image('stand.png', 1.0),
            'left': load_image('left.png', 1.0),
            'right': load_image('right.png', 1.0)
        }
        
        self.image = self.images['stand']
        # 玩家固定在屏幕中央底部
        self.rect = self.image.get_rect()
        self.speed = 5
        self.direction = 0
        self.lightness = 1

    def update(self, key):
        # 玩家位置固定不动,只改变图像
        if key == 'left':
            self.image = self.images['left']
        elif key == 'right':
            self.image = self.images['right']
        else:
            self.image = self.images['stand']

    def draw(self, x, y):
        screen.blit(self.image, (x, y))

player = Player()
player_group = pg.sprite.Group()
player_group.add(player)

# 石头类
class Stone(pg.sprite.Sprite):
    stone_images = {}
    
    @classmethod
    def load_images(cls):
        if not cls.stone_images:
            base_image = load_image('stone.png')
            cls.stone_images['normal'] = base_image
            cls.stone_images['dim'] = change_brightness(base_image.copy(), 0.5)
    
    def __init__(self, x, y):
        super().__init__()
        Stone.load_images()
        # 判断是否在隧道区域
        is_tunnel = (10 <= y <= 12)
        self.image = self.stone_images['dim' if is_tunnel else 'normal']
        self.mode = 'tunnel' if is_tunnel else 'stone'
        self.rect = self.image.get_rect()
        self.x = x
        self.y = y
        self.rect.x = x * 50
        self.rect.y = y * 50
        self.lightness = 1

    def update(self, dx=0, dy=0):
        # 移动石头
        self.rect.x += dx
        self.rect.y += dy

stone_group = pg.sprite.Group()
tunnel_group = pg.sprite.Group()
stones_group = pg.sprite.Group()

# 隧道判断函数
tunnel_jm = lambda x, y: 10 <= y <= 12

# 游戏主循环
def main():
    global screen  # 声明screen为全局变量
    
    fullscreen = False
    done = False
    clock = pg.time.Clock()
    
    # 初始化石头
    for stone_x in range(0, 29):
        for stone_y in range(0, 18):
            stone = Stone(stone_x, stone_y)
            stones_group.add(stone)
            if tunnel_jm(stone_x, stone_y):
                tunnel_group.add(stone)
            else:
                stone_group.add(stone)
    
    while not done: 
        # 处理事件
        dx = 0  # 石头移动距离
        
        for event in pg.event.get():
            if event.type == pg.QUIT:
                done = True
            elif event.type == pg.KEYDOWN:
                if event.key == pg.K_LEFT:
                    dx = 5  # 石头向右移动
                    player.update('left')
                elif event.key == pg.K_RIGHT:
                    dx = -5  # 石头向左移动
                    player.update('right')
                elif event.key == pg.K_ESCAPE:
                    done = True
                elif event.key == pg.K_F11:
                    if not fullscreen:
                        screen = pg.display.set_mode(constant.SCREEN_SIZE, pg.FULLSCREEN)
                        fullscreen = True
                    else:
                        screen = pg.display.set_mode(constant.SCREEN_SIZE)
                        fullscreen = False
            elif event.type == pg.KEYUP:
                player.update('stand')
        
        # 移动所有石头(制造玩家移动的错觉)
        if dx != 0:
            for stone in stones_group:
                stone.update(dx=dx)

        #撞检测
        if pg.sprite.spritecollide(player, stone_group, False):
            stones_group.update(dy=1)
        elif pg.sprite.spritecollide(player, tunnel_group, False):
            stones_group.update(dy=-1)
        
        # 填充背景色
        screen.fill((0, 220, 255))
        
        # 绘制石头
        stones_group.draw(screen)
        
        # 绘制玩家
        player.draw(100,540)
        
        # 更新窗口
        pg.display.flip()
        clock.tick(60)
    
    pg.quit()
    sys.exit()

if __name__ == "__main__":
    main()

这是让AI帮忙生成的注释,运行完程序所有石头直接往上飘,当时我自己都蒙了,希望广大网友帮提提意见。
(在这里感谢大家了😀)

  • 写回答

5条回答 默认 最新

  • 阿里嘎多学长 2025-06-17 21:55
    关注

    阿里嘎多学长整理AIGC生成,因移动端显示问题导致当前答案未能完全显示,请使用PC端查看更加详细的解答过程

    问题解答

    你的Pygame代码出错了,根据你提供的代码,可能是因为你没有正确地导入Pygame模块或没有正确地初始化Pygame环境。

    首先,检查你的代码是否正确地导入Pygame模块:

    import pygame
    

    如果你已经正确地导入了Pygame模块,那么可能是因为你没有正确地初始化Pygame环境。Pygame需要在每个游戏循环中被初始化和更新。

    你可以尝试使用以下代码来初始化Pygame环境:

    pygame.init()
    screen = pygame.display.set_mode((800, 600))
    pygame.display.set_caption('Game')
    

    其中,800600是屏幕的宽度和高度,Game是游戏的标题。

    如果你已经正确地初始化了Pygame环境,那么可能是因为你的代码中有语法错误或逻辑错误。可以尝试使用PyCharm或其他IDE来检查代码中的错误。

    如果你仍然无法解决问题,可以提供更多的代码信息或错误信息,我将尽力帮助你解决问题。

    评论

报告相同问题?

问题事件

  • 已结题 (查看结题原因) 6月29日
  • 创建了问题 6月17日