会员可以在此提问,百战程序员老师有问必答
对大家有帮助的问答会被标记为“推荐”
看完课程过来浏览一下别人提的问题,会帮你学得更全面
截止目前,同学们一共提了 128778个问题

新建文件夹 (2).zip


老师为什么我运行的时候没有窗口显示出来

Python 全系列/第二阶段:Python 深入与提高/坦克大战 136楼
Python 全系列/第二阶段:Python 深入与提高/异常机制 137楼

'''
1.坦克类
    1.1 我方坦克
    1.2 敌方坦克
    坦克的显示
    坦克的移动
    坦克的射击

2. 子弹类
    显示子弹
    子弹的移动

3. 墙壁类
    显示墙壁

4. 爆炸的效果类
    显示爆炸效果

5. 音效类
    播放音效

6. 游戏主窗口类
    开始游戏
    结束游戏
'''

'''
坦克类
'''
import pygame
from time import sleep
import random

#设置通用属性
BG_COLOR = pygame.Color(156,156,156)
Screen_Width = 700
Screen_Height = 500
Text_Color = pygame.Color(255,0,0)

class Tank:
   
    def display_tank(self) -> None:
        '''
        显示坦克
        '''
        #获取最新坦克的朝向位置图片
        self.image = self.images.get(self.directon)
        MainGame.windows.blit(self.image,self.rect)
    def move(self) -> None:
        '''
        坦克移动
        '''
        if self.directon == 'L':
            #判断是否超出边界
            if self.rect.left > 0:
                #修改坦克的位置  离左边的距离
                self.rect.left -= self.speed
        elif self.directon == 'R':
            #判断是否超出边界
            if self.rect.left + self.rect.width < Screen_Width:
                #修改坦克的位置  离左边的距离
                self.rect.left += self.speed
        elif self.directon == 'U':
            #判断是否超出边界
            if self.rect.top > 0:
                #修改坦克的位置  离上边的距离
                self.rect.top -= self.speed
        elif self.directon == 'D':
            #判断是否超出边界
            if self.rect.top + self.rect.height < Screen_Height:
                #修改坦克的位置  离上边的距离
                self.rect.top += self.speed
    def shot(self) -> None:
        '''
        坦克射击
        '''
        pass

class Mytank(Tank):
    '''
    我方坦克
    '''
    def __init__(self,left,top) -> None:
        #设置我方坦克的图片资源
        self.images = {
            'U':pygame.image.load('./img/p1tankU.gif'),
            'D':pygame.image.load('./img/p1tankD.gif'),
            'L':pygame.image.load('./img/p1tankL.gif'),
            'R':pygame.image.load('./img/p1tankR.gif'),
        }
        #设置坦克的方向
        self.directon = 'L'
        #获取图片信息
        self.image = self.images.get(self.directon)
        #获取图形的矩形面积
        self.rect = self.image.get_rect()
        #设置我方坦克位置
        self.rect.left = left
        self.rect.top = top
        #设置移动速度
        self.speed = 15
        #设置移动开关
        self.remove = False

class Enemytank(Tank):
    '''
    敌方坦克
    '''
    def __init__(self,left,top,speed) -> None:
        self.images = {
            'U':pygame.image.load('./img/enemy1U.gif'),
            'D':pygame.image.load('./img/enemy1D.gif'),
            'L':pygame.image.load('./img/enemy1L.gif'),
            'R':pygame.image.load('./img/enemy1R.gif'),
        }
        #设置地方坦克的方向
        self.directon = self.rand_direction()
        #获取图片信息
        self.image = self.images.get(self.directon)
        #获取图像图形
        self.rect = self.image.get_rect()
        #设置敌方坦克位置
        self.rect.left = left
        self.rect.top = top
        #设置移动速度
        self.speed = speed
        #设置移动步长
        self.step = 30

    def rand_direction(self) -> str:
        '''
        生成随机方向
        '''
        chice = random.randint(1,4)
        if chice == 1:
            return 'U'
        elif chice == 2:
            return 'L'
        elif chice == 3:
            return 'D'
        elif chice == 4:
            return 'R'
   
    def rand_move(self):
        '''
        随机移动
        '''
        #判断步长是否为0
        if self.step <= 0:
            #如果小于0,更换方向
            self.directon = self.rand_direction()
            #重置步长
            self.step = 20
        else:
            #如果大于0,移动
            self.move()
            self.step -= 1
    def shot(self):
        '''
        敌方坦克的射击
        '''
        num = random.randint(1,100)
        if num < 9:
            return Bullet(self)

class Bullet:
    '''
    子弹类
    '''
    def __init__(self,tank) -> None:
        #加载图片
        self.image = pygame.image.load('./img/enemymissile.gif')
        #获取子弹的方向
        self.directon = tank.directon
        #获取子弹图形
        self.rect = self.image.get_rect()
        #设置子弹位置
        if self.directon =='L':
            #子弹的位置 = 坦克的位置+坦克的宽度/2 -子弹的宽度/2
            self.rect.top = tank.rect.top + tank.rect.height/2 - self.rect.height/2
            #子弹的位置 = 坦克的位置 - 子弹的宽度
            self.rect.left = tank.rect.left - self.rect.width
           
        elif self.directon =='R':
            #子弹的位置 = 坦克的位置+坦克的宽度/2 -子弹的宽度/2
            self.rect.top = tank.rect.top + tank.rect.height/2 - self.rect.height/2
            #子弹的位置 = 坦克的位置 - 子弹的宽度
            self.rect.left = tank.rect.left + self.rect.width
           
        elif self.directon =='U':
            #子弹的位置 = 坦克的位置+坦克的宽度/2 -子弹的宽度/2
            self.rect.left = tank.rect.left + tank.rect.width/2 - self.rect.width/2
            #子弹的位置 = 坦克的位置 - 子弹的高度
            self.rect.top = tank.rect.top - self.rect.height

        elif self.directon =='D':
            #子弹的位置 = 坦克的位置+坦克的宽度/2 -子弹的宽度/2
            self.rect.left = tank.rect.left + tank.rect.width/2 - self.rect.width/2
            #子弹的位置 = 坦克的位置 - 子弹的高度
            self.rect.top = tank.rect.top + self.rect.height
        #设置子弹的速度
        self.speed = 10

    def display_bullet(self) -> None:
        '''
        显示子弹
        '''
        MainGame.windows.blit(self.image,self.rect)
       
    def move_bullet(self) -> None:
        '''
        子弹的移动
        '''
        #根据子弹生成的方向来移动
        if self.directon == 'L':
            #判断子弹是否超出屏幕
            if self.rect.left > 0:
                self.rect.left -= self.speed

        elif self.directon == 'R':
            if self.rect.left + self.rect.width < Screen_Width:
                self.rect.left += self.speed
        elif self.directon == 'U':
            if self.rect.top > 0:
                self.rect.top -= self.speed
        elif self.directon == 'D':
            if self.rect.top + self.rect.height < Screen_Height:
                self.rect.top += self.speed

class Wall:
    '''
    墙壁类
    '''
    def __init__(self) -> None:
        pass
    def display_wall(self) -> None:
        '''
        显示墙壁
        '''
        pass

class Explode:
    '''
    爆炸效果类
    '''
    def __init__(self) -> None:
        pass
    def display_explode(self) -> None:
        '''
        显示爆炸效果
        '''
        pass

class Music:
    '''
    音乐类
    '''
    def __init__(self) -> None:
        pass
    def play_music(self) -> None:
        '''
        播放音效
        '''
        pass

class MainGame:
    '''
    游戏主窗口类
    '''
    #设置主窗口对象
    windows = None
    #设置我方坦克的位置
    my_tank = None
    #存储敌方坦克的列表
    enemy_tank_list = []
    #设置敌方坦克的数量
    enemy_tank_count = 6
    #存储我方子弹的列表
    my_bullet_list = []
    #存储敌方子弹列表
    enemy_bullet_list = []


    def __init__(self) -> None:
        pass
    def start_game(self) -> None:
        '''
        开始游戏
        '''
        pygame.display.init()
        #创建一个窗口
        MainGame.windows = pygame.display.set_mode((Screen_Width,Screen_Height))
        #设置窗口标题
        pygame.display.set_caption('坦克大战')
        #创建一个我方坦克
        MainGame.my_tank = Mytank(450,300)
        #创建敌方坦克
        self.creat_enemy_tank()

        #刷新窗口
        while True:
            sleep(0.06)
            #添加背景色
            MainGame.windows.fill(BG_COLOR)
            #增加提示文字
            #1. 增加文字的内容及字体
            #获得可用字体
            #num = 6
            text = self.get_text_surface(f'敌方坦克的剩余数量{MainGame.enemy_tank_count}')
            #2. 如何添加文字
            MainGame.windows.blit(text,(10,10))
            #增加事件
            self.get_event()
            #显示我方坦克
            MainGame.my_tank.display_tank()
            #显示敌方坦克
            self.display_enemy_tank()
            #一直移动坦克
            if MainGame.my_tank.remove:
                MainGame.my_tank.move()
            #显示我方子弹
            self.display_my_bullet()
            #显示敌方子弹
            self.display_enemy_bullet()
            pygame.display.update()
           
    def display_my_bullet(self) -> None:
        '''
        显示我方子弹
        '''
        for my_bullet in MainGame.my_bullet_list:
            #显示我方子弹
            my_bullet.display_bullet()
            #移动我方子弹
            my_bullet.move_bullet()

    def creat_enemy_tank(self) -> None:
        '''
        创建地方坦克
        '''
        self.enemy_top = 100
        self.enemy_speed = 8
        for i in range(self.enemy_tank_count):
            #生成坦克位置
            left = random.randint(0,600)
            #创建敌方坦克
            e_tank = Enemytank(left,self.enemy_top,self.enemy_speed)
            #将敌方坦克添加到列表中
            self.enemy_tank_list.append(e_tank)

    def display_enemy_tank(self) -> None:
        '''
        显示敌方坦克
        '''
        for e_tank in self.enemy_tank_list:
            #显示敌方坦克
            e_tank.display_tank()
            #移动敌方坦克
            e_tank.rand_move()
            #发射子弹
            e_bullet = e_tank.shot()
            #判断是否有子弹
            if e_bullet:
                #将子弹添加到列表中
                MainGame.enemy_bullet_list.append(e_bullet)
               
   
    def display_enemy_bullet(self) -> None:
        '''
        显示敌方子弹
        '''
        for e_bullet in MainGame.enemy_bullet_list:
            #显示子弹
            # if e_bullet.live:
                # 如果存活
                    e_bullet.display_bullet()
                    e_bullet.move_bullet()
            # else:
                #如果子弹不存活
                # MainGame.enemy_bullet_list.remove(e_bullet)
               
    def get_text_surface(self,text:str) -> None:
        '''
        获取文字的图片
        '''
        #初始化字体模块
        pygame.font.init()
        # #获取可以使用的所有字体
        # print(pygame.font.get_fonts())
        #创建字体
        font = pygame.font.SysFont('kaiti',18)
        #绘制文字内容
        text_surface = font.render(text,True,Text_Color)
        #将绘制的文字信息返回
        return text_surface
    def get_event(self) -> None:
        '''
        获取事件
        '''
        #获取所有事件
        event_list = pygame.event.get()
        for event in event_list:
            #判断是什么事件,然后做吹相应的处理
            if event.type == pygame.QUIT:
                #点击X退出游戏
                self.end_game()
            if event.type == pygame.KEYDOWN:
                #按下键盘
                if event.key == pygame.K_LEFT:
                    print('坦克向左移动')
                    #修改方向
                    MainGame.my_tank.directon = 'L'
                    #修改坦克可以移动
                    MainGame.my_tank.remove = True
                    #通过坦克对象
                    # MainGame.my_tank.move()
                elif event.key == pygame.K_RIGHT:
                    print('坦克向右移动')
                    MainGame.my_tank.directon = 'R'
                    #修改坦克可以移动
                    MainGame.my_tank.remove = True
                    # MainGame.my_tank.move()
                elif event.key == pygame.K_UP:
                    print('坦克向上移动')
                    MainGame.my_tank.directon = 'U'
                    #修改坦克可以移动
                    MainGame.my_tank.remove = True
                    # MainGame.my_tank.move()
                elif event.key == pygame.K_DOWN:
                    print('坦克向下移动')
                    MainGame.my_tank.directon = 'D'
                    #修改坦克可以移动
                    MainGame.my_tank.remove = True
                    # MainGame.my_tank.move()
                elif event.key == pygame.K_SPACE:
                    #发射子弹
                    print('发射子弹')
                    #创建子弹
                    m_bullet = Bullet(MainGame.my_tank)
                    #将子弹添加到列表中
                    MainGame.my_bullet_list.append(m_bullet)

            if event.type == pygame.KEYUP and event.key in (pygame.K_LEFT,pygame.K_RIGHT,pygame.K_UP,pygame.K_DOWN):
                #修改坦克的移动状态
                MainGame.my_tank.remove = False

            #可以吧循环体中的move模块都移动到这里
            # MainGame.my_tank.move()

    def end_game(self) -> None:
        '''
        结束游戏
        '''
        print('结束游戏,欢迎再次使用')
        exit()


if __name__ == '__main__':
    #调用MainGame中的start_game方法,开始游戏
    MainGame().start_game()
    
    
    
    
    Hello from the pygame community. https://www.pygame.org/contribute.html
Traceback (most recent call last):
  File "e:\VScode\TANK_GAME\17. 敌方坦克发射子弹.py", line 460, in <module>
    MainGame().start_game()
  File "e:\VScode\TANK_GAME\17. 敌方坦克发射子弹.py", line 324, in start_game
    self.display_enemy_bullet()
  File "e:\VScode\TANK_GAME\17. 敌方坦克发射子弹.py", line 374, in display_enemy_bullet
    if e_bullet.live:
       ^^^^^^^^^^^^^
AttributeError: 'Bullet' object has no attribute 'live'
这个‘live’命令是系统自带的吗,为什么我在调用的时候提醒我没有这个目标呢

Python 全系列/第二阶段:Python 深入与提高/坦克大战 139楼
Python 全系列/第二阶段:Python 深入与提高/坦克大战 140楼
Python 全系列/第二阶段:Python 深入与提高/坦克大战 141楼

import pygame


# 设置通用属性

BG_COLOR = pygame.Color(0,0,0)

SCREEN_WIDTH = 700

SCREEN_HEIGHT = 500

TEXT_COLOR = pygame.Color(255,0,0)


class Tank:

         #'''坦克类'''

    def __init__(self,left:int,top:int) -> None:

        # 设置我方坦克的图片资源

        self.images = {

            'U':pygame.image.load('./img/p1tankU.gif'),

            'D':pygame.image.load('./img/p1tankD.gif'),

            'L':pygame.image.load('./img/p1tankL.gif'),

            'R':pygame.image.load('./img/p1tankR.gif'),

            }

        # 设置我方坦克的方向

        self.direction = 'L'

        # 获取图片信息

        self.image = self.images.get(self.direction)

         # 获取图片的矩形

        self.rect = self.image.get_rect()

        # 设置我方坦克位置

        self.rect.left = left

        self.rect.top = top



    def display_tank(self) -> None:

        #'''显示坦克'''

        self.image = self.images.get(self.direction)

        MainGame.window.blit(self.image,self.rect)


class MainGame:

 # '''游戏主窗口类'''  

    window = None

    my_tank = None


    def __init__(self) -> None:

        pass

    def start_game(self) -> None:

        # '''开始游戏 # 初始化游戏窗口

        pygame.display.init()

             # 创建一个窗口

        MainGame.window = pygame.display.set_mode((SCREEN_WIDTH,SCREEN_HEIGHT))

        # 设置窗口标题

        pygame.display.set_caption('坦克小子')

        # 创建一个我方 坦克

        MainGame.my_tank = Tank(350,200)

        # 刷新窗口

        while True:

             # 给窗口设置填充色

            MainGame.window.fill(BG_COLOR)

            # 1.要增加文字内容

            num = 6

            text = self.get_text_surface(f'敌方坦克剩余数量{num}')

             # 2.如何把文字加上

            MainGame.window.blit(text,(10,10))

            #增加事件

            self.get_event()

             # 显示 我方坦克

            MainGame.my_tank.display_tank()

            pygame.display.update()


    def get_text_surface(self,text:str) -> None:

        '''获取文字的图片'''

  # 初始化字体模块

        pygame.font.init()

  # 获取可以使用的字体

  # print(pygame.font.get_fonts())

  # 创建字体

        font = pygame.font.SysFont('kaiti',18)

  # 绘制文字信息

        text_surface = font.render(text,True,TEXT_COLOR)

  # 将绘制的文字信息返回

        return text_surface



    def get_event(self) -> None:

   # '''获取事件'''# 获取所有事件

        event_list = pygame.event.get()

    # 遍历事件

        for event in event_list:

      # 判断是什么事件,然后做出相应的处理

            if event.type == pygame.QUIT:

        # 点击关闭按钮

                self.end_game()

            if event.type == pygame.KEYDOWN:

        # 按下键盘

                if event.key == pygame.K_LEFT:

                    print('坦克向左移动')

                    MainGame.my_tank.direction = 'L'

                    MainGame.my_tank.move()

                elif event.key == pygame.K_RIGHT:

                    print('坦克向右移动')

                    MainGame.my_tank.direction = 'R'

                    MainGame.my_tank.move()

                elif event.key == pygame.K_UP:

                    print('坦克向上移动')

                    MainGame.my_tank.direction = 'U'

                    MainGame.my_tank.move()

                elif event.key == pygame.K_DOWN:

                    print('坦克向下移动')

                    MainGame.my_tank.direction = 'D'

                    MainGame.my_tank.move()

    def end_game(self) -> None:

    #'''结束游戏'''

        print('谢谢使用,欢迎再次使用')

        exit()


if __name__ == "__main__":

  # 调用MainGame类中的start_game方法,开始游戏

    MainGame().start_game()

                                 



        #坦克的移动方法

    def move(self):

        pass

  #碰撞墙壁的方法

    def hitWalls(self):

        pass

  #射击方法

    def shot(self):

        pass

  #展示坦克

    def displayTank(self):

        pass

class MyTank(Tank):                             #我方坦克类

 

    def __init__(self):

        pass

  #碰撞敌方坦克的方法

    def hitEnemyTank(self):

        pass

class EnemyTank(Tank):

  #'''敌方坦克类'''

    def __init__(self) -> None:

        pass

class Bullet:

  #'''子弹类'''

    def __init__(self) -> None:

        pass

    def display_bullet(self) -> None:

    #'''显示子弹'''

        pass

    def move(self) -> None:

    #'''子弹的移动 '''

        pass

class Wall:

  #'''墙壁类'''

    def __init__(self) -> None:

        pass

    def display_wall(self) -> None:

    #'''显示墙壁'''

        pass

class Explode:

  #'''爆炸效果类'''

    def __init__(self) -> None:

        pass

    def display_explode(self) -> None:

    #'''显示爆炸效果'''

        pass

class Music:

  #'''音效类'''

    def __init__(self) -> None:

      pass

    def play_music(self) -> None:

    #'''播放音效'''

        pass


为啥我的是运行后一按就闪退?









Python 全系列/第二阶段:Python 深入与提高/坦克大战 142楼
Python 全系列/第二阶段:Python 深入与提高/坦克大战 143楼
Python 全系列/第二阶段:Python 深入与提高/文件处理 144楼
Python 全系列/第二阶段:Python 深入与提高/坦克大战 146楼
Python 全系列/第二阶段:Python 深入与提高/模块 147楼
Python 全系列/第二阶段:Python 深入与提高/坦克大战 148楼
Python 全系列/第二阶段:Python 深入与提高/坦克大战 149楼
Python 全系列/第二阶段:Python 深入与提高/坦克大战 150楼

百战程序员微信公众号

百战程序员微信小程序

©2014-2024 百战汇智(北京)科技有限公司 All Rights Reserved 北京亦庄经济开发区科创十四街 赛蒂国际工业园
网站维护:百战汇智(北京)科技有限公司
京公网安备 11011402011233号    京ICP备18060230号-3    营业执照    经营许可证:京B2-20212637