C语言实现的Tank游戏

文章来源于网络,如有侵权请联系删除,谢谢!  可供大家了解GDI显示图片功能。 

// tank.cpp : Defines the entry point for the application.
//

#include "stdafx.h"
#include "resource.h"
#include <stdio.h>
#include <stdlib.h>
#include <queue>
#include <TIME.H>
#include <mmsystem.h> //导入声音头文件库   
#pragma comment(lib,"winmm.lib")//导入声音的链接库 

#define MAX_LOADSTRING 100

// Global Variables:


HINSTANCE hInst;								// current instance
TCHAR szWindowClass[MAX_LOADSTRING];								// The title bar text

HDC hdc, mhdc, mmhdc;        //贴图
int pre_Time, now_Time;      //消息循环
int blood[10]={1,1,1,2,2,2,3,3,4,4};    //随机从中得到敌人的血并出现敌人
HBITMAP myTank_bmp[2][4][2]; //我的坦克图
HBITMAP enemy_bmp[4][4][2];  //敌人坦克图
HBITMAP background[2];       //背景图
HBITMAP bullet_bmp[2];       //子弹图
HBITMAP wall_bmp[11];		 //墙图

HBITMAP gameover_bmp[2];     //gameover图
HBITMAP win_bmp[2];          //win图
HBITMAP number_bmp[10];      //number图
HBITMAP light_bmp[4];        //复活的时候的星光
HBITMAP no_hurt_bmp[2][2];   //无敌状态图
HBITMAP level_bmp[4];        //关卡图
int key_pre_time[2], key_now_time[2];  //按键时间
int start;                   //页面id
HBITMAP page[10];            //页面图
HBITMAP T[2];                //页面坦克指针图
HBITMAP fire[3][2];			 //坦克爆炸,子弹打墙的火焰
HBITMAP prop_bmp[7];		 //道具图
int timing;					 //获得时间静止后敌人停止的时间
int wall_time;				 //获得铁围墙后铁围墙的时间
int start_time;				 //进入游戏后一段时间不能活动
int end_time;				 //当通过这一关后一段时间后才进入下一关
bool lv_up[2];				 //是否升级,若升级为true,否则为false
bool win;					 //是否通关,true为通关,false为没有
bool gameover;				 //是否输掉,true为输,false为没有输

	//0:普通;  1:穿甲;  2:加强子弹; 3:爆炸弹; 
//4,铁墙  5:血瓶 6:定时
struct Tank{
	int x, y, d;                   //坦克坐标和方向
	int pre_time, now_time;
	int tkind;                     //坦克种类
	int bkind;				       //bkind 子弹种类
	int bullet_pre_time, bullet_now_time;//连续发生子弹的时间间隔
	int no_hurt_time, no_hurt_num; //无敌时间间隔
	int prop_time;			       //道具持续时间
	int light_num, num;            //无敌状态
	int blood;					   //血
	Tank(){
		no_hurt_num=no_hurt_time=light_num=prop_time=0;num=1;
	}
}myTank[2], enemy[5];

int life_num[2];				   //坦克的命
int lv_num[2];					   //等级
int fight_num[2];				   //杀敌数
int enemy_num[12];				   //剩余敌人数

struct bullet{
	int x, y, d;				   //子弹坐标和方向
	int f;						   //是否存在,1存在,0不存在
	int belong;					   //子弹属于坦克,<=1属于我方坦克,>1为敌人坦克
	int kind;					   //子弹种类
	int fire_num;				   //当撞墙后或者打到坦克时火焰持续时间
	bullet(){
		f=0;fire_num=0;
	}
}bullet[500];

struct Prop{
	int show_time;				   //道具显示持续的时间
	int pre_time, now_time;		   //道具出现时间间隔
	int kind;					   //道具的种类
	int x, y;					   //道具出现的坐标
}prop;

int map[31][50];				   //地图,0:空地;1、2:土墙;3:铁墙;4:草地;5:河

// Foward declarations of functions included in this code module:
ATOM				MyRegisterClass(HINSTANCE hInstance);
BOOL				InitInstance(HINSTANCE, int);
LRESULT CALLBACK	WndProc(HWND, UINT, WPARAM, LPARAM);
LRESULT CALLBACK	About(HWND, UINT, WPARAM, LPARAM);

void draw_myTank();						  //画我的坦克
void draw_enemy();						  //画敌人
void draw_light();						  //画坦克出现时的星光
void draw_no_hurt(int x,int y,int id);    //画无敌状态,在(x,y)出现标号为id的坦克
void draw_bullet();						  //画子弹
void draw_fire(int x,int y,int kind);     //画火焰,x、y为火焰坐标,kind为火焰种类
void draw_prop();						  //画道具
void draw_wall();						  //画墙
void draw_num();						  //画背景右边数字信息

void create_bullet(int d,int id,int kind);//发射炮弹,d为发射炮弹的方向,id为发射炮弹的坦克,kind为发射炮弹的种类
void move_myTank(int d,int id);		      //移动我的坦克,d为移动的方向,id为移动坦克的标号
void move_enemy();						  //敌人移动
BOOL meet(int x,int y,int d,int id);	  //判断碰撞,x、y为坐标,d为方向,id为坦克标号
void bullet_hit();						  //子弹打到物体
void remove_wall(int x,int y);			  //当子弹为爆炸弹时把x,y坐标附近的墙破坏掉
void key_down(int id);		              //模拟按键操作,id为我的坦克标号
void get_prop(int id,int x,int y);		  //获得道具,id为获得道具坦克的标号,在(x,y)处获得
void init();							  //每关初始化
void open_map(int id);					  //加载地图,id为关卡标号
void myPaint();							  //把贴图函数放在此函数中


int APIENTRY WinMain(HINSTANCE hInstance,
                     HINSTANCE hPrevInstance,
                     LPSTR     lpCmdLine,
                     int       nCmdShow)
{
 	// TODO: Place code here.
	MSG msg;
	HACCEL hAccelTable;

	// Initialize global strings
	LoadString(hInstance, IDC_TANK, szWindowClass, MAX_LOADSTRING);
	MyRegisterClass(hInstance);

	// Perform application initialization:
	if (!InitInstance (hInstance, nCmdShow)) 
	{
		return FALSE;
	}

	hAccelTable = LoadAccelerators(hInstance, (LPCTSTR)IDC_TANK);

	// Main message loop:
	while (msg.message!=WM_QUIT) 
	{
		if (PeekMessage(&msg,NULL,0,0,PM_REMOVE)) 
		{
			TranslateMessage(&msg);
			DispatchMessage(&msg);
		}
		else{
			if(start>5&&start_time<0){							//判断是否进入游戏页面和静止时间是否结束
				key_now_time[0]=key_now_time[1]=GetTickCount();
				if(key_now_time[0]-key_pre_time[0]>=30&&myTank[0].blood&&life_num[0]>0){//坦克1的按键
					key_down(0);
				}
				if(start>=9&&key_now_time[1]-key_pre_time[1]>=30&&myTank[1].blood&&life_num[1]>0){//坦克2的按键
					key_down(1);
				}
				if(life_num[0]<=0&&life_num[1]<=0) gameover=true;//若两个坦克的血都小于等于0则gameover
			}
			now_Time=GetTickCount();
			if(now_Time-pre_Time>=30){
				myPaint();										 //贴图
			}
		}
	}
	
	return msg.wParam;
}



//
//  FUNCTION: MyRegisterClass()
//
//  PURPOSE: Registers the window class.
//
//  COMMENTS:
//
//    This function and its usage is only necessary if you want this code
//    to be compatible with Win32 systems prior to the 'RegisterClassEx'
//    function that was added to Windows 95. It is important to call this function
//    so that the application will get 'well formed' small icons associated
//    with it.
//
ATOM MyRegisterClass(HINSTANCE hInstance)
{
	WNDCLASSEX wcex;

	wcex.cbSize = sizeof(WNDCLASSEX); 

	wcex.style			= CS_HREDRAW | CS_VREDRAW;
	wcex.lpfnWndProc	= (WNDPROC)WndProc;
	wcex.cbClsExtra		= 0;
	wcex.cbWndExtra		= 0;
	wcex.hInstance		= hInstance;
	wcex.hIcon			= LoadIcon(hInstance, (LPCTSTR)IDI_TANK);
	wcex.hCursor		= LoadCursor(NULL, IDC_ARROW);
	wcex.hbrBackground	= (HBRUSH)(COLOR_WINDOW+1);
	wcex.lpszMenuName	= (LPCSTR)IDC_TANK;
	wcex.lpszClassName	= szWindowClass;
	wcex.hIconSm		= LoadIcon(wcex.hInstance, (LPCTSTR)IDI_SMALL);

	return RegisterClassEx(&wcex);
}

//
//   FUNCTION: InitInstance(HANDLE, int)
//
//   PURPOSE: Saves instance handle and creates main window
//
//   COMMENTS:
//
//        In this function, we save the instance handle in a global variable and
//        create and display the main program window.
//

BOOL InitInstance(HINSTANCE hInstance, int nCmdShow)
{
   HWND hWnd;

   hInst = hInstance; // Store instance handle in our global variable

   hWnd = CreateWindow(szWindowClass, "坦克大战", WS_OVERLAPPEDWINDOW,
      100, 40, 1150, 680, NULL, NULL, hInstance, NULL);

   if (!hWnd)
   {
      return FALSE;
   }

   ShowWindow(hWnd, nCmdShow);
   UpdateWindow(hWnd);
   
   hdc=GetDC(hWnd);
   mhdc=CreateCompatibleDC(hdc);
   mmhdc=CreateCompatibleDC(hdc);
   HBITMAP bmp=CreateCompatibleBitmap(hdc,1300,680);//1015 680
   SelectObject(mhdc,bmp);
/**********************************************************************************************/
/***********************************以下为加载位图*********************************************/
/**********************************************************************************************/
   char str[100];                               
   int i, j, k;
   for(i=0;i<2;i++){								//加载我的坦克位图
	   for(j=0;j<4;j++){
		   for(k=0;k<2;k++){
				sprintf(str,"Image\\MyTank\\myTank%d%d%d.bmp",i,j,k);
				myTank_bmp[i][j][k]=(HBITMAP)LoadImage(NULL,str,IMAGE_BITMAP,40,40,LR_LOADFROMFILE);
		   }
		  
		   
	   }
   }
   for(i=0;i<4;i++){							     //加载敌人位图
	   for(j=0;j<4;j++){
		   for(k=0;k<2;k++){
			   sprintf(str,"Image\\Enemy\\enemy%d%d%d.bmp",i,j,k);
			   enemy_bmp[i][j][k]=(HBITMAP)LoadImage(NULL,str,IMAGE_BITMAP,40,40,LR_LOADFROMFILE);
		   }
	   }
   }

   for(i=0;i<2;i++){                                 //加载子弹位图
		sprintf(str,"Image\\Bullet\\bullet%d.bmp",i);
		bullet_bmp[i]=(HBITMAP)LoadImage(NULL,str,IMAGE_BITMAP,10,10,LR_LOADFROMFILE);
   }
		
   for(i=1;i<=10;i++){
		sprintf(str,"Image\\Wall\\wall%d.bmp",i);
		wall_bmp[i]=(HBITMAP)LoadImage(NULL,str,IMAGE_BITMAP,20,20,LR_LOADFROMFILE);//加载墙的位图
   }
   for(i=0;i<=5;i++){
	   if(i<=3)
		sprintf(str,"Image\\page%d.bmp",0);
	   else sprintf(str,"Image\\page%d.bmp",i);
		page[i]=(HBITMAP)LoadImage(NULL,str,IMAGE_BITMAP,1150,680,LR_LOADFROMFILE);//加载页面
   }
   int x, y;
   for(i=0;i<3;i++){							
	   for(j=0;j<2;j++){
		sprintf(str,"Image\\Fire\\fire%d%d.bmp
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值