[C/C++/初学者]飞机大战 原神版
前言:
本人现在是一名软件专业的大一学生,
此程序为本校的校内技能大赛-程序设计大赛-专科组参赛作品。而设计它的初衷也不是为了拿奖,(小声:毕竟我这种简易版飞机大战几乎没什么深度。)
而是为了加深自己对C语言和C++的理解,也是为了进一步提高自己的编程技术,因为前段时间也是刚刚才完成学生成绩管理系统。
受到时间与技术的双重限制,故只有实现了基本功能,
以下是程序鉴赏环节。
鉴赏:
一、封面
二、菜单界面
三、游戏规则
四、游戏主体
素材:
head.h(头文件):
#include<stdio.h>
#include<time.h>
#include<stdlib.h>//包含清屏指令
#include<graphics.h>//图形库头文件
#include<conio.h> //使用getch(),以获取键盘消息
#include<mmsystem.h>//包含多媒体设备接口的头文件
#pragma comment(lib,"winmm.lib")
#pragma warning (disable :4996)#define SIZE 650 //背景大小
#define PSIZE 80 //飞机大小
#define MAX 100//子弹数目
#define FMAX 10//敌机数目/*使用布尔类型中的true和false来代表阿影和史莱姆的存活*/
typedef struct Member
{double x;double y;bool life;
}mem;void welcome1();
void gamemenu();
void welcome();
void explation();//游戏规则void Game(); //游戏进程
void Load();//图片加载
void DataInit();//数据初始化
void PlaneCtr();//通过输入上下左右来改变飞机的坐标
void Show();//画面呈现
void BullterCre();//按了空格,调用函数,创建子弹
void BullterMove();//子弹移动
void FplaneCre();//敌机创建
void FplaneMove();//敌机移动
void Hit();//消灭敌机void FdieRetain();//击中后效果保留一段时间
void PDie();//被敌机击中
void Score();//分数显示
void BGM();//背景音乐
BGM.cpp(音频函数):
#include<stdio.h>
#include"head.h"//播放舰桥音乐
void BGM()
{//打开音乐mciSendString(TEXT("open denglu.mp3"),0,0,0);//播放音乐mciSendString(TEXT("play denglu.mp3 repeat"),0,0,0); //repeat控制音频的循环播放
}
Menu.cpp(菜单函数):
#include<stdio.h>
#include"head.h"int color(int c)
{SetConsoleTextAttribute(GetStdHandle(STD_OUTPUT_HANDLE), c); //更改文字颜色return 0;
}//光标移动
void gotoxy(int x, int y)
{HANDLE handle = GetStdHandle(STD_OUTPUT_HANDLE);COORD pos;pos.X = x;pos.Y = y;SetConsoleCursorPosition(handle, pos);
}void welcome1()
{printf("■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■\n");printf("■ ■\n");printf("■ ■ ■ ■ ■\n");printf("■ ■ ■ ■ ■ ■ ■ ■\n");printf("■ ■■■■■ ■ ■ ■ ■ ■\n");printf("■ ■ ■ ■ ■ ■■■ ■■■ ■ ■■■ ■\n");printf("■ ■ ■ ■ ■ ■ ■ ■ ■ ■ ■ ■ ■\n");printf("■ ■ ■ ■ ■ ■ ■ ■■■ ■ ■■■ ■\n");printf("■ ■\n");printf("■ TECH OTAKUS SAVE THE WORLD ■\n");printf("■ ■\n");printf("■ 技术宅拯救世界 ■\n");printf("■ 注:请按下任意键进入■\n");printf("■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■\n");system("pause");system("cls");
}void gamemenu()
{time_t TIME;struct tm *t;TIME=time(0);t=localtime(&TIME);//SND_FILENAME表示pszSound参数指定的是文件名(pszSound还可以指定资源、内存音乐、系统音乐等等);//SND_ASYNC:用异步方式播放声音,PlaySound函数在开始播放后立即返回;//SND_SYNC:同步播放声音,在播放完后PlaySound函数才返回;//SND_LOOP一遍遍的重复播放声音,必须与SND_ASYNC标志一块使用。printf("■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■\n");printf("■ ■\n");printf("■ ■\n");printf("■ ■\n");printf("■ 【欢迎回到提瓦特,旅行者】 ■\n");printf("■ ■\n");printf("■ ■\n");printf("■ ■\n");printf("■ 当前时间为:%s\n",asctime(t));printf("■ ■\n");printf("■ ■\n");printf("■ ■\n");printf("■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■\n");system("pause");system("cls");
}//主界面
void welcome()
{int n;printf("■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■\n");printf("■ 原神战机 Genshin War-Plane V5.9 ■\n");printf("■ ■\n");printf("■ ■\n");printf("■ 操作选择(Change) ■\n");printf("■ ■\n");printf("■ 1.开始游戏(Play Game) ■\n");printf("■ 2.游戏规则(Game Rule) ■\n");printf("■ 3.退出游戏(Exit Game) ■\n");printf("■ ■\n");printf("■ ■\n");printf("■ ■\n");printf("■制作人: 学号: 联系方式:■\n");printf("■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■\n");color(15);gotoxy(20, 15);printf("请选择您的操作 1 2 3 4: ");scanf("%d", &n); // 输入选项switch (n){case 1:break;case 2:explation(); // 游戏规则break;case 3:exit(0); // 退出游戏break;default:color(8);gotoxy(33, 22);printf("请输入1-3之间的数");_getch(); // 输入任意键system("cls"); // 清屏welcome();}
}//游戏规则及相关信息
void explation()
{system("cls");printf("■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■\n");printf("■ 游戏规则 Rules of game ■\n");printf("■ ■\n");printf("■ ■\n");printf("■ ①击败史莱姆可获得1分 ■\n");printf("■ ②原作:原神——米哈游 ■\n");printf("■ ③游戏途中可按下Backspace键退出游戏 ■\n");printf("■ ④使用↑↓← → 键分别控制阿影的移动 ■\n");printf("■ ⑤按下空格键即为发射渔获,一发子弹即可消灭史莱姆 ■\n");printf("■ ⑥音乐:Genshin Impact Main Theme 原神——陈致逸/HOYO-MiX ■\n");printf("■ ■\n");printf("■ 按回车键返回主页面 ■\n");printf("■ ■\n");printf("■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■■\n");_getch(); system("cls");welcome();
}
body.cpp(主体函数):
/*若解压后发现IMAGE处出现错误,请前往https://easyx.cn/网址,下载easyx图形库
因无法直接使用透明背景图,故此处使用掩码操作实现了类似效果*/#include<stdio.h>
#include"head.h"//定义图片变量
IMAGE bk;//背景图
IMAGE plane_back;//阿影背景图
IMAGE plane_mask;//阿影掩码图
IMAGE fplane_back;//史莱姆背景图
IMAGE fplane_mask;//史莱姆掩码图
IMAGE bullte_back;//子弹背景图
IMAGE bullte_mask;//子弹掩码图
IMAGE fdie_back;//击中史莱姆效果背景图
IMAGE fdie_mask;//击中史莱姆效果掩码图
IMAGE pdie_back;//被击中背景图
IMAGE pdie_mask;//被击中掩码图//定义全局变量
mem plane;//阿影结构体
mem bullte[MAX];//子弹结构体数组
mem fplane[FMAX];//史莱姆结构体
mem fdie[FMAX];//击中敌机/*GetTickCount是返回(retrieve)从操作系统启动所经过(elapsed)毫秒数的函数,
而DWORD则是这个函数的返回值。
此处因为考虑到游戏中常有的无敌时间机制,故查询并考虑了该函数*/DWORD b_time_start, b_time_last; //每次发射子弹时的时间间隔DWORD pf_time_start, pf_time_last; //每次产生史莱姆时的间隔DWORD p_time_start, p_time_last; //无敌时间int flag;//本机生命值
int count;//得分计数器
int boom;//爆炸标志/*
SIZE:
背景图:500*1000PSIZE:
阿影:100*152
阿影2:100*100
史莱姆:100*65
史莱姆原浆:100*65
渔获:50*200
*///图片加载
void Load()
{loadimage(&bk, "beijing.jpg");//加载阿影图片loadimage(&plane_back, "plane3.jpg"); //背景loadimage(&plane_mask, "plane4.jpg"); //掩码//加载史莱姆图片 loadimage(&fplane_back, "diren1.jpg");loadimage(&fplane_mask, "diren2.jpg");//记载渔获图片loadimage(&bullte_back, "zidan1.jpg");loadimage(&bullte_mask, "zidan2.jpg");//史莱姆凋落物loadimage(&fdie_back, "boom1.jpg");loadimage(&fdie_mask, "boom2.jpg");//记载阿影相撞loadimage(&pdie_back, "plane1.jpg");loadimage(&pdie_mask, "plane2.jpg");
}//数据初始化
void DataInit()
{//阿影的数据初始化plane.x=200; //阿影起始X位置在背景图的中心,背景的二分之一减去自身的一半plane.y=500; //阿影起始Y位置在背景图的中心偏上plane.life=true; //阿影出生是存活的//渔获初始化for (int i=0;i<MAX;i++){bullte[i].life = false;//渔获没按空格键前是不存在的}//时间变化初始化b_time_start = b_time_last = GetTickCount();//开机到现在的毫秒数pf_time_start = pf_time_last = GetTickCount();p_time_start = p_time_last = GetTickCount();//被击中无敌时间变化量//史莱姆初始化for (int i = 0; i<FMAX; i++){fplane[i].life = false;}//击中史莱姆效果初始化for (int i = 0; i < FMAX; i++){fdie[i].life = false;}//生命值初始化flag=3;//死亡爆炸效果控制boom=0;//得分计数器count=0;}//通过键盘改变阿影的坐标
void PlaneCtr()
{if (GetAsyncKeyState(VK_UP))//向上移动{if (plane.y>0)//不能越界plane.y-=1;}if (GetAsyncKeyState(VK_DOWN))//向下移动{if (plane.y<700)//y最大值600,飞机图片大小为80plane.y+=1;}if (GetAsyncKeyState(VK_LEFT))//向左移动{if (plane.x>0)//可以缩入墙壁一半机体plane.x-=1;}if (GetAsyncKeyState(VK_RIGHT))//向右移动{if (plane.x<450)plane.x+=1;}if (GetAsyncKeyState(VK_SPACE) && b_time_last - b_time_start>80)//发射子弹,每颗子弹间接为80毫秒{BullterCre();//空格发射子弹b_time_start = b_time_last;}b_time_last = GetTickCount();
}//画面呈现
void Show()
{ BeginBatchDraw();//双缓冲绘图,防闪烁putimage(0, 0, &bk);Score();//分数和生命值显示if (plane.life)//飞机存活就打印飞机{putimage((int)plane.x, (int)plane.y, &plane_mask,NOTSRCERASE);putimage((int)plane.x, (int)plane.y, &plane_back,SRCINVERT);}if (boom){putimage((int)plane.x,(int)plane.y, &pdie_mask,NOTSRCERASE);putimage((int)plane.x,(int)plane.y, &pdie_back,SRCINVERT);if (rand()%80 ==2){boom=0;//飞机复活plane.x=200; //飞机起始位置在背景图的中央plane.y=500;}}if (plane.life==false&&boom==0&&flag!=0){if (p_time_last-p_time_start>=4000)//无敌时间3秒{plane.life=true;p_time_start=p_time_last;}p_time_last=GetTickCount();putimage((int)plane.x,(int)plane.y, &plane_mask,NOTSRCERASE);}for (int i=0;i<MAX;i++)//循环判断子弹{if (bullte[i].life)//子弹存在就打印子弹{putimage((int)bullte[i].x,(int)bullte[i].y, &bullte_mask,NOTSRCERASE);putimage((int)bullte[i].x,(int)bullte[i].y, &bullte_back,SRCINVERT);}}for (int i=0;i<FMAX; i++){if (fdie[i].life)//打印击中效果{putimage((int)fdie[i].x,(int)fdie[i].y, &fdie_mask,NOTSRCERASE);putimage((int)fdie[i].x,(int)fdie[i].y, &fdie_back,SRCINVERT);}if (fplane[i].life)//打印敌机{putimage((int)fplane[i].x,(int)fplane[i].y, &fplane_mask,NOTSRCERASE);putimage((int)fplane[i].x,(int)fplane[i].y, &fplane_back,SRCINVERT);}}EndBatchDraw();
}//创建渔获
void BullterCre()
{for (int i=0;i<MAX;i++){if (!bullte[i].life)//子弹不存在就创建子弹{//从飞机的正前方发出去bullte[i].x = plane.x+50; //宽度:50bullte[i].y = plane.y-200; //长度:200bullte[i].life = true;break;//一次空格产生一颗子弹}}
}//渔获移动
void BullterMove()
{for (int i=0;i<MAX;i++){if (bullte[i].life)//子弹存在,它的y坐标就减少{bullte[i].y--;//坐标减,产生移动if (bullte[i].y<0)//子弹回收,否则下次全是发射出去的子弹{bullte[i].life=false;}}}
}//史莱姆创建
void FplaneCre()
{for (int i=0;i<FMAX;i++){if (!fplane[i].life&&pf_time_last-pf_time_start>100)//没有敌机就进行构建,用时间函数控制产生速度{fplane[i].life=true;fplane[i].x=rand()%400;//不让敌出现在窗口外,背景的宽度减去飞机的宽度fplane[i].y=0;pf_time_start=pf_time_last;break;//每次一个}pf_time_last=GetTickCount();//获取新的时间}
}//史莱姆移动
void FplaneMove()
{for (int i=0; i<FMAX;i++){if (fplane[i].life){fplane[i].y+=0.3;//敌机往下走if (fplane[i].y>1000)//敌机回收fplane[i].life = false;}}
}//消灭史莱姆
void Hit()
{for (int i=0;i<FMAX;i++){if (!fplane[i].life)//不存在则换下一个判断continue;for (int j=0;j<MAX;j++){if (!bullte[j].life)continue;//子弹不存在也换下一个判断if (bullte[j].x>fplane[i].x//子弹和敌机有交集则都消失&& bullte[j].x<fplane[i].x + PSIZE&&bullte[j].y>fplane[i].y&&bullte[j].y<fplane[i].y + PSIZE) {fdie[i].life=true;//击中效果fdie[i].x=fplane[i].x;fdie[i].y=fplane[i].y;bullte[j].life=false;fplane[i].life=false;count++;}}}
}//史莱姆原浆效果 保留一段时间
void FdieRetain()
{for (int i=0;i<FMAX;i++){if (rand()%40==2){fdie[i].life=false;}}}//与史莱姆相撞
void PDie()
{for (int i = 0; i < FMAX; i++){if (!fplane[i].life)continue;if (plane.x>fplane[i].x&&plane.x<fplane[i].x + PSIZE&&plane.y>fplane[i].y&&plane.y < fplane[i].y + PSIZE&&plane.life){plane.life=false;flag-=1;//生命值-1boom=1;//输出爆炸图片break;}}
}//分数显示
void Score()
{char myscore[MAX] = "当前得分为:";char num[20];sprintf(num, "%d", count);settextcolor(WHITE);outtextxy(0, 0, myscore);//输出分数outtextxy(80, 0, num);char _myscore[MAX] = "当前生命值:";char _num[20];sprintf(_num, "%d", flag);settextcolor(WHITE);outtextxy(0, 50, _myscore);outtextxy(90, 50, _num);//输出剩余生命值}//游戏进程
void Game()
{//加载图片数和初始化数据Load();DataInit();while (1){Show();//图像显示if(flag==0)break;if(GetAsyncKeyState(VK_BACK)){exit(0);}PlaneCtr();//操控BullterMove();//子弹移动FplaneCre();//敌机创建 Hit();//判断是否打中敌机FplaneMove();//敌机往下走FdieRetain();//击中敌机后效果保留一段时间PDie();//被敌机击中}
}int main()
{BGM();welcome1();gamemenu();welcome();initgraph(500, 1000);Game();getchar();return 0;
}
[C/C++/初学者]飞机大战 原神版相关推荐
- C++的学习心得和知识总结(十六)|基于EasyX实现小甲鱼Python飞机大战项目(C++版)
目录结构 注:提前言明 本文借鉴了以下博主.书籍或网站的内容,其列表如下: 1.小甲鱼Python项目 – 飞机大战 2.本文使用的掩码图生成工具 自动生成遮罩图的程序,点击前往 3.EasyX官方链 ...
- python飞机大战源代码-python版飞机大战代码分享
利用pygame实现了简易版飞机大战.源代码如下: # -*- coding:utf-8 -*- import pygame import sys from pygame.locals import ...
- python飞机大战类_Python版飞机大战
前面学了java用java写了飞机大战这次学完python基础后写了个python版的飞机大战,有兴趣的可以看下. 父类是飞行物类是所有对象的父类,setting里面是需要加载的图片,你可以换称自己的 ...
- C语言程序飞机大战,C语言版飞机大战游戏
C语言版飞机大战,供大家参考,具体内容如下 不多说直接上代码 #include #include #include #include #include using namespace std; /*= ...
- 飞机大战(C语言版)
大一下要交课程设计,于是就用C语言写了一个飞机大战小游戏 ,没有用到第三方库,飞机和子弹的移动使用的光标移动函数,所以没有卡顿 其中w s a d分别表示上下左右(包括大写),空格发射子弹,游戏结束后 ...
- 飞机大战(easyx版)
#include<graphics.h> #include<conio.h> #include<stdio.h>//引用Windows Multimedia API ...
- java做飞机大战_Java+swing版飞机大战
Java小游戏实训--飞机大战 一.实验目的 使用Java+swing实现飞机大战小游戏 二.实验要求 1.掌握Java的基本语法. 2.掌握面向对象的编程思想. 3.掌握利用swing布局游戏界面的 ...
- 飞机大战(Python版)
文章目录 项目目录 最终效果 完整代码 项目目录 mian.py:实现游戏的主窗口以及游戏的主要逻辑 bullet.py:实现子弹类 enemy.py:实现敌方飞机类 myplane.py:实现我方飞 ...
- 简易版的飞机大战(C语言)
一.只会发射激光,画质不清晰的飞机大战 游戏的总体结构根据C语言的循环制作的 本来还想说点什么但是注释里面都有 代码: #include <stdio.h> #include <s ...
最新文章
- Hadoop文件系统元数据fsimage和编辑日志edits
- video/audio在ios/android上播放兼容
- vector 源码及使用
- 如何修改Win7开机登陆界面背景图片
- 业务的可变性和不可变性分析_不可变性真的意味着线程安全吗?
- 作者:郭琨(1985-),女,博士,中国科学院虚拟经济与数据科学研究中心助理研究员...
- 网络编程(一)基础知识
- java学习-BeanUtils给对象的属性赋值
- keep dark about sth
- linux创建进程 api,.net Core 3.0 WebApi 创建Linux守护进程的方法
- 怎么在mac上更改移动硬盘的权限
- eds能谱图分析实例_SPC控制图公式_均值极差SPC控制图公式应用实例分析
- 转录组+云平台助力HIF-1α促进冠状病毒感染的分子机制研究
- HTML 入门基础教程
- 【合天网安】CONN.ASP暴库漏洞实验
- java B2B2C源码电子商务平台 ---搭建Eureka注册中心
- CoreOS Fest 系列之第一篇:容器江湖
- 今日睡眠质量记录74分
- #Linux的边边角角# 之 EPERM错误和setuid魔法
- python日期加减一年_Python日期的加减等操作