俄罗斯方块小游戏
#include "stdio.h"
#include "string.h"
#include "stdlib.h"
#include "time.h"
#include "conio.h"
#include "windows.h"
// =============================================================================
typedef struct yonghu //储存用户
{
char Name[20];//用户名
unsigned short Score;//总成绩
struct yonghu *next;
}yonghu;
// =============================================================================
// 7种方块的4旋转状态(4位为一行)
static unsigned short youxifangkuai[7][4] =
{
{ 0x00F0U, 0x2222U, 0x00F0U, 0x2222U }, // I型
{ 0x0072U, 0x0262U, 0x0270U, 0x0232U }, // T型
{ 0x0223U, 0x0074U, 0x0622U, 0x0170U }, // L型
{ 0x0226U, 0x0470U, 0x0322U, 0x0071U }, // J型
{ 0x0063U, 0x0264U, 0x0063U, 0x0264U }, // Z型
{ 0x006CU, 0x0462U, 0x006CU, 0x0462U }, // S型
{ 0x0660U, 0x0660U, 0x0660U, 0x0660U } // O型
};
// =============================================================================
// 初始状态的游戏池
static unsigned short chushizhuangtai[28] =
{
0xC003U, 0xC003U, 0xC003U, 0xC003U, 0xC003U, 0xC003U, 0xC003U,
0xC003U, 0xC003U, 0xC003U, 0xC003U, 0xC003U, 0xC003U, 0xC003U,
0xC003U, 0xC003U, 0xC003U, 0xC003U, 0xC003U, 0xC003U, 0xC003U,
0xC003U, 0xC003U, 0xC003U, 0xC003U, 0xC003U, 0xFFFFU, 0xFFFFU
};
#define true 1
#define false 0
#define COL_BEGIN 2
#define COL_END 14
#define ROW_BEGIN 4
#define ROW_END 26
#define M 20
char password[M]="1234";
char password1[M]="tourist";
// =============================================================================
typedef struct youxishuju // 这个结构体存储游戏相关数据
{
unsigned short pool[28]; // 游戏池
signed char x; // 当前方块x坐标,此处坐标为方块左上角坐标
signed char y; // 当前方块y坐标
signed char type[3]; // 当前、下一个和下下一个方块类型
signed char orientation[3]; // 当前、下一个和下下一个方块旋转状态
} youxishuj;
// =============================================================================
typedef struct youxineirong // 这个结构体存储游戏内容
{
// 游戏池内每格的颜色
signed char color[28][16];
int dead; // 挂
int pause; // 暂停
int clockwise; // 旋转方向:顺时针为true
signed char direction; // 移动方向:0向左移动 1向右移动
int model; // 模式 游戏模式为false
unsigned score; // 得分
unsigned speed; //速度
unsigned erasedCount[4]; // 消行数
unsigned erasedTotal; // 消行总数
unsigned tetrisCount[7]; // 各方块数
unsigned tetrisTotal; // 方块总数
} youxineirong;
HANDLE g_hConsoleOutput; // 控制台输出句柄
// =============================================================================
// 函数声明
void initGame(youxishuj *, youxineirong *,yonghu*, int,int,yonghu *); // 初始化游戏
void giveTetris(youxishuj *, youxineirong *); // 给一个方块
int checkCollision(const youxishuj *); // 碰撞检测
void insertTetris(youxishuj *); // 插入方块
void removeTetris(youxishuj *); // 移除方块
void horzMoveTetris(youxishuj *, youxineirong *); // 水平移动方块
void moveDownTetris(youxishuj *, youxineirong *,yonghu *,int,yonghu *); // 向下移动方块
void rotateTetris(youxishuj *, youxineirong *); // 旋转方块
void dropDownTetris(youxishuj *, youxineirong *,yonghu *,int,yonghu *); // 方块直接落地
int checkErasing(youxishuj *, youxineirong *,yonghu *,int,yonghu *); // 消行检测
void keydownControl(youxishuj *, youxineirong *, yonghu *,int,int,yonghu *); // 键按下
void setPoolColor(const youxishuj *, youxineirong *); // 设置颜色
void gotoxyWithFullwidth(short x, short y); // 以全角定位到某点
void printPoolBorder(); // 显示游戏池边界
void printTetrisPool(const youxishuj *, const youxineirong *); // 显示游戏池
void printCurrentTetris(const youxishuj *, const youxineirong *); // 显示当前方块
void printNextTetris(const youxishuj *); // 显示下一个和下下一个方块
void printScore(const youxishuj *, const youxineirong *,const yonghu *,yonghu *); // 显示得分信息
void runGame(youxishuj *, youxineirong *,yonghu *,int,yonghu *); // 运行游戏
void printPrompting(); // 显示提示信息
int mainMenu(); // 主菜单
void autoRun(youxishuj *, youxineirong *); // 自动运行
yonghu *psctLoadLink(void); //该函数用于从文件读取历史最高分
void iSaveLink(yonghu *); //该函数用于存储每局游戏数据
int iPassLink(yonghu *); //此函数用于验证密码,密码支持(M-1)位的字符
void show(yonghu *); //展示排行榜前三名
int nanduxuanze(void);
// =============================================================================
// 主函数
void main()
{
int model,y=0,t=0,x=0;
yonghu *m=(yonghu *)malloc(sizeof(yonghu));
strcpy(m->Name,password1);
yonghu *temp,*p;
temp=psctLoadLink();
youxishuj tetrisManager;
youxineirong tetrisControl;
CONSOLE_CURSOR_INFO cursorInfo = { 1, FALSE }; // 光标信息
g_hConsoleOutput = GetStdHandle(STD_OUTPUT_HANDLE); // 获取控制台输出句柄
SetConsoleCursorInfo(g_hConsoleOutput, &cursorInfo); // 设置光标隐藏
SetConsoleTitleA("俄罗斯方块——By: Mr.Huang");
do
{
model = mainMenu();
switch (model)
{
case 0: case 1:
loop:SetConsoleTextAttribute(g_hConsoleOutput, 0x07);
system("cls");
initGame(&tetrisManager, &tetrisControl,temp, model==0,t,m); // 初始化游戏
printPrompting(); // 显示提示信息
printPoolBorder(); // 显示游戏池边界
switch (model)
{
case 0:
runGame(&tetrisManager, &tetrisControl,temp,t,m);
break;// 运行游戏
case 1:
runGame(&tetrisManager, &tetrisControl,temp,t,m);
break;//自动运行
}
system("cls");
SetConsoleTextAttribute(g_hConsoleOutput, 0x09);
gotoxyWithFullwidth(11, 10);
printf("游戏结束");
gotoxyWithFullwidth(11, 12);
printf("最终分数:%u",(tetrisControl.score));
p=temp;
while(y<3)
{
if((tetrisControl.score)>(p->Score))break;
p=p->next;
y++;
}
if(y==0)
{
p->next->next->Score=p->next->Score;
strcpy(p->next->next->Name,p->next->Name);
p->next->Score=p->Score;
strcpy(p->next->Name,p->Name);
x=1;
}
else if(y==1)
{
p->next->Score=p->Score;
strcpy(p->next->Name,p->Name);
x=1;
}
else if(y==2)x=1;
if(x){p->Score=tetrisControl.score,strcpy(p->Name,m->Name);}
iSaveLink(temp);
SetConsoleTextAttribute(g_hConsoleOutput, 0x07);
system("pause > nul");
system("cls");
break;
case 2://登录
SetConsoleTextAttribute(g_hConsoleOutput, 0x07);
system("cls");
if(iPassLink(m)==1)
{
model=1;
goto loop;
}
break;
case 3://排行榜展示
SetConsoleTextAttribute(g_hConsoleOutput, 0x07);
system("cls");
show(temp);
break;
case 4://难度选择
SetConsoleTextAttribute(g_hConsoleOutput, 0x07);
system("cls");
t=nanduxuanze();
model=0;
goto loop;
}
} while (1);
gotoxyWithFullwidth(0, 0);
CloseHandle(g_hConsoleOutput);
}
// =============================================================================
// 初始化游戏
void initGame(youxishuj *manager, youxineirong *control, yonghu *temp,int model,int t,yonghu *m)
{
memset(manager, 0, sizeof(youxishuj)); // 全部置0
// 初始化游戏池
memcpy(manager->pool, chushizhuangtai, sizeof(unsigned short [28]));
srand((unsigned)time(NULL)); // 设置随机种子
manager->type[1] = rand() % 7; // 下一个
manager->orientation[1] = rand() & 3;
manager->type[2] = rand() % 7; // 下下一个
manager->orientation[2] = rand() & 3;
memset(control, 0, sizeof(youxineirong)); // 全部置0
control->model = model;
if(t==0 || t==1)control->speed=1; //初始化速度
else if(t==2)control->speed=2;
else if(t==3)control->speed=3;
else if(t==4)control->speed=4;
giveTetris(manager, control); // 给下一个方块
setPoolColor(manager, control); // 设置颜色
printScore(manager, control,temp,m); // 显示得分信息
}
// =============================================================================
// 给一个方块
void giveTetris(youxishuj *manager, youxineirong *control)
{
unsigned short tetris;
manager->type[0] = manager->type[1]; // 下一个方块置为当前
manager->orientation[0] = manager->orientation[1];
manager->type[1] = manager->type[2];// 下下一个置方块为下一个
manager->orientation[1] = manager->orientation[2];
manager->type[2] = rand() % 7;// 随机生成下下一个方块
manager->orientation[2] = rand() & 3;
tetris = youxifangkuai[manager->type[0]][manager->orientation[0]]; // 当前方块
// 设置当前方块y坐标,保证刚给出时只显示方块最下面一行
// 这种实现使得玩家可以以很快的速度将方块落在不显示出来的顶部4行内
if (tetris & 0xF000)
{
manager->y = 0;
}
else
{
manager->y = (tetris & 0xFF00) ? 1 : 2;
}
manager->x = 6; // 设置当前方块x坐标
if (checkCollision(manager)) // 检测到碰撞
{
control->dead = true; // 标记游戏结束
}
else // 未检测到碰撞
{
insertTetris(manager); // 将当前方块加入游戏池
}
++control->tetrisTotal; // 方块总数
++control->tetrisCount[manager->type[0]]; // 相应方块数
printNextTetris(manager); // 显示下一个方块
}
// =============================================================================
// 碰撞检测
int checkCollision(const youxishuj *manager)
{
// 当前方块
unsigned short tetris = youxifangkuai[manager->type[0]][manager->orientation[0]];
unsigned short dest = 0U;
// 获取当前方块在游戏池中的区域:
// 游戏池坐标x y处小方格信息,按低到高存放在16位无符号数中
dest |= (((manager->pool[manager->y + 0] >> manager->x) << 0x0) & 0x000F);
dest |= (((manager->pool[manager->y + 1] >> manager->x) << 0x4) & 0x00F0);
dest |= (((manager->pool[manager->y + 2] >> manager->x) << 0x8) & 0x0F00);
dest |= (((manager->pool[manager->y + 3] >> manager->x) << 0xC) & 0xF000);
// 若当前方块与目标区域存在重叠(碰撞),则位与的结果不为0
return ((dest & tetris) != 0);
}
// =============================================================================
// 插入方块
void insertTetris(youxishuj *manager)
{
// 当前方块
unsigned short tetris = youxifangkuai[manager->type[0]][manager->orientation[0]];
// 当前方块每4位取出,位或到游戏池相应位置,即完成插入方块
manager->pool[manager->y + 0] |= (((tetris >> 0x0) & 0x000F) << manager->x);
manager->pool[manager->y + 1] |= (((tetris >> 0x4) & 0x000F) << manager->x);
manager->pool[manager->y + 2] |= (((tetris >> 0x8) & 0x000F) << manager->x);
manager->pool[manager->y + 3] |= (((tetris >> 0xC) & 0x000F) << manager->x);
}
// =============================================================================
// 移除方块
void removeTetris(youxishuj *manager)
{
// 当前方块
unsigned short tetris = youxifangkuai[manager->type[0]][manager->orientation[0]];
// 当前方块每4位取出,按位取反后位与到游戏池相应位置,即完成移除方块
manager->pool[manager->y + 0] &= ~(((tetris >> 0x0) & 0x000F) << manager->x);
manager->pool[manager->y + 1] &= ~(((tetris >> 0x4) & 0x000F) << manager->x);
manager->pool[manager->y + 2] &= ~(((tetris >> 0x8) & 0x000F) << manager->x);
manager->pool[manager->y + 3] &= ~(((tetris >> 0xC) & 0x000F) << manager->x);
}
// =============================================================================
// 设置颜色
void setPoolColor(const youxishuj *manager, youxineirong *control)
{
// 由于显示游戏池时,先要在游戏池里判断某一方格有方块才显示相应方格的颜色
// 这里只作设置即可,没必要清除
// 当移动方块或给一个方块时调用
signed char i, x, y;
// 当前方块
unsigned short tetris = youxifangkuai[manager->type[0]][manager->orientation[0]];
for (i = 0; i < 16; ++i)
{
y = (i >> 2) + manager->y; // 待设置的列
if (y > ROW_END) // 超过底部限制
{
break;
}
x = (i & 3) + manager->x; // 待设置的行
if ((tetris >> i) & 1) // 检测的到小方格属于当前方块区域
{
control->color[y][x] = (manager->type[0] | 8); // 设置颜色
}
}
}
// =============================================================================
// 旋转方块
void rotateTetris(youxishuj *manager, youxineirong *control)
{
signed char ori = manager->orientation[0]; // 记录原旋转状态
removeTetris(manager); // 移走当前方块
// 顺/逆时针旋转
manager->orientation[0] = (control->clockwise) ? ((ori + 1) & 3) : ((ori + 3) & 3);
if (checkCollision(manager)) // 检测到碰撞
{
manager->orientation[0] = ori; // 恢复为原旋转状态
insertTetris(manager); // 放入当前方块。由于状态没改变,不需要设置颜色
}
else
{
insertTetris(manager); // 放入当前方块
setPoolColor(manager, control); // 设置颜色
printCurrentTetris(manager, control); // 显示当前方块
}
}
// =============================================================================
// 水平移动方块
void horzMoveTetris(youxishuj *manager, youxineirong *control)
{
int x = manager->x; // 记录原列位置
removeTetris(manager); // 移走当前方块
control->direction == 0 ? (--manager->x) : (++manager->x); // 左/右移动
if (checkCollision(manager)) // 检测到碰撞
{
manager->x = x; // 恢复为原列位置
insertTetris(manager); // 放入当前方块。由于位置没改变,不需要设置颜色
}
else
{
insertTetris(manager); // 放入当前方块
setPoolColor(manager, control); // 设置颜色
printCurrentTetris(manager, control); // 显示当前方块
}
}
// =============================================================================
// 向下移动方块
void moveDownTetris(youxishuj *manager, youxineirong *control,yonghu *temp,int t,yonghu *m)
{
signed char y = manager->y; // 记录原行位置
removeTetris(manager); // 移走当前方块
++manager->y; // 向下移动
if (checkCollision(manager)) // 检测到碰撞
{
manager->y = y; // 恢复为原行位置
insertTetris(manager); // 放入当前方块。由于位置没改变,不需要设置颜色
if (checkErasing(manager, control,temp,t,m)) // 检测到消行
{
printTetrisPool(manager, control); // 显示游戏池
}
}
else
{
insertTetris(manager); // 放入当前方块
setPoolColor(manager, control); // 设置颜色
printCurrentTetris(manager, control); // 显示当前方块
}
}
// =============================================================================
// 方块直接落地
void dropDownTetris(youxishuj *manager, youxineirong *control,yonghu *temp,int t,yonghu *m)
{
removeTetris(manager); // 移走当前方块
// 从上往下检测
// 注意这里不能从下往上,否则会出现方块穿过盖埋入空洞的BUG
for (; manager->y < ROW_END; ++manager->y)
{
if (checkCollision(manager)) // 检测到碰撞
{
break;
}
}
--manager->y; // 上移一格当然没有碰撞
insertTetris(manager); // 放入当前方块
setPoolColor(manager, control); // 设置颜色
checkErasing(manager, control,temp,t,m); // 检测消行
printTetrisPool(manager, control); // 显示游戏池
}
// =============================================================================
// 消行检测
int checkErasing(youxishuj *manager, youxineirong *control,yonghu *temp,int t,yonghu *m)
{
static const unsigned scores[5] = { 0, 10, 30, 90, 150 }; // 消行得分
signed char count = 0;
signed char k = 0, y = manager->y + 3;
do // 从下往上检测
{
if (y < ROW_END && manager->pool[y] == 0xFFFFU) // 有效区域内且一行已填满
{
++count;
// 消除一行方块
memmove(manager->pool + 1, manager->pool, sizeof(unsigned short) * y);
// 颜色数组的元素随之移动
memmove(control->color[1], control->color[0], sizeof(signed char [16]) * y);
}
else
{
--y;
++k;
}
} while (y >= manager->y && k < 4);
control->erasedTotal += count; // 消行总数
control->score += scores[count] * control->speed; // 得分
if (count > 0)
{
++control->erasedCount[count - 1]; // 消行
}
if (control->score >=1000 && t==0)control->speed=4;
else if (control->score >=300 && t==0)control->speed=3;
else if (control->score >=100 && t==0)control->speed=2;
giveTetris(manager, control); // 给下一个方块
setPoolColor(manager, control); // 设置颜色
printScore(manager, control,temp,m); // 显示得分信息
return (count > 0);
}
// =============================================================================
// 键按下
void keydownControl(youxishuj *manager, youxineirong *control, yonghu *temp,int key,int t,yonghu *m)
{
if (key == 13) // 暂停/解除暂停
{
control->pause = !control->pause;
}
if (control->pause) // 暂停状态,不作处理
{
return;
}
switch (key)
{
case 'w': case 'W': case '8': case 72: // 上
control->clockwise = true; // 顺时针旋转
rotateTetris(manager, control); // 旋转方块
break;
case 'a': case 'A': case '4': case 75: // 左
control->direction = 0; // 向左移动
horzMoveTetris(manager, control); // 水平移动方块
break;
case 'd': case 'D': case '6': case 77: // 右
control->direction = 1; // 向右移动
horzMoveTetris(manager, control); // 水平移动方块
break;
case 's': case 'S': case '2': case 80: // 下
moveDownTetris(manager, control,temp,t,m); // 向下移动方块
break;
case ' ': // 直接落地
dropDownTetris(manager, control,temp,t,m);
break;
case '0': // 反转
control->clockwise = false; // 逆时针旋转
rotateTetris(manager, control); // 旋转方块
break;
default:
break;
}
}
// =============================================================================
// 以全角定位到某点
void gotoxyWithFullwidth(short x, short y)
{
static COORD cd;
cd.X = (short)(x << 1);
cd.Y = y;
SetConsoleCursorPosition(g_hConsoleOutput, cd);
}
// =============================================================================
// 主菜单
int mainMenu()
{
static const char *modelItem[] = { "1.基础游戏模式", "2.自动测试模式", "3.登录模式", "4.排行榜", "5.难度选择"};
int index = 0, ch;
SetConsoleTextAttribute(g_hConsoleOutput, FOREGROUND_GREEN | // 前景色_绿色
FOREGROUND_INTENSITY);
gotoxyWithFullwidth(15, 5);
printf("┏━━━━━━━┓");
gotoxyWithFullwidth(15, 6);
printf("┃%2s%s%2s┃", "", "俄罗斯方块", "");
gotoxyWithFullwidth(15, 7);
printf("┗━━━━━━━┛");
SetConsoleTextAttribute(g_hConsoleOutput, 0xF0);
gotoxyWithFullwidth(15, 14);
printf("%2s%s%2s", "", modelItem[0], "");
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY);
gotoxyWithFullwidth(15, 16);
printf("%2s%s%2s", "", modelItem[1], "");
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 18);
printf("%2s%s%2s", "", modelItem[2], "");
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 20);
printf("%2s%s%2s", "", modelItem[3], "");
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 22);
printf("%2s%s%2s", "", modelItem[4], "");
do
{
ch = _getch();
switch (ch)
{
case 'w':case 'W':case '8':case 72: // 上
case 'a':case 'A':case '4':case 75:
if (index > 0) index--;
else index=4;
if (index == 0)
{
SetConsoleTextAttribute(g_hConsoleOutput, 0xF0);
gotoxyWithFullwidth(15, 14);
printf("%2s%s%2s", "", modelItem[0], "");
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY);
gotoxyWithFullwidth(15, 16);
printf("%2s%s%2s", "", modelItem[1], "");
gotoxyWithFullwidth(15, 18);
printf("%2s%s%2s", "", modelItem[2], "");
gotoxyWithFullwidth(15, 20);
printf("%2s%s%2s", "", modelItem[3], "");
gotoxyWithFullwidth(15, 22);
printf("%2s%s%2s", "", modelItem[4], "");
}
else if (index == 1)
{
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 14);
printf("%2s%s%2s", "", modelItem[0], "");
SetConsoleTextAttribute(g_hConsoleOutput, 0xF0);
gotoxyWithFullwidth(15, 16);
printf("%2s%s%2s", "", modelItem[1], "");
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 18);
printf("%2s%s%2s", "", modelItem[2], "");
gotoxyWithFullwidth(15, 20);
printf("%2s%s%2s", "", modelItem[3], "");
gotoxyWithFullwidth(15, 22);
printf("%2s%s%2s", "", modelItem[4], "");
}
else if (index == 2)
{
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY);
gotoxyWithFullwidth(15, 14);
printf("%2s%s%2s", "", modelItem[0], "");
gotoxyWithFullwidth(15, 16);
printf("%2s%s%2s", "", modelItem[1], "");
SetConsoleTextAttribute(g_hConsoleOutput, 0xF0);
gotoxyWithFullwidth(15, 18);
printf("%2s%s%2s", "", modelItem[2], "");
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 20);
printf("%2s%s%2s", "", modelItem[3], "");
gotoxyWithFullwidth(15, 22);
printf("%2s%s%2s", "", modelItem[4], "");
}
else if (index == 3)
{
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 14);
printf("%2s%s%2s", "", modelItem[0], "");
gotoxyWithFullwidth(15, 16);
printf("%2s%s%2s", "", modelItem[1], "");
gotoxyWithFullwidth(15, 18);
printf("%2s%s%2s", "", modelItem[2], "");
SetConsoleTextAttribute(g_hConsoleOutput, 0xF0);
gotoxyWithFullwidth(15, 20);
printf("%2s%s%2s", "", modelItem[3], "");
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 22);
printf("%2s%s%2s", "", modelItem[4], "");
}
else if (index == 4)
{
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 14);
printf("%2s%s%2s", "", modelItem[0], "");
gotoxyWithFullwidth(15, 16);
printf("%2s%s%2s", "", modelItem[1], "");
gotoxyWithFullwidth(15, 18);
printf("%2s%s%2s", "", modelItem[2], "");
gotoxyWithFullwidth(15, 20);
printf("%2s%s%2s", "", modelItem[3], "");
SetConsoleTextAttribute(g_hConsoleOutput, 0xF0);
gotoxyWithFullwidth(15, 22);
printf("%2s%s%2s", "", modelItem[4], "");
}
break;
case 'd':case 'D':case '6':case 77:// 右
case 's':case 'S':case '2':case 80:
if (index <4) index++;
else index =0;
if (index == 0)
{
SetConsoleTextAttribute(g_hConsoleOutput, 0xF0);
gotoxyWithFullwidth(15, 14);
printf("%2s%s%2s", "", modelItem[0], "");
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 16);
printf("%2s%s%2s", "", modelItem[1], "");
gotoxyWithFullwidth(15, 18);
printf("%2s%s%2s", "", modelItem[2], "");
gotoxyWithFullwidth(15, 20);
printf("%2s%s%2s", "", modelItem[3], "");
gotoxyWithFullwidth(15, 22);
printf("%2s%s%2s", "", modelItem[4], "");
}
else if (index == 1)
{
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 14);
printf("%2s%s%2s", "", modelItem[0], "");
SetConsoleTextAttribute(g_hConsoleOutput, 0xF0);
gotoxyWithFullwidth(15, 16);
printf("%2s%s%2s", "", modelItem[1], "");
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 18);
printf("%2s%s%2s", "", modelItem[2], "");
gotoxyWithFullwidth(15, 20);
printf("%2s%s%2s", "", modelItem[3], "");
gotoxyWithFullwidth(15, 22);
printf("%2s%s%2s", "", modelItem[4], "");
}
else if (index == 2)
{
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 14);
printf("%2s%s%2s", "", modelItem[0], "");
gotoxyWithFullwidth(15, 16);
printf("%2s%s%2s", "", modelItem[1], "");
SetConsoleTextAttribute(g_hConsoleOutput, 0xF0);
gotoxyWithFullwidth(15, 18);
printf("%2s%s%2s", "", modelItem[2], "");
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 20);
printf("%2s%s%2s", "", modelItem[3], "");
gotoxyWithFullwidth(15, 22);
printf("%2s%s%2s", "", modelItem[4], "");
}
else if (index == 3)
{
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 14);
printf("%2s%s%2s", "", modelItem[0], "");
gotoxyWithFullwidth(15, 16);
printf("%2s%s%2s", "", modelItem[1], "");
gotoxyWithFullwidth(15, 18);
printf("%2s%s%2s", "", modelItem[2], "");
SetConsoleTextAttribute(g_hConsoleOutput, 0xF0);
gotoxyWithFullwidth(15, 20);
printf("%2s%s%2s", "", modelItem[3], "");
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 22);
printf("%2s%s%2s", "", modelItem[4], "");
}
else if (index == 4)
{
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 14);
printf("%2s%s%2s", "", modelItem[0], "");
gotoxyWithFullwidth(15, 16);
printf("%2s%s%2s", "", modelItem[1], "");
gotoxyWithFullwidth(15, 18);
printf("%2s%s%2s", "", modelItem[2], "");
gotoxyWithFullwidth(15, 20);
printf("%2s%s%2s", "", modelItem[3], "");
SetConsoleTextAttribute(g_hConsoleOutput, 0xF0);
gotoxyWithFullwidth(15, 22);
printf("%2s%s%2s", "", modelItem[4], "");
}
break;// 下
case ' ': case 13:
return index;
}
} while (1);
}
// =============================================================================
// 显示游戏池边界
void printPoolBorder()
{
signed char y;
SetConsoleTextAttribute(g_hConsoleOutput, 0xF0);
for (y = ROW_BEGIN; y < ROW_END; ++y) // 不显示顶部4行和底部2行
{
gotoxyWithFullwidth(10, y - 3);
printf("%2s", "");
gotoxyWithFullwidth(23, y - 3);
printf("%2s", "");
}
gotoxyWithFullwidth(10, y - 3); // 底部边界
printf("%28s", "");
}
// 定位到游戏池中的方格
#define gotoxyInPool(x, y) gotoxyWithFullwidth(x + 9, y - 3)
// =============================================================================
// 显示游戏池
void printTetrisPool(const youxishuj *manager, const youxineirong *control)
{
signed char x, y;
for (y = ROW_BEGIN; y < ROW_END; ++y) // 不显示顶部4行和底部2行
{
gotoxyInPool(2, y); // 定点到游戏池中的方格
for (x = COL_BEGIN; x < COL_END; ++x) // 不显示左右边界
{
if ((manager->pool[y] >> x) & 1) // 游戏池该方格有方块
{
// 用相应颜色,显示一个实心方块
SetConsoleTextAttribute(g_hConsoleOutput, control->color[y][x]);
printf("■");
}
else // 没有方块,显示空白
{
SetConsoleTextAttribute(g_hConsoleOutput, 0);
printf("%2s", "");
}
}
}
}
// =============================================================================
// 显示当前方块
void printCurrentTetris(const youxishuj *manager, const youxineirong *control)
{
signed char x, y;
// 显示当前方块是在移动后调用的,为擦去移动前的方块,需要扩展显示区域
// 由于不可能向上移动,故不需要向下扩展
y = (manager->y > ROW_BEGIN) ? (manager->y - 1) : ROW_BEGIN; // 向上扩展一格
for (; y < ROW_END && y < manager->y + 4; ++y)
{
x = (manager->x > COL_BEGIN) ? (manager->x - 1) : COL_BEGIN; // 向左扩展一格
for (; x < COL_END && x < manager->x + 5; ++x) // 向右扩展一格
{
gotoxyInPool(x, y); // 定点到游戏池中的方格
if ((manager->pool[y] >> x) & 1) // 游戏池该方格有方块
{
// 用相应颜色,显示一个实心方块
SetConsoleTextAttribute(g_hConsoleOutput, control->color[y][x]);
printf("■");
}
else // 没有方块,显示空白
{
SetConsoleTextAttribute(g_hConsoleOutput, 0);
printf("%2s", "");
}
}
}
}
// =============================================================================
// 显示下一个和下下一个方块
void printNextTetris(const youxishuj *manager)
{
signed char i;
unsigned short tetris;
// 边框
SetConsoleTextAttribute(g_hConsoleOutput, 0xF);
gotoxyWithFullwidth(26, 1);
printf("┏━━━━┳━━━━┓");
gotoxyWithFullwidth(26, 2);
printf("┃%8s┃%8s┃", "", "");
gotoxyWithFullwidth(26, 3);
printf("┃%8s┃%8s┃", "", "");
gotoxyWithFullwidth(26, 4);
printf("┃%8s┃%8s┃", "", "");
gotoxyWithFullwidth(26, 5);
printf("┃%8s┃%8s┃", "", "");
gotoxyWithFullwidth(26, 6);
printf("┗━━━━┻━━━━┛");
// 下一个,用相应颜色显示
tetris = youxifangkuai[manager->type[1]][manager->orientation[1]];
SetConsoleTextAttribute(g_hConsoleOutput, manager->type[1] | 8);
for (i = 0; i < 16; ++i)
{
gotoxyWithFullwidth((i & 3) + 27, (i >> 2) + 2);
((tetris >> i) & 1) ? printf("■") : printf("%2s", "");
}
// 下下一个,不显示彩色
tetris = youxifangkuai[manager->type[2]][manager->orientation[2]];
SetConsoleTextAttribute(g_hConsoleOutput, 8);
for (i = 0; i < 16; ++i)
{
gotoxyWithFullwidth((i & 3) + 32, (i >> 2) + 2);
((tetris >> i) & 1) ? printf("■") : printf("%2s", "");
}
}
// =============================================================================
// 显示得分信息
void printScore(const youxishuj *manager, const youxineirong *control,const yonghu *temp,yonghu *m)
{
static const char *modelName[] = { "游戏模式", "测试模式" };
static const char *tetrisName = "ITLJZSO";
signed char i;
SetConsoleTextAttribute(g_hConsoleOutput, FOREGROUND_GREEN | // 前景色_绿色
FOREGROUND_INTENSITY);
gotoxyWithFullwidth(1, 1);
printf("%s", control->model ? modelName[0] : modelName[1]);
gotoxyWithFullwidth(1, 2);
printf("历史最高分:%u", temp->Score);
gotoxyWithFullwidth(1, 3);
printf("按Esc回主菜单");
gotoxyWithFullwidth(1, 4);
printf("当前游戏人:");
gotoxyWithFullwidth(1, 5);
printf("%s", m->Name);
SetConsoleTextAttribute(g_hConsoleOutput, 0xE);
gotoxyWithFullwidth(1, 6);
printf("难度:%u", control->speed);
gotoxyWithFullwidth(1, 7);
printf("得分:%u", control->score);
gotoxyWithFullwidth(1, 8);
printf("消行总数:%u", control->erasedTotal);
for (i = 0; i < 4; ++i)
{
gotoxyWithFullwidth(1, 10 + i);
printf("同时消%d行次数:%u", i + 1, control->erasedCount[i]);
}
gotoxyWithFullwidth(1, 15);
printf("方块总数:%u", control->tetrisTotal);
for (i = 0; i < 7; ++i)
{
gotoxyWithFullwidth(1, 17 + i);
printf("%c形方块个数:%u", tetrisName[i], control->tetrisCount[i]);
}
}
// =============================================================================
// 显示提示信息
void printPrompting()
{
SetConsoleTextAttribute(g_hConsoleOutput, 0xB);
gotoxyWithFullwidth(26, 8);
printf("游戏模式:");
gotoxyWithFullwidth(27, 10);
printf("向左移动:← A 4");
gotoxyWithFullwidth(27, 11);
printf("向右移动:→ D 6");
gotoxyWithFullwidth(27, 12);
printf("向下移动:↓ S 2");
gotoxyWithFullwidth(27, 13);
printf("顺时针转:↑ W 8");
gotoxyWithFullwidth(27, 14);
printf("逆时针转:0");
gotoxyWithFullwidth(27, 15);
printf("直接落地:空格");
gotoxyWithFullwidth(27, 16);
printf("暂停游戏:回车");
gotoxyWithFullwidth(26, 18);
printf("测试模式:");
gotoxyWithFullwidth(27, 20);
printf("加速:↑ +");
gotoxyWithFullwidth(27, 21);
printf("减速:↓ -");
gotoxyWithFullwidth(25, 23);
printf("By: Mr.Huang");
}
// =============================================================================
// 运行游戏
void runGame(youxishuj *manager, youxineirong *control,yonghu *temp,int k,yonghu *m)
{
int ch;
clock_t clockLast, clockNow;
clockLast = clock(); // 计时
printTetrisPool(manager, control); // 显示游戏池
while (!control->dead) // 没挂
{
while (_kbhit()) // 有键按下
{
ch = _getch();
if (ch == 27) // Esc键
{
return;
}
keydownControl(manager, control,temp, ch,k,m); // 处理按键
}
if (!control->pause && control->speed==1) // 未暂停
{
clockNow = clock(); // 计时
// 两次记时的间隔超过0.45秒
if (clockNow - clockLast > 0.45F * CLOCKS_PER_SEC)
{
clockLast = clockNow;
keydownControl(manager, control,temp, 80,k,m); // 方块往下移
}
}
else if (!control->pause && control->speed==2) // 未暂停
{
clockNow = clock(); // 计时
// 两次记时的间隔超过0.3秒
if (clockNow - clockLast > 0.30F * CLOCKS_PER_SEC)
{
clockLast = clockNow;
keydownControl(manager, control, temp,80,k,m); // 方块往下移
}
}
else if (!control->pause && control->speed==3) // 未暂停
{
clockNow = clock(); // 计时
// 两次记时的间隔超过0.2秒
if (clockNow - clockLast > 0.20F * CLOCKS_PER_SEC)
{
clockLast = clockNow;
keydownControl(manager, control,temp, 80,k,m); // 方块往下移
}
}
else if (!control->pause && control->speed==4) // 未暂停
{
clockNow = clock(); // 计时
// 两次记时的间隔超过0.1秒
if (clockNow - clockLast > 0.1F * CLOCKS_PER_SEC)
{
clockLast = clockNow;
keydownControl(manager, control,temp, 80,k,m); // 方块往下移
}
}
}
}
// =============================================================================
//验证密码,密码支持(M-1)位的字符
int iPassLink(yonghu *m)
{
int x,n=1;
for(;;n++)
{
if(n<=3)
{
char ch,password0[M],ch1,password1[M];
int i=0;
SetConsoleTextAttribute(g_hConsoleOutput, 0x07);
system("cls");
SetConsoleTextAttribute(g_hConsoleOutput, FOREGROUND_GREEN | // 前景色_绿色
FOREGROUND_INTENSITY);
gotoxyWithFullwidth(15, 5);
printf("┏━━━━┓");
gotoxyWithFullwidth(15, 6);
printf("┃%2s%s%2s┃", "", "登录", "");
gotoxyWithFullwidth(15, 7);
printf("┗━━━━┛");
gotoxyWithFullwidth(12, 10);
printf("%2s%s%2s", "", "请输入用户名", "");
while((ch1=getch())!='\r' && i<=M)
{
if(ch1=='\b')
{
if(i>0)
{
i--;
printf("\b \b");// 密码支持退格的实现
}
else
putchar(7);
}
else
{
password1[i++]=ch1;
printf("%c",ch1);
}
}
password1[i]='\0';
i=0;
gotoxyWithFullwidth(12, 13);
printf("%2s%s%2s", "", "请输入密码", "");
while((ch=getch())!='\r' && i<=M)
{
if(ch=='\b')
{
if(i>0)
{
i--;
printf("\b \b");// 密码支持退格的实现
}
else
putchar(7);
}
else
{
password0[i++]=ch;
printf("*");
}
}
password0[i]='\0';
if(strcmp(password0,password)==0)
{
SetConsoleTextAttribute(g_hConsoleOutput, 0x07);
system("cls");
SetConsoleTextAttribute(g_hConsoleOutput, FOREGROUND_GREEN | // 前景色_绿色
FOREGROUND_INTENSITY);
gotoxyWithFullwidth(15, 5);
printf("┏━━━━┓");
gotoxyWithFullwidth(15, 6);
printf("┃%2s%s%2s┃", "", "登录", "");
gotoxyWithFullwidth(15, 7);
printf("┗━━━━┛");
gotoxyWithFullwidth(15, 16);
printf("%2s%s%2s", "", "密码正确", "");
gotoxyWithFullwidth(10, 19);
printf("%2s%s%2s", "", "登录成功,输入任意键开始游戏", "");
x=1;
strcpy(m->Name,password1);
getchar();
return x;
}
else if(n==1 || n==2)
{
SetConsoleTextAttribute(g_hConsoleOutput, 0x07);
system("cls");
SetConsoleTextAttribute(g_hConsoleOutput, FOREGROUND_GREEN | // 前景色_绿色
FOREGROUND_INTENSITY);
gotoxyWithFullwidth(15, 5);
printf("┏━━━━┓");
gotoxyWithFullwidth(15, 6);
printf("┃%2s%s%2s┃", "", "登录", "");
gotoxyWithFullwidth(15, 7);
printf("┗━━━━┛");
gotoxyWithFullwidth(15, 16);
printf("%2s%s%2s", "", "密码错误", "");
gotoxyWithFullwidth(14, 19);
printf("%2s%s%d%2s", "", "您还有",3-n,"次机会","");
getchar();
}
}
else
{
SetConsoleTextAttribute(g_hConsoleOutput, 0x07);
system("cls");
SetConsoleTextAttribute(g_hConsoleOutput, FOREGROUND_GREEN | // 前景色_绿色
FOREGROUND_INTENSITY);
gotoxyWithFullwidth(15, 5);
printf("┏━━━━┓");
gotoxyWithFullwidth(15, 6);
printf("┃%2s%s%2s┃", "", "登录", "");
gotoxyWithFullwidth(15, 7);
printf("┗━━━━┛");
gotoxyWithFullwidth(15, 16);
printf("%2s%s%2s", "", "密码均错误", "");
gotoxyWithFullwidth(15, 19);
printf("%2s%s%2s", "", "无法继续操作","");
getchar();
SetConsoleTextAttribute(g_hConsoleOutput, 0x07);
system("cls");
x=0;
return x;
}
}
}
// =============================================================================
//存储每局游戏数据
void iSaveLink(yonghu *temp)
{
FILE *p;
p=fopen("chengji.txt","w");
while(temp!=NULL)
{
fprintf(p,"%u %s\n",
temp->Score,
temp->Name);
temp=temp->next;
}
fclose(p);
}
// =============================================================================
//从文件读取学生成绩
yonghu *psctLoadLink(void)
{
FILE *p;
if((p=fopen("chengji.txt","r"))==NULL)
{
p=fopen("chengji.txt","a+");
yonghu *head,*temp1,*temp2;
head=(yonghu *)malloc(sizeof(yonghu));
head->Score=0,strcpy(head->Name,password1);
temp1=(yonghu *)malloc(sizeof(yonghu));
temp1->Score=0,strcpy(temp1->Name,password1);
temp2=(yonghu *)malloc(sizeof(yonghu));
temp2->Score=0,strcpy(temp2->Name,password1);
head->next=temp1;
temp1->next=temp2;
temp2->next=NULL;
fclose(p);
return head;
}
yonghu *head,*temp1,*temp2;
head=(yonghu *)malloc(sizeof(yonghu));
fscanf(p,"%u %s\n",&(head->Score),&(head->Name));
temp1=(yonghu *)malloc(sizeof(yonghu));
fscanf(p,"%u %s\n",&(temp1->Score),&(temp1->Name));
temp2=(yonghu *)malloc(sizeof(yonghu));
fscanf(p,"%u %s\n",&(temp2->Score),&(temp2->Name));
head->next=temp1;
temp1->next=temp2;
temp2->next=NULL;
fclose(p);
return head;
}
// =============================================================================
//展示排行榜前三名
void show(yonghu *temp)
{
yonghu *p;
p=temp;
SetConsoleTextAttribute(g_hConsoleOutput, FOREGROUND_GREEN | FOREGROUND_INTENSITY);
gotoxyWithFullwidth(15, 5);
printf("┏━━━━━┓");
gotoxyWithFullwidth(15, 6);
printf("┃%2s%s%2s┃", "", "排行榜", "");
gotoxyWithFullwidth(15, 7);
printf("┗━━━━━┛");
gotoxyWithFullwidth(16, 10);
printf("%2s%s%2s", "", "最高分", "");
gotoxyWithFullwidth(13, 11);
printf("%2s%s%2s%u分%2s", "",p->Name,"",p->Score, "");
p=p->next;
gotoxyWithFullwidth(16, 13);
printf("%2s%s%2s", "", "第二名", "");
gotoxyWithFullwidth(13, 14);
printf("%2s%s%2s%u分%2s", "",p->Name,"",p->Score, "");
p=p->next;
gotoxyWithFullwidth(16, 16);
printf("%2s%s%2s", "", "第三名", "");
gotoxyWithFullwidth(13, 17);
printf("%2s%s%2s%u分%2s", "",p->Name,"",p->Score, "");
getchar();
SetConsoleTextAttribute(g_hConsoleOutput, 0x07);
system("cls");
}
// =============================================================================
//选择难度界面
int nanduxuanze()
{
static const char *modelItem[] = { "1.低速模式", "2.中速模式", "3.高速模式", "4.死亡模式"};
int index = 0, ch;
SetConsoleTextAttribute(g_hConsoleOutput, FOREGROUND_GREEN | // 前景色_绿色
FOREGROUND_INTENSITY);
gotoxyWithFullwidth(15, 5);
printf("┏━━━━━━┓");
gotoxyWithFullwidth(15, 6);
printf("┃%2s%s%2s┃", "", "难度选择", "");
gotoxyWithFullwidth(15, 7);
printf("┗━━━━━━┛");
SetConsoleTextAttribute(g_hConsoleOutput, 0xF0);
gotoxyWithFullwidth(15, 14);
printf("%2s%s%2s", "", modelItem[0], "");
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY);
gotoxyWithFullwidth(15, 16);
printf("%2s%s%2s", "", modelItem[1], "");
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 18);
printf("%2s%s%2s", "", modelItem[2], "");
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 20);
printf("%2s%s%2s", "", modelItem[3], "");
do
{
ch = _getch();
switch (ch)
{
case 'w':case 'W':case '8':case 72: // 上
case 'a':case 'A':case '4':case 75:
if (index > 0) index--;
else index=3;
if (index == 0)
{
SetConsoleTextAttribute(g_hConsoleOutput, 0xF0);
gotoxyWithFullwidth(15, 14);
printf("%2s%s%2s", "", modelItem[0], "");
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY);
gotoxyWithFullwidth(15, 16);
printf("%2s%s%2s", "", modelItem[1], "");
gotoxyWithFullwidth(15, 18);
printf("%2s%s%2s", "", modelItem[2], "");
gotoxyWithFullwidth(15, 20);
printf("%2s%s%2s", "", modelItem[3], "");
}
else if (index == 1)
{
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 14);
printf("%2s%s%2s", "", modelItem[0], "");
SetConsoleTextAttribute(g_hConsoleOutput, 0xF0);
gotoxyWithFullwidth(15, 16);
printf("%2s%s%2s", "", modelItem[1], "");
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 18);
printf("%2s%s%2s", "", modelItem[2], "");
gotoxyWithFullwidth(15, 20);
printf("%2s%s%2s", "", modelItem[3], "");
}
else if (index == 2)
{
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY);
gotoxyWithFullwidth(15, 14);
printf("%2s%s%2s", "", modelItem[0], "");
gotoxyWithFullwidth(15, 16);
printf("%2s%s%2s", "", modelItem[1], "");
SetConsoleTextAttribute(g_hConsoleOutput, 0xF0);
gotoxyWithFullwidth(15, 18);
printf("%2s%s%2s", "", modelItem[2], "");
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 20);
printf("%2s%s%2s", "", modelItem[3], "");
}
else if (index == 3)
{
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 14);
printf("%2s%s%2s", "", modelItem[0], "");
gotoxyWithFullwidth(15, 16);
printf("%2s%s%2s", "", modelItem[1], "");
gotoxyWithFullwidth(15, 18);
printf("%2s%s%2s", "", modelItem[2], "");
SetConsoleTextAttribute(g_hConsoleOutput, 0xF0);
gotoxyWithFullwidth(15, 20);
printf("%2s%s%2s", "", modelItem[3], "");
}
break;
case 'd':case 'D':case '6':case 77:// 右
case 's':case 'S':case '2':case 80:
if (index <3) index++;
else index =0;
if (index == 0)
{
SetConsoleTextAttribute(g_hConsoleOutput, 0xF0);
gotoxyWithFullwidth(15, 14);
printf("%2s%s%2s", "", modelItem[0], "");
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 16);
printf("%2s%s%2s", "", modelItem[1], "");
gotoxyWithFullwidth(15, 18);
printf("%2s%s%2s", "", modelItem[2], "");
gotoxyWithFullwidth(15, 20);
printf("%2s%s%2s", "", modelItem[3], "");
}
else if (index == 1)
{
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 14);
printf("%2s%s%2s", "", modelItem[0], "");
SetConsoleTextAttribute(g_hConsoleOutput, 0xF0);
gotoxyWithFullwidth(15, 16);
printf("%2s%s%2s", "", modelItem[1], "");
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 18);
printf("%2s%s%2s", "", modelItem[2], "");
gotoxyWithFullwidth(15, 20);
printf("%2s%s%2s", "", modelItem[3], "");
}
else if (index == 2)
{
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 14);
printf("%2s%s%2s", "", modelItem[0], "");
gotoxyWithFullwidth(15, 16);
printf("%2s%s%2s", "", modelItem[1], "");
SetConsoleTextAttribute(g_hConsoleOutput, 0xF0);
gotoxyWithFullwidth(15, 18);
printf("%2s%s%2s", "", modelItem[2], "");
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 20);
printf("%2s%s%2s", "", modelItem[3], "");
}
else if (index == 3)
{
SetConsoleTextAttribute(g_hConsoleOutput,
FOREGROUND_BLUE | // 前景色_蓝色
FOREGROUND_INTENSITY );
gotoxyWithFullwidth(15, 14);
printf("%2s%s%2s", "", modelItem[0], "");
gotoxyWithFullwidth(15, 16);
printf("%2s%s%2s", "", modelItem[1], "");
gotoxyWithFullwidth(15, 18);
printf("%2s%s%2s", "", modelItem[2], "");
SetConsoleTextAttribute(g_hConsoleOutput, 0xF0);
gotoxyWithFullwidth(15, 20);
printf("%2s%s%2s", "", modelItem[3], "");
}
break;// 下
case ' ': case 13:
return index+1;
}
} while (1);
}