C语言Window控制台实现弹弹方块(单个方块,多个方块)
扫描二维码
随时随地手机看文章
前面,我们用C语言实现了列表时的学生信息管理系统,那么,window控制台还能做什么好玩的东西呢?
http://blog.csdn.NET/morixinguan/article/details/77511003
这节我们来实现一下Window下的弹弹方块。
设计这个小游戏要考虑的问题
(1)方块:方块的大小,方块的颜色,方块在Window控制终端的起始位置(x,y的坐标),方块移动的速度,移动的方向。
(2)边框:弹弹方块需要在一定的空间内弹,而不能超出这个空间,那么这时需要设计一个边框,需要考虑边框的大小。
(3)方块和边框之间的关系:方块不能超出边框之外,也就是要判断一个方块以及方框的临界条件。
方块用" * " 组成的图形来代替,边框长用" - ",宽用方向 " | "代替。
现在可以来实现这个小游戏:
我们需要有以下的接口:
//窗口初始化
void HANDLE_init(HANDLE hOut);
//显示边框的函数
void show_map(HANDLE hOut);
//显示方块
void show_block(HANDLE hOut,struct block_t *array , int size);
//清除方块
void clear_block(HANDLE hOut,struct block_t *array , int size);
//移动方块
void move_block(struct block_t *array , int size);
//检测方块是否在边框内
int check_block(struct block_t *array , int size);
下面开始写代码:
#include <stdio.h>
#include <stdlib.h>
#include <Windows.h>
#include <conio.h>
#include <tchar.h>
#define msleep(x) (usleep(1000*x))
#define ROW 18
#define COL 60
#define TITLE "弹弹方块游戏 设计者:杨源鑫 日期:2017年8月24日 版本:1.0"
//在终端上打印信息
#define Print_Info_To_console(str,hOut,pos,x,y,color_type) \
SetConsoleTextAttribute(hOut, color_type); \
pos.X = x; \
pos.Y = y ; \
SetConsoleCursorPosition(hOut,pos); \
printf("%s",str);
//窗口初始化
void HANDLE_init(HANDLE hOut);
void show_map(HANDLE hOut);
void show_block(HANDLE hOut,int row , int col , int w , int h);
void clear_block(HANDLE hOut,int row , int col , int w , int h);
void move_block(int *row , int *col , int *drow , int *dcol , int h , int w);
//定义设置光标结构体变量
CONSOLE_CURSOR_INFO cci;
//定义默认的坐标位置
COORD pos = {0,0};
int main(int argc , char **argv)
{
int row = 5 ;
int col = 5 ;
int w = 4 ;
int h = 2 ;
int drow = 1 ;
int dcol = 1 ;
HANDLE hOut;
hOut = GetStdHandle(STD_OUTPUT_HANDLE);
HANDLE_init(hOut);
//刷方框
show_map(hOut);
while(1)
{
show_block(hOut, row , col , w , h);
//sleep(1);
Sleep(100);
clear_block(hOut,row , col , w , h);
move_block(&row , &col , &drow , &dcol , h , w);
}
return 0 ;
}
//窗口初始化
void HANDLE_init(HANDLE hOut)
{
SetConsoleTitleA(TITLE);
//获取当前的句柄---设置为标准输出句柄
//获取光标信息
GetConsoleCursorInfo(hOut, &cci);
//设置光标大小
cci.dwSize = 1;
//设置光标不可见 FALSE
cci.bVisible = 0;
//设置(应用)光标信息
SetConsoleCursorInfo(hOut, &cci);
}
//画边框
void show_map(HANDLE hOut)
{
int i ;
system("cls"); //全局刷
Print_Info_To_console(TITLE,hOut,pos,2,0,FOREGROUND_GREEN | 0x8);
//Print_Info_To_console(str,hOut,pos,x,y,color_type)
for(i = 1 ; i <= COL ; i++)
{
Print_Info_To_console("-",hOut,pos,i,1,FOREGROUND_GREEN | 0x8);
Print_Info_To_console("-",hOut,pos,i,ROW,FOREGROUND_GREEN | 0x8);
}
for(i = 1 ; i <= ROW ; i++ )
{
Print_Info_To_console("|",hOut,pos,1,i,FOREGROUND_GREEN | 0x8);
Print_Info_To_console("|",hOut,pos,COL,i,FOREGROUND_GREEN | 0x8);
}
fflush(stdout);
}
//画方块
void show_block(HANDLE hOut,int row , int col , int w , int h)
{
int i , j ;
for(i = 0 ; i < h ; i++)
{
for(j = 0 ; j < w ; j++)
{
Print_Info_To_console("*",hOut,pos,col+j,row+i,FOREGROUND_RED | FOREGROUND_GREEN | 0x8);
}
}
fflush(stdout);
}
void move_block(int *row , int *col , int *drow , int *dcol , int h , int w)
{
if((*row == ROW-h) || (*row == 2) )
*drow = -*drow ;
if((*col == COL-w) || (*col == 2))
*dcol = -*dcol;
*row += *drow ;
*col += *dcol ;
}
void clear_block(HANDLE hOut,int row , int col , int w , int h)
{
int i , j ;
for(i = 0 ; i < h ; i++)
{
for(j = 0 ; j < w ; j++)
{
Print_Info_To_console("*",hOut,pos,col+j,row+i,0);
}
}
fflush(stdout);
}
运行结果演示:
那么既然可以实现一个,可以实现多个方块同时运行吗?当然是可以的!
多个方块,这时候要考虑什么问题?
前面我们知道,关于方块我们设计的时候需要考虑的问题:方块的起始位置,方块的大小,方块的移动方向,方块的颜色。现在我们要实现多个方块,那么就需要设计一个结构体,然后定义一个结构体数组来存储这些方块。
我们设计的结构体如下:
struct block_t
{
//方块的起始位置
int row;
int col;
//方块的大小
int w;
int h;
//方块的移动方向
int drow ;
int dcol ;
//方块着色
int color ;
};
当然,上面的接口内存需要改动一下,参数传参改为结构体数组的形式即可,这样就方便很多了。
接口修改如下:
//窗口初始化
void HANDLE_init(HANDLE hOut);
//显示边框的函数
void show_map(HANDLE hOut);
//显示方块
void show_block(HANDLE hOut,struct block_t *array , int size);
//清除方块
void clear_block(HANDLE hOut,struct block_t *array , int size);
//移动方块
void move_block(struct block_t *array , int size);
//检测方块是否在边框内
int check_block(struct block_t *array , int size);
下面开始修改代码:
#include <stdio.h>
#include <stdlib.h>
#include <Windows.h>
#include <conio.h>
#include <tchar.h>
#define msleep(x) (usleep(1000*x))
#define NR(x) (sizeof(x)/sizeof(x[0]))
//定义边框的行为18,列为60
#define ROW 18
#define COL 60
#define TITLE "弹弹方块游戏 设计者:杨源鑫 日期:2017年8月24日 版本:2.0"
//在终端上打印信息
#define Print_Info_To_console(str,hOut,pos,x,y,color_type) \
SetConsoleTextAttribute(hOut, color_type); \
pos.X = x; \
pos.Y = y ; \
SetConsoleCursorPosition(hOut,pos); \
printf("%s",str);
struct block_t
{
//方块的起始位置
int row;
int col;
//方块的大小
int w;
int h;
//方块的移动方向
int drow ;
int dcol ;
//方块着色
int color ;
};
//窗口初始化
void HANDLE_init(HANDLE hOut);
//显示边框的函数
void show_map(HANDLE hOut);
//显示方块
void show_block(HANDLE hOut,struct block_t *array , int size);
//清除方块
void clear_block(HANDLE hOut,struct block_t *array , int size);
//移动方块
void move_block(struct block_t *array , int size);
//检测方块是否在边框内
int check_block(struct block_t *array , int size);
//定义设置光标结构体变量
CONSOLE_CURSOR_INFO cci;
//定义默认的坐标位置
COORD pos = {0,0};
int main(void)
{
//定义方块结构体数组
struct block_t array[] = {
{3,4,3,2,1,1,FOREGROUND_RED | FOREGROUND_GREEN | 0x8},
{6,7,3,2,1,1,FOREGROUND_RED | 0x8},
{8,9,3,2,1,1,FOREGROUND_GREEN | FOREGROUND_BLUE | 0x8},
};
//刷方框
if(check_block(array , NR(array)))
{
printf("方块定义不在界线内\n");
return -1 ;
}
HANDLE hOut;
hOut = GetStdHandle(STD_OUTPUT_HANDLE);
HANDLE_init(hOut);
fflush(stdout);
//显示边框
show_map(hOut);
while(1)
{
//显示方块
show_block(hOut ,array , NR(array));
//延时
msleep(100);
//清除方块
clear_block(hOut ,array , NR(array));
//移动方块
move_block(array , NR(array));
}
return 0 ;
}
//窗口初始化
void HANDLE_init(HANDLE hOut)
{
SetConsoleTitleA(TITLE);
//获取当前的句柄---设置为标准输出句柄
//获取光标信息
GetConsoleCursorInfo(hOut, &cci);
//设置光标大小
cci.dwSize = 1;
//设置光标不可见 FALSE
cci.bVisible = 0;
//设置(应用)光标信息
SetConsoleCursorInfo(hOut, &cci);
}
//画边框
void show_map(HANDLE hOut)
{
int i ;
system("cls"); //全局刷
Print_Info_To_console(TITLE,hOut,pos,2,0,FOREGROUND_GREEN | 0x8);
for(i = 1 ; i <= COL ; i++)
{
Print_Info_To_console("-",hOut,pos,i,1,FOREGROUND_GREEN | 0x8);
Print_Info_To_console("-",hOut,pos,i,ROW,FOREGROUND_GREEN | 0x8);
}
for(i = 1 ; i <= ROW ; i++ )
{
Print_Info_To_console("|",hOut,pos,1,i,FOREGROUND_GREEN | 0x8);
Print_Info_To_console("|",hOut,pos,COL,i,FOREGROUND_GREEN | 0x8);
}
fflush(stdout);
}
//显示方块子函数
static void _show_block(HANDLE hOut,struct block_t block)
{
int i , j ;
for(i = 0 ; i < block.h ; i++)
{
for(j = 0 ; j < block.w ; j++)
{
Print_Info_To_console("*",hOut,pos,block.col+j,block.row+i,block.color);
//Print_Info_To_console("*",hOut,pos,block.col+j,block.row+i,FOREGROUND_RED | FOREGROUND_GREEN | 0x8);
//printf("\033[%d;%dH\033[%dm \033[0m" , block.row+i , block.col+j , block.color);
}
}
fflush(stdout);
}
void show_block(HANDLE hOut ,struct block_t *array , int size)
{
int i ;
for(i = 0 ; i < size ; i++)
{
_show_block(hOut,array[i]);
}
}
//移动方块子函数
static void _move_block(struct block_t *block)
{
if((block->row >= ROW-block->h) || (block->row <= 2) )
block->drow = -block->drow ;
if((block->col >= COL-block->w) || (block->col <= 2))
block->dcol = -block->dcol;
block->row += block->drow ;
block->col += block->dcol ;
}
void move_block(struct block_t *array , int size)
{
int i ;
for(i = 0 ; i < size ; i++)
{
_move_block(&(array[i]));
}
}
//清除方块子函数
static void _clear_block(HANDLE hOut,struct block_t block)
{
int i , j ;
for(i = 0 ; i < block.h ; i++)
{
for(j = 0 ; j < block.w ; j++)
{
Print_Info_To_console("*",hOut,pos,(block.col)+j,(block.row)+i,0);
//printf("\033[%d;%dH " , (block.row)+i , (block.col)+j);
}
}
fflush(stdout);
}
void clear_block(HANDLE hOut,struct block_t *array , int size)
{
int i ;
for(i = 0 ; i < size ; i++)
{
_clear_block(hOut,array[i]);
}
}
//检测方块是否在允许的方块内
static int _check_block(struct block_t block)
{
if((block.row == 2) || (block.col == 2) ||
(block.row == ROW - block.h) || (block.col == COL-block.w))
{
return 1 ;
}
return 0 ;
}
int check_block(struct block_t *array , int size)
{
int i ;
for(i = 0 ; i < size ; i++)
{
if(_check_block(array[i]))
return 1 ;
}
return 0 ;
}
运行结果演示:
那么该游戏还能继续拓展,比如,方块的移动方式修改用手动用键盘的上下左右按键来进行控制,还有,方块如果碰撞到了,会弹开一段距离。甚至,我们还可以借助这个,设计一个控制台版本的坦克大战。
更多脑洞,需要你仔细的斟酌与思考,一个游戏不是轻轻松松就做出来的。发挥你的脑洞,想你所想,编你所编!!
原文链接:http://blog.csdn.net/morixinguan/article/details/77541343
免责声明:本文内容由21ic获得授权后发布,版权归原作者所有,本平台仅提供信息存储服务。文章仅代表作者个人观点,不代表本平台立场,如有问题,请联系我们,谢谢!