欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

通过pygame实现的python飞机大战项目

程序员文章站 2022-05-28 10:23:48
...

游戏主要特点

  • 游戏自带时间计数和成绩计数。
  • 游戏的子弹有7种,通过拾取道具可以升级子弹,子弹拥有持续时间,超过持续时间会降级。
  • 游戏道具有6种,分别为“伪三连散射”,“EXP X2”,“毫无特效的保护盾”,“升级为好看子弹1号”,“升级为好看子弹2号”,“普通子弹升级”。
  • 游戏我方飞机为4种,为“粉”,“红”,“黄”,“蓝”四种飞机,没有区别,顶多碰撞箱大小不一样,开局随机,吃到“子弹升级”飞机同时升级(碰撞箱变大)。
  • 游戏有四种背景,开局随机。
  • 游戏子弹击中敌机有1分爆炸特效,敌机爆炸也有1毛特效。
  • 游戏敌机分大中小三种,它们的血量不同,分数不同,小敌机8种,中敌机5种,大敌机2种。
  • 游戏飞机只能y轴移动,不会开火,非常沙雕。
  • 游戏敌机血量在一定范围内随机。
  • 我方飞机为鼠标控制,开火鼠标左击。开火有间隔。

一个佛系介绍

素材使用网络素材,腾讯全民飞机大战同款素材,只用于学习(shui文章)

老师要求的python练习题目为飞机大战,使用pygame完成。

由于面向对象掌握不太行,代码可读性。。。能跑就行。
pygame函数众多,学习时间较短,pygame的教程为英文,对于英语渣十分不友好,于是很多的操作使用基础函数魔改而成,没有运用自带的函数。

下面为游戏截图:
通过pygame实现的python飞机大战项目
游戏没有开始界面,解释编译即玩。
游戏退出极其简单,撞死就行,或右上角X。

通过pygame实现的python飞机大战项目

游戏玩法

  1. 运行代码
  2. 移动鼠标,控制飞机
  3. 鼠标左击,发射子弹
  4. 捡道具升级飞机
  5. 等待狗带

介绍完毕,放代码。。。

一段没有素材等于废话的全代码

python代码+素材,点击跳转

import pygame
import sys
import random
import json
import time
from pygame.locals import *
pygame.init()

#导入我方飞机模型
with open("data/plane.json","r") as f:
    plane_data1=json.loads(f.read())
plane_model = pygame.image.load("data/Skin.png")
planeRandom = random.randint(1,4)
plane=plane_data1["plane{}".format(planeRandom)]
plane1_1=plane["level1"]
plane1=plane_model.subsurface(Rect(plane1_1))#对应飞机模型切割导入

#导入敌方飞机模型
with open("data/enemy_model.json","r") as f:
    enemy_data1=json.loads(f.read())
enemy_model = pygame.image.load("data/enemyplane.png")

#导入子弹模型
with open("data/bullet.json","r") as f:
    bullet_data1=json.loads(f.read())
bullet_model = pygame.image.load("data/bullet.png")
bullet_yellow = bullet_data1["yellow"]
bullet_blue = bullet_data1["blue"]
bullet1 = bullet_model.subsurface(bullet_yellow["1"])

#导入奖励箱模型
with open("data/luckbox.json","r") as f:
    luckbox_data1=json.loads(f.read())
luckbox_model = pygame.image.load("data/luckbox.png")

#导入数字模型
with open("data/numY.json","r") as f:
    num_data=json.loads(f.read())
num_model=pygame.image.load("data/num_Y.png")

#导入爆炸画面
with open("data/break.json","r") as f:
    break_data=json.loads(f.read())
break_model=pygame.image.load("data/Break.png")
break_1 = break_data["cratch"]
break_2 = break_data["break"]

#显示时间
def digital_time(screen):#63,85#125,261
    playtime = int(time.time()-start)
    if playtime//60<10:
        showmin = "0"+str(playtime//60)
    else:
        showmin = str(playtime // 60)
    if playtime%60<10:
        showsec = "0"+str(playtime%60)
    else:
        showsec = str(playtime%60)
    j=0
    for i in showmin:
        num=num_model.subsurface(Rect(num_data[i]))
        num=pygame.transform.smoothscale(num,(30,40))
        screen.blit(num,(30*j,0))
        j=1
    j=0
    for i in showsec:
        num=num_model.subsurface(Rect(num_data[i]))
        num=pygame.transform.smoothscale(num,(30,40))
        screen.blit(num,(65+30*j,0))
        j=1

#显示积分
def digital_num(screen):
    global score
    showscore=str(score)
    j=0
    for i in showscore[::-1]:
        num = num_model.subsurface(Rect(num_data[i]))
        num = pygame.transform.smoothscale(num, (30, 40))
        screen.blit(num, (482 - 30 * j, 0))
        j+=1

#制造小飞机
def plan_s():
    modelNum=random.randint(1,8)
    enemy_rectS = enemy_data1["enemyS"]
    enemyrect = enemy_rectS["enemy{}".format(modelNum)]
    whatX = random.randint(-50, 300 - enemyrect[2])
    position = random.randint(enemyrect[2], enemyrect[2]+30)
    planeNum=random.randint(3,6)
    planeHealth=random.randint(2,4)
    for i in range(planeNum):
        if whatX+position*i+ enemyrect[2]>550:
            break
        p1=[1,modelNum,[whatX+position*i,-enemyrect[3]]]
        c1=[p1,enemyrect[2],enemyrect[3],planeHealth]
        enemyPlane.append(p1)
        collisionBox.append(c1)

#制造中飞机
def plan_m():
    modelNum=random.randint(1,5)
    enemy_rectM = enemy_data1["enemyM"]
    enemyrect = enemy_rectM["enemy{}".format(modelNum)]
    whatX = random.randint(-60, 230 - enemyrect[2])
    position = random.randint(enemyrect[2], enemyrect[2] + 30)
    planeNum = random.randint(2, 4)
    planeHealth = random.randint(7, 9)
    for i in range(planeNum):
        if whatX+position*i+ enemyrect[2] > 570:
            break
        p1 = [2, modelNum, [whatX + position * i, -enemyrect[3]]]
        c1 = [p1, enemyrect[2], enemyrect[3], planeHealth]
        enemyPlane.append(p1)
        collisionBox.append(c1)

#制造Boss飞机
def plan_l():
    modelNum=random.randint(1,2)
    enemy_rectL = enemy_data1["enemyL"]
    enemyrect = enemy_rectL["enemy{}".format(modelNum)]
    whatX = random.randint(0, 512 - enemyrect[2])
    planeHealth = random.randint(14, 18)
    p1 = [3, modelNum, [whatX, -enemyrect[3]]]
    c1 = [p1, enemyrect[2], enemyrect[3], planeHealth]
    enemyPlane.append(p1)
    collisionBox.append(c1)

#绘制敌人
def blict_enemy(screen):
    for enemy in enemyPlane:
        if enemy == None:
            return
        if enemy[0] == 1:
            if enemy[2][1]>600:
                try:
                    collisionBox.remove(collisionBox[enemyPlane.index(enemy)])
                except:
                    pass
                enemyPlane.remove(enemy)
                continue
            enemy_rectS = enemy_data1["enemyS"]
            enemyrect = enemy_rectS["enemy{}".format(enemy[1])]
            enemyNow=enemy_model.subsurface(Rect(enemyrect))
            enemy[2][1]+=3
            screen.blit(enemyNow,enemy[2])
            continue
        if enemy[0] == 2:
            if enemy[2][1]>600:
                try:
                    collisionBox.remove(collisionBox[enemyPlane.index(enemy)])
                except:
                    pass
                enemyPlane.remove(enemy)
                continue
            enemy_rectM = enemy_data1["enemyM"]
            enemyrect = enemy_rectM["enemy{}".format(enemy[1])]
            enemyNow=enemy_model.subsurface(Rect(enemyrect))
            enemy[2][1]+=2
            screen.blit(enemyNow,enemy[2])
            continue
        if enemy[0] == 3:
            if enemy[2][1]>600:
                try:
                    collisionBox.remove(collisionBox[enemyPlane.index(enemy)])
                except:
                    pass
                enemyPlane.remove(enemy)
                continue
            enemy_rectL = enemy_data1["enemyL"]
            enemyrect = enemy_rectL["enemy{}".format(enemy[1])]
            enemyNow=enemy_model.subsurface(Rect(enemyrect))
            enemy[2][1]+=1
            screen.blit(enemyNow,enemy[2])
            continue

#爆炸动画
def blit_break(screen):
    for br in breakPos:
        if br[0]==1:
            rect = break_1["{}".format(br[1])]
            img = break_model.subsurface(rect)
            rect = img.get_rect()
            rect.center = br[2]
            screen.blit(img,rect)
            br[3]-=1
            if br[3]==0:
                br[3]=2
                br[1]+=1
            if br[1]==10:
                breakPos.remove(br)
        if br[0]==2:
            rect = break_2["{}".format(br[1])]
            img = break_model.subsurface(rect)
            rect = img.get_rect()
            rect.center = br[2]
            screen.blit(img, rect)
            br[3] -= 1
            if br[3] == 0:
                br[3] = 5
                br[1] += 1
            if br[1] == 7:
                breakPos.remove(br)

#检查子弹碰撞
def checkTouch(bulletHeart):
    global bulletsize
    for bullet in bulletPos:
        if bullet == None:
            return
        for check in collisionBox:
            if check == None:
                return
            if bullet[0]+bulletsize//2<check[0][2][0] or bullet[0]-bulletsize//2>check[0][2][0]+check[1]:
                continue
            if bullet[1]>check[0][2][1]+check[2] or bullet[1]<check[0][2][1]:
                continue
            bulletPos.remove(bullet)
            br=[1,1,bullet,2]
            breakPos.append(br)
            check[3]-=bulletHeart
            if check[3]<=0 :
                enemyPlane.remove(enemyPlane[collisionBox.index(check)])
                collisionBox.remove(check)
                br = [2, 1, [check[0][2][0]+check[1]//2,check[0][2][1]+check[2]//2], 5]
                breakPos.append(br)
                global score,exp_value
                if check[0][0]==1:
                    score+=1*exp_value
                elif check[0][0]==2:
                    score+=5*exp_value
                elif check[0][0]==3:
                    score+=20*exp_value
            if check[0][2][1]>600:
                collisionBox.remove(check)
            break

#飞机碰撞
def cratchDetect(nowsPos):
    global protect_value
    for check in collisionBox:
        if nowsPos[0]<check[0][2][0] or nowsPos[0]>check[0][2][0]+check[1]:
            continue
        if nowsPos[1]<check[0][2][1]+20 or nowsPos[1]>check[0][2][1]+check[2]:
            continue
        enemyPlane.remove(enemyPlane[collisionBox.index(check)])
        collisionBox.remove(check)
        if protect_value ==0:
            sys.exit()
        else:
            protect_value =0
    for box in goodluckBox:
        rect=[]
        if box[0]==1:
            rect = luckbox_data1["speed"]
        elif box[0]==2:
            rect = luckbox_data1["three"]
        elif box[0]==3:
            rect = luckbox_data1["exp"]
        elif box[0]==4:
            rect = luckbox_data1["blue1"]
        elif box[0]==5:
            rect = luckbox_data1["blue2"]
        elif box[0]==6:
            rect = luckbox_data1["protect"]
        if nowsPos[0]<box[1][0] or nowsPos[0]>box[1][0]+rect[2]:
            continue
        if nowsPos[1]<box[1][1] or nowsPos[1]>box[1][1]+rect[3]:
            continue
        if box[0]==1:
            global speedState,levelState
            speedState=900
            if levelState[0]<4:
                levelState[0]+=1
                levelState[1]=1
        if box[0]==2:
            global threeState,three_value
            threeState=400
            three_value=1
        if box[0]==3:
            global expState,exp_value
            expState=400
            exp_value=2
        if box[0]==4:
            global blue1State,blue1_value
            blue1State=150
            blue1_value[0] = 1
            blue1_value[1] = 1
        if box[0]==5:
            global blue2State,blue2_value
            blue2State=150
            blue2_value[0] = 1
            blue2_value[1] = 1
        if box[0]==6:
            protect_value=1
        goodluckBox.remove(box)

#增加幸运箱
def add_luckbox():
    ran = random.random()
    if ran<0.003:
        nowX = random.randint(0,434)
        ranX = random.randint(1,4)
        ranY = random.randint(-3,3)
        g1=[1,[nowX,-49],ranX,ranY]
        goodluckBox.append(g1)
    elif ran<0.004:
        nowX = random.randint(0, 434)
        ranX = random.randint(1, 4)
        ranY = random.randint(-3, 3)
        g2 = [2, [nowX, -49], ranX,ranY]
        goodluckBox.append(g2)
    elif ran < 0.005:
        nowX = random.randint(0, 434)
        ranX = random.randint(1, 4)
        ranY = random.randint(-3, 3)
        g3 = [3, [nowX, -49], ranX,ranY]
        goodluckBox.append(g3)
    elif ran < 0.006:
        nowX = random.randint(0, 444)
        ranX = random.randint(1, 4)
        ranY = random.randint(-3, 3)
        g4 = [4, [nowX, -76], ranX,ranY]
        goodluckBox.append(g4)
    elif ran < 0.007:
        nowX = random.randint(0, 390)
        ranX = random.randint(1, 4)
        ranY = random.randint(-3, 3)
        g5 = [5, [nowX, -97], ranX,ranY]
        goodluckBox.append(g5)
    elif ran < 0.008:
        nowX = random.randint(0, 434)
        ranX = random.randint(1, 4)
        ranY = random.randint(-3, 3)
        g6 = [6, [nowX, -78], ranX,ranY]
        goodluckBox.append(g6)

#绘制幸运箱
def blit_luckbox(screen):
    for box in goodluckBox:
        if box[0]==1:
            boxmodel=luckbox_model.subsurface(luckbox_data1["speed"])
            screen.blit(boxmodel,box[1])
            box[1][0]+=box[2]
            box[1][1]+=box[3]
            if box[1][0]<0 or box[1][0]>434:
                box[2]=-box[2]
            if box[1][1]<-49 or box[1][1]>551:
                box[3]=-box[3]
        elif box[0]==2:
            boxmodel=luckbox_model.subsurface(luckbox_data1["three"])
            screen.blit(boxmodel,box[1])
            box[1][0]+=box[2]
            box[1][1]+=box[3]
            if box[1][0]<0 or box[1][0]>434:
                box[2]=-box[2]
            if box[1][1]<-49 or box[1][1]>551:
                box[3]=-box[3]
        elif box[0]==3:
            boxmodel=luckbox_model.subsurface(luckbox_data1["exp"])
            screen.blit(boxmodel,box[1])
            box[1][0]+=box[2]
            box[1][1]+=box[3]
            if box[1][0]<0 or box[1][0]>434:
                box[2]=-box[2]
            if box[1][1]<-49 or box[1][1]>551:
                box[3]=-box[3]
        elif box[0]==4:
            boxmodel=luckbox_model.subsurface(luckbox_data1["blue1"])
            screen.blit(boxmodel,box[1])
            box[1][0]+=box[2]
            box[1][1]+=box[3]
            if box[1][0]<0 or box[1][0]>444:
                box[2]=-box[2]
            if box[1][1]<-76 or box[1][1]>524:
                box[3]=-box[3]
        elif box[0]==5:
            boxmodel=luckbox_model.subsurface(luckbox_data1["blue2"])
            screen.blit(boxmodel,box[1])
            box[1][0]+=box[2]
            box[1][1]+=box[3]
            if box[1][0]<0 or box[1][0]>390:
                box[2]=-box[2]
            if box[1][1]<-97 or box[1][1]>503:
                box[3]=-box[3]
        elif box[0]==6:
            boxmodel=luckbox_model.subsurface(luckbox_data1["protect"])
            screen.blit(boxmodel,box[1])
            box[1][0]+=box[2]
            box[1][1]+=box[3]
            if box[1][0]<0 or box[1][0]>434:
                box[2]=-box[2]
            if box[1][1]<-78 or box[1][1]>552:
                box[3]=-box[3]

#幸运箱效果
def box_effect():
    global speedState,threeState,expState,blue1State,blue2State,protectState,levelState,blue1_value,blue2_value
    global plane1,bullet1,bullet_speed,open_fire_speed,bullet_heart,bulletsize
    if speedState>0:
        speedState-=1
    elif speedState==0 and levelState[0]>1:
        levelState[0] -= 1
        levelState[1] = 1
        speedState =900
    if threeState>0:
        threeState-=1
    elif threeState==0:
        global three_value
        three_value = 0
        threeState=-1
    if expState>0:
        expState-=1
    elif expState==0:
        global exp_value
        exp_value=1
        expState=-1
    if blue1State>0:
        blue1State-=1
    elif blue1State==0:
        blue1_value[0]=0
        blue1_value[1]=1
        blue1State=-1
    if blue2State>0:
        blue2State-=1
    elif blue2State == 0:
        blue2_value[0]=0
        blue2_value[1]=1
        blue2State=-1
    if levelState[1]==1:
        plane1 = plane_model.subsurface(plane["level{}".format(levelState[0])])
        if blue1_value[0]==0 and blue2_value[0]==0:
            bullet1 = bullet_model.subsurface(bullet_yellow["{}".format(levelState[0])])
            bullet_heart = 1 + 0.3 * (levelState[0] - 1)
        else:
            bullet_heart = 1.7 + 0.3 * (levelState[0] - 1)
        bullet_speed = 4 * levelState[0]
        open_fire_speed=50-10*levelState[0]
        levelState[1]=0
    if blue1_value[1]==1:
        if blue1_value[0]==1:
            bullet1 = bullet_model.subsurface(bullet_blue["1"])
            bullet_heart = 2 + 0.3 * (levelState[0] - 1)
            bulletsize = bullet_blue["1"][2]
            blue1_value[1]=0
        else:
            bullet1 = bullet_model.subsurface(bullet_yellow["{}".format(levelState[0])])
            bullet_heart = 1 + 0.3 * (levelState[0] - 1)
            bulletsize = bullet_yellow["{}".format(levelState[0])][2]
            blue1_value[1] = 0
    if blue2_value[1]==1:
        if blue2_value[0] == 1:
            bullet1 = bullet_model.subsurface(bullet_blue["2"])
            bullet_heart = 2 + 0.3 * (levelState[0] - 1)
            bulletsize = bullet_blue["2"][2]
            blue2_value[1] = 0
        else:
            bullet1 = bullet_model.subsurface(bullet_yellow["{}".format(levelState[0])])
            bullet_heart = 1 + 0.3 * (levelState[0] - 1)
            bulletsize = bullet_yellow["{}".format(levelState[0])][2]
            blue2_value[1] = 0

#主背景加载
size = width,height = 512,600
backLuck = random.randint(1,4)
background = pygame.image.load("data/background{}.jpg".format(backLuck))
screen = pygame.display.set_mode(size)
pygame.display.set_caption("努力施工dog")
clock = pygame.time.Clock()

#参数初始化
bulletPos=[]
enemyPlane=[]
collisionBox=[]
breakPos=[]
goodluckBox=[]
bullet_speed=4
bullet_heart=1
open_fire=0
open_fire_speed=40
bgn=0
bgnn=0
Count_fire=open_fire_speed
Count_240=180
Count_boss=1200
bulletsize=0
score=0

#状态
levelState=[1,0]
threeState=0
three_value=0
expState=-1
exp_value=1
blue1State=-1
blue1_value=[0,0]
blue2State=-1
blue2_value=[0,0]
speedState=0
protect_value=0

#启动游戏
start = time.time()
while True:
    #game刷新率限制60hz
    clock.tick(60)
    # 遍历所有的事件
    for event in pygame.event.get():
        # 如果单击关闭窗口,则退出
        if event.type == pygame.QUIT:
            sys.exit()
        # 添加子弹
        if event.type == pygame.MOUSEBUTTONDOWN:
            open_fire = 1
        if event.type == pygame.MOUSEBUTTONUP:
            open_fire = 0
    #刷新敌机
    if Count_fire>0:
        Count_fire-=1
    if Count_240>0:
        Count_240-=1
    if Count_boss>0:
        Count_boss-=1
    if Count_240%120==0:
        plan_s()
    if Count_240==0:
        plan_m()
        Count_240=239
    if Count_boss==0:
        plan_l()
        Count_boss=1200

    if open_fire == 1 and Count_fire==0:
        if three_value==0:
            bulletPos.append(list(pygame.mouse.get_pos()))
            Count_fire=open_fire_speed
        else:
            three_pos=list(pygame.mouse.get_pos())
            bulletPos.append([three_pos[0],three_pos[1]-8])
            bulletPos.append([three_pos[0]-35,three_pos[1]])
            bulletPos.append([three_pos[0]+35,three_pos[1]])
            Count_fire=open_fire_speed

    add_luckbox()
    box_effect()
    # 背景循环移动效果
    if bgn !=168:
        backgroundNOW = background.subsurface(Rect((0, 168 - bgn), (512, 600)))
        screen.blit(backgroundNOW, (0, 0))
        bgn+=1
    else:
        backgroundOLD = background.subsurface(Rect((0,  0), (512, 600 - bgnn)))
        backgroundNEW = background.subsurface(Rect((0, 768-bgnn), (512,  bgnn)))
        screen.blit(backgroundOLD, (0, bgnn))
        screen.blit(backgroundNEW, (0,0))
        bgnn+=1
        if bgnn == 600:
            bgnn=0
            bgn=0

    checkTouch(bullet_heart)
    # 主机的子弹发射
    for bullet_one in bulletPos:
        if bullet_one == None:
            break
        bullet1R = bullet1.get_rect()
        bulletsize=bullet1R[2]
        if bullet_one[1] > -bullet1R[3]:
            bullet1R.center = bullet_one
            bullet_one[1] -=bullet_speed
            screen.blit(bullet1, bullet1R)
        else:
            bulletPos.remove(bullet_one)
    blict_enemy(screen)
    blit_luckbox(screen)
    # 主机追随鼠标移动
    mouse_pos = pygame.mouse.get_pos()
    cratchDetect(mouse_pos)
    mou_plane = plane1.get_rect()
    mou_plane.center = mouse_pos
    screen.blit(plane1, mou_plane)
    #爆炸动画
    blit_break(screen)
    # 更新界面
    digital_time(screen)
    digital_num(screen)
    pygame.display.flip()
相关标签: 实例