C語言之飛機大戰(zhàn)游戲
本文實例為大家分享了C語言之飛機大戰(zhàn)游戲的具體代碼,供大家參考,具體內(nèi)容如下
技術(shù)原型
1、void gotoxy(int x, int y) 函數(shù),該函數(shù)可以使光標去到(x,y)的位置進行打??;
2、鏈表,用于存儲狀態(tài);
3、windows.h中有非阻塞輸入,_kbhit();
4、隨機生成數(shù);
5、視覺暫留;
6、碰撞檢測;
7、清屏函數(shù);
8、設(shè)置邊界;
技術(shù)路線
1、設(shè)置一個邊界;
2、維護一個子彈的列表;
3、維護一個敵機的列表;
4、初始化飛機的位置;
5、每隔一秒鐘生成一架敵機,生成位置x坐標隨機,坐標為0;
6、設(shè)置點擊空格生成子彈;
7、設(shè)置while(1)循環(huán),在其中每次進行清屏和更新;
8、每次更新遍歷子彈鏈表,使所有子彈的位置向上移動1;
9、每次更新遍歷敵機鏈表,使所有敵機的位置向下移動1;
10、碰撞檢測,遍歷子彈和敵機列表,發(fā)現(xiàn)碰撞則從各自的鏈表中移除碰撞的節(jié)點;
11、當(dāng)有敵機碰撞到本機游戲結(jié)束;
12、當(dāng)子彈或者敵機碰撞到邊界,則從鏈表中移除;
13、每次檢測到碰撞加一分。
實現(xiàn)效果

花費時間
約6小時30分鐘
代碼
#include <stdio.h>
#include <stdlib.h>
#include <conio.h>
#include <time.h>
#include <windows.h>
#include <math.h>
struct node {
int x;
int y;
struct node* next;
};
typedef struct node node_t;
typedef struct node* nodeptr_t;
void gotoxy(int x, int y); //光標定位函數(shù)
void print_plane(int x, int y); //打印飛機
nodeptr_t generate_bullet(nodeptr_t listnode, int x, int y); //生成子彈
void print_bullet(nodeptr_t listnode); //打印子彈
nodeptr_t update_bullet(nodeptr_t listnode); //更新子彈位置
nodeptr_t generate_target(nodeptr_t listnode, int x); //生成敵機
void print_target(nodeptr_t listnode); //打印敵機
nodeptr_t update_target(nodeptr_t listnode); //更新敵機位置
int collision_detection(nodeptr_t bulletlist, nodeptr_t targetlist); //碰撞檢測
bool is_gameover(int x,int y, nodeptr_t targetlist); // 游戲結(jié)束
void clear(nodeptr_t bulletlist, nodeptr_t targetlist);
int main() {
int plane_x = 0, plane_y = 19; //飛機位置
char control; //輸入
bool isfire = 0; //是否開火
nodeptr_t target = nullptr; //敵機鏈表
target = (nodeptr_t)malloc(sizeof(node_t));
target->next = nullptr;
target->x = 0;
target->y = 0;
nodeptr_t bullet = nullptr; //子彈鏈表
bullet = (nodeptr_t)malloc(sizeof(node_t));
bullet->next = nullptr;
bullet->x = 0;
bullet->y = 0;
int subtime = 0;
time_t starttime;
starttime = time(NULL);
int grade = 0; //分數(shù)
int targetspeed = 0;
int bulletspeed = 0;
while(1)
{
system("cls");
time_t currenttime;
currenttime = time(NULL);
//每隔一秒生成一架敵機
if (currenttime - starttime - subtime > 0)
{
srand((unsigned)time(NULL));
unsigned int target_y = rand() % 14 + 3;
target = generate_target(target, target_y);
}
subtime = currenttime - starttime;
//開火則生成子彈
if (isfire)
{
bullet = generate_bullet(bullet, plane_x, plane_y - 1);
isfire = 0;
}
//打印敵機
print_target(target);
targetspeed++;
if(targetspeed % 2 == 0)
target = update_target(target);
//打印子彈
print_bullet(bullet);
bulletspeed++;
if (bulletspeed % 2 == 0)
bullet = update_bullet(bullet);
//碰撞檢測
grade = grade + collision_detection(bullet, target);
gotoxy(0, 25);
printf("SCORE: %d", grade);
//打印飛機
print_plane(plane_x, plane_y);
//敵機本機是否相撞
bool isgameover = is_gameover(plane_x, plane_y, target);
//Sleep(100);
//非阻塞鍵盤輸入
if (isgameover)
{
clear(target, bullet);
plane_x = 0;
plane_y = 19;
isfire = 0;
system("cls");
gotoxy(8, 8);
printf("SCORE: %d", grade);
gotoxy(8, 9);
printf("GAME OVER");
grade = 0;
break;
}
if (_kbhit())
{
control = _getch();
if (control == ' ')
isfire = 1;
else
isfire = 0;
if (control == 'w' && plane_y > 0)
plane_y--;
if (control == 's' && plane_y < 20)
plane_y++;
if (control == 'a' && plane_x > 0)
plane_x--;
if (control == 'd' && plane_x < 20)
plane_x++;
}
}
return 0;
}
void gotoxy(int x, int y)//光標定位函數(shù)
{
COORD p;//定義結(jié)構(gòu)體變量p
HANDLE handle = GetStdHandle(STD_OUTPUT_HANDLE);//獲取當(dāng)前函數(shù)句柄
p.X = x;
p.Y = y;//將光標的目標移動位置傳遞給結(jié)構(gòu)體
SetConsoleCursorPosition(handle, p);//移動光標
return;
}
void print_plane(int x, int y) //打印飛機
{
if (x == 0)
{
gotoxy(x, y);
printf("*");
gotoxy(x, y + 1);
printf("***");
gotoxy(x, y + 2);
printf(" *");
}
else if (x == 1)
{
gotoxy(x, y);
printf("*");
gotoxy(x-1, y + 1);
printf("****");
gotoxy(x-1, y + 2);
printf("* *");
}
else if (x == 20)
{
gotoxy(x, y);
printf("*");
gotoxy(x - 2, y + 1);
printf("***");
gotoxy(x - 1, y + 2);
printf("* ");
}
else if (x == 19)
{
gotoxy(x, y);
printf("*");
gotoxy(x - 2, y + 1);
printf("****");
gotoxy(x - 1, y + 2);
printf("* *");
}
else
{
gotoxy(x, y);
printf("*");
gotoxy(x - 2, y + 1);
printf("*****");
gotoxy(x - 1, y + 2);
printf("* *");
}
return;
}
nodeptr_t generate_bullet(nodeptr_t listnode, int x, int y)
{
nodeptr_t newbullet = nullptr; //子彈鏈表
newbullet = (nodeptr_t)malloc(sizeof(node_t));
newbullet->next = listnode->next;
newbullet->x = x;
newbullet->y = y;
listnode->next = newbullet;
return listnode;
}
void print_bullet(nodeptr_t listnode)
{
nodeptr_t templist = listnode;
while (templist->next != nullptr)
{
gotoxy((templist->next->x), templist->next->y);
printf("|");
templist = templist->next;
}
return;
}
nodeptr_t update_bullet(nodeptr_t listnode)
{
nodeptr_t templist = listnode;
while (templist->next != nullptr)
{
if (templist->next->y > 0)
(templist->next->y)--;
else
{
nodeptr_t tempnode = templist->next;
templist->next = tempnode->next;
tempnode->next = nullptr;
free(tempnode);
}
if (templist->next != nullptr)
templist = templist->next;
else
break;
}
return listnode;
}
nodeptr_t generate_target(nodeptr_t listnode, int x)
{
nodeptr_t newtarget = nullptr; //子彈鏈表
newtarget = (nodeptr_t)malloc(sizeof(node_t));
newtarget->next = listnode->next;
newtarget->x = x;
newtarget->y = 0;
listnode->next = newtarget;
return listnode;
}
void print_target(nodeptr_t listnode)
{
nodeptr_t templist = listnode;
while(templist->next != nullptr)
{
gotoxy(templist->next->x, templist->next->y);
printf("+");
templist = templist->next;
}
return;
}
nodeptr_t update_target(nodeptr_t listnode)
{
nodeptr_t templist = listnode;
while (templist->next != nullptr)
{
if (templist->next->y < 21)
(templist->next->y)++;
else
{
nodeptr_t tempnode = templist->next;
templist->next = tempnode->next;
tempnode->next = nullptr;
free(tempnode);
}
if (templist->next != nullptr)
templist = templist->next;
else
break;
}
return listnode;
}
int collision_detection(nodeptr_t bulletlist, nodeptr_t targetlist)
{
int grade = 0;
nodeptr_t tempbulletlist = bulletlist;
while(tempbulletlist->next != nullptr)
{
nodeptr_t temptargetlist = targetlist;
while(temptargetlist->next != nullptr)
{
if(temptargetlist->next->x == (tempbulletlist->next->x) && temptargetlist->next->y > tempbulletlist->next->y)
{
nodeptr_t tempnode = temptargetlist->next;
temptargetlist->next = tempnode->next;
tempnode->next = nullptr;
free(tempnode);
tempnode = tempbulletlist->next;
tempbulletlist->next = tempnode->next;
tempnode->next = nullptr;
free(tempnode);
grade++;
break;
}
if (temptargetlist->next != nullptr)
temptargetlist = temptargetlist->next;
else
break;
}
if (tempbulletlist->next != nullptr)
tempbulletlist = tempbulletlist->next;
else
break;
}
return grade;
}
bool is_gameover(int x, int y, nodeptr_t targetlist)
{
nodeptr_t temptargetlist = targetlist;
while (temptargetlist->next != nullptr)
{
int tempsub = abs((temptargetlist->next->x) - x);
if (tempsub == 0 && temptargetlist->next->y > y)
{
return 1;
}
else if(tempsub == 1 && temptargetlist->next->y > y + 1)
{
return 1;
}
else if (tempsub == 2 && temptargetlist->next->y > y + 1)
{
return 1;
}
temptargetlist = temptargetlist->next;
}
return 0;
}
void clear(nodeptr_t bulletlist, nodeptr_t targetlist)
{
while (bulletlist->next != nullptr)
{
nodeptr_t temp = bulletlist->next;
bulletlist->next = temp->next;
//temp->next = nullptr;
free(temp);
}
while (targetlist->next != nullptr)
{
nodeptr_t temp = targetlist->next;
targetlist->next = temp->next;
//temp->next = nullptr;
free(temp);
}
return;
}
以上就是本文的全部內(nèi)容,希望對大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。
相關(guān)文章
cin.get()和cin.getline()之間的區(qū)別
以下是對cin.get()和cin.getline()的區(qū)別進行了詳細的分析介紹,需要的朋友可以過來參考下,希望對大家有所幫助2013-09-09
OpenCV4.1.0+VisualStudio2019開發(fā)環(huán)境搭建(超級簡單)
這篇文章主要介紹了OpenCV4.1.0+VisualStudio2019開發(fā)環(huán)境搭建(超級簡單),文中通過示例代碼介紹的非常詳細,對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧2021-03-03
C語言實現(xiàn)時區(qū)轉(zhuǎn)換函數(shù)的實例
這篇文章主要介紹了C語言實現(xiàn)時區(qū)轉(zhuǎn)換函數(shù)的實例的相關(guān)資料,這里分析需求并提供實現(xiàn)代碼,需要的朋友可以參考下2017-08-08
Visual?C++?6.0添加一個對話框的實現(xiàn)步驟
VC6.0是微軟公司推出的一款集成開發(fā)環(huán)境,本文主要介紹了Visual?C++?6.0添加一個對話框的實現(xiàn)步驟,具有一定的參考價值,感興趣的可以了解一下2024-06-06
從匯編看c++中函數(shù)里面的static關(guān)鍵字的使用說明
c++中的static關(guān)鍵字使得函數(shù)里面的局部變量的存活期不在局限于函數(shù)里面,而是變?yōu)樵谡麄€程序生命期里面都有效2013-05-05

