c语言数据结构程序设计俄罗斯方块

合集下载

C语言实现俄罗斯方块(转)

C语言实现俄罗斯方块(转)

C语⾔实现俄罗斯⽅块(转)原⽂地址如下:在图书馆看到⼀本书有俄罗斯⽅块的源程序⾃⼰当年也是俄罗斯⽅块的爱好者便想分析分析这个⼩游戏的源代码这⼏天有空就看了看发现读源码对编程领悟很有帮助读完深深的感觉到程序的确是好的数据结构加上好的算法这段程序定义了两个数据结构分别是//游戏底板结构,表⽰每个⼩⽅块所具有的属性struct BOARD{//当前状态,只有0或1,1表⽰次⼩⽅块已被占⽤int var;//⼩⽅块的颜⾊int color;}Table_board[Vertical_boxs][Horizontal_boxs];//游戏跳出的⽅块结构struct SHAPE{//⼀个字节等于8位,每四位来表⽰⼀个游戏⽅块的⼀⾏//如box[0]="0x88",box[1]="oxc0"表⽰的是://1000//1000//1100//0000//以此来表⽰游戏⽅块的各种形状char box[2];//游戏⽅块的颜⾊int color;//下⼀个游戏⽅块的编号int next;//这个next设计的也是相当妙啊};该源码的算法更确切的说是游戏的逻辑读完也是很有体会把握好⼤的系统强⼤的逻辑能⼒是必要的平时⾃⼰还是要再数据结构和算法这些⽅⾯加强学习、锻炼这段程序还有就是中断不是很理解还需要时间领悟⼀下下⾯贴⼀下我的程序注释这个游戏的层次描述:1预览功能2控制功能俄罗斯⽅块 3显⽰更新功能4分数更新功能5游戏帮助功能下⾯是源码:(该程序⽤到了TC的图形库,所以VC下是运⾏不了的,不过VC做代码编辑阅读⽐较⽅便,所以代码注释采⽤了VC下的//)//加载头⽂件#include <stdio.h>#include <stdlib.h>#include <dos.h>#include <graphics.h>//加载tc图形库//定义按键码#define VK_LEFT 0x4b00#define VK_RIGHT 0x4d00#define VK_DOWN 0x5000#define VK_UP 0x4800#define VK_ESC 0x011b//设置中断号 1c:时钟中断时得到控制权,若要固定时间发⽣事件,可以通过修改1c中断来得到#define TIMER 0x1c//共有19种形态的游戏⽅块#define MAX_BOX 19//⽅块的边长为20#define BSIZE 20//显⽰游戏界⾯的左上⾓x坐标#define Sys_x 160//显⽰游戏界⾯的左上⾓y坐标#define Sys_y 25//⽔平⽅向的⽅块数量#define Horizontal_boxs 10//垂直⽅向的⽅块数量#define Vertical_boxs 15//第⼀个游戏⽅块的产⽣起始位置#define Begin_boxs_x Horizontal_boxs/2//前景⾊#define FgColor 3//背景⾊#define BgColor 0//右边状态栏的x坐标#define LeftWin_x Sys_x+Horizontal_boxs*BSIZE+46#define false 0#define true 1//移动的⽅向#define MoveLeft 1#define MoveRight 2#define MoveDown 3#define MoveRoll 4//保存当前游戏⽅块编号int current_box_numb;//保存游戏⽅块的当前坐标int Curbox_x=Sys_x+Begin_boxs_x*BSIZE,Curbox_y=Sys_y;//是否要产⽣新游戏⽅块int flag_newbox=false;//下落速度int speed=1;//游戏得分int score=0;//每等级所需要分数int speed_step=30;//指向原来时钟中断处理过程⼊⼝的中断处理函数指针关键字interrupt指定⼀个函数应该被看成⼀个中断函数void interrupt(*oldtimer)(void);//游戏底板结构,表⽰每个⼩⽅块所具有的属性struct BOARD{//当前状态,只有0或1,1表⽰次⼩⽅块已被占⽤int var;//⼩⽅块的颜⾊int color;}Table_board[Vertical_boxs][Horizontal_boxs];//游戏跳出的⽅块结构struct SHAPE{//⼀个字节等于8位,每四位来表⽰⼀个游戏⽅块的⼀⾏//如box[0]="0x88",box[1]="oxc0"表⽰的是://1000//1000//1100//0000//以此来表⽰游戏⽅块的各种形状char box[2];//游戏⽅块的颜⾊int color;//下⼀个游戏⽅块的编号int next;};//初始化游戏⽅块的内容,包括形状颜⾊和下⼀个游戏⽅块编号struct SHAPE shapes[MAX_BOX]={{0x88,0xc0,CYAN,1},{0xe8,0x0,CYAN,2},{0xc4,0x40,CYAN,3},{0x2e,0x0,CYAN,0},{0x44,0xc0,MAGENTA,5},{0x8e,0x0,MAGENTA,6},{0xc8,0x80,MAGENTA,7},{0xe2,0x0,MAGENTA,4},{0x8c,0x40,YELLOW,9},{0x6c,0x0,YELLOW,8},{0x4c,0x80,BROWN,11},{0xc6,0x0,BROWN,10},{0x4e,0x0,WHITE,13},{0x8c,0x80,WHITE,14},{0xe4,0x0,WHITE,15},{0x4c,0x40,WHITE,12},{0x88,0x88,RED,17},{0xf0,0x0,RED,16},{0xcc,0x0,BLUE,18},};//定时计数器变量unsigned int TimerCounter=0;//以下为函数声明void initialize(int,int,int,int);void interrupt newtimer(void);void SetTimer(void interrupt(*IntProc)(void));void KillTimer(void);void ShowScore(int);void ShowSpeed(int);void show_help(int,int);void setFullRow(int);int DelFullRow(int);void show_box(int,int,int,int);void EraseBox(int,int,int);void ErasePreBox(int,int,int);int MkNextBox(int);int MoveAble(int,int,int,int);//主函数void main(){int GameOver=0;int key,nextbox;int Currentaction=0;int gd=VGA,gm=VGAHI,errorcode;initgraph(&gd,&gm,"");errorcode=graphresult();if(errorcode!=grOk){printf("\nNotice:Graphics error: %s\n",grapherrormsg(errorcode));printf("Press any key to quit!");getch();exit(1);}setbkcolor(BgColor);setcolor(FgColor);randomize();SetTimer(newtimer);initialize(Sys_x,Sys_y,Horizontal_boxs,Vertical_boxs);//初始化nextbox=MkNextBox(-1);show_box(Curbox_x,Curbox_y,current_box_numb,shapes[current_box_numb].color); show_box(LeftWin_x,Curbox_y+320,nextbox,shapes[nextbox].color);show_help(Sys_x,Curbox_y+320);getch();while (1){Currentaction=0;flag_newbox=false;//int bioskey(int cmd)//完成直接键盘操作,cmd的值决定执⾏什么操作//cmd=0,返回下⼀个键盘键⼊的值//cmd=1,查询是否按下⼀个键,若按下⼀个键返回⾮零值,否则返回0if(bioskey(1)){key=bioskey(0);}else{key=0;}switch(key){case VK_LEFT:if(MoveAble(Curbox_x,Curbox_y,current_box_numb,MoveLeft)){EraseBox(Curbox_x,Curbox_y,current_box_numb);Curbox_x-=BSIZE;Currentaction=MoveLeft;}break;case VK_RIGHT:if(MoveAble(Curbox_x,Curbox_y,current_box_numb,MoveRight)){EraseBox(Curbox_x,Curbox_y,current_box_numb);Curbox_x+=BSIZE;Currentaction=MoveRight;}break;case VK_DOWN:if(MoveAble(Curbox_x,Curbox_y,current_box_numb,MoveDown)){EraseBox(Curbox_x,Curbox_y,current_box_numb);Curbox_y+=BSIZE;Currentaction=MoveDown;}elseflag_newbox=true;break;case VK_UP:if(MoveAble(Curbox_x,Curbox_y,shapes[current_box_numb].next,MoveRoll)){EraseBox(Curbox_x,Curbox_y,current_box_numb);current_box_numb=shapes[current_box_numb].next;Currentaction=MoveLeft;}break;case VK_ESC:GameOver=1;break;default:break;}if (Currentaction)//当前有动作就执⾏{show_box(Curbox_x,Curbox_y,current_box_numb,shapes[current_box_numb].color); Currentaction=0;}if(flag_newbox)//按了向下键,但不能下移就产⽣新的游戏⽅块{ErasePreBox(LeftWin_x,Sys_y+200,nextbox);nextbox=MkNextBox(nextbox);show_box(LeftWin_x,Curbox_y+200,nextbox,shapes[nextbox].color);if(!MoveAble(Curbox_x,Curbox_y,current_box_numb,MoveDown)){show_box(Curbox_x,Curbox_y,current_box_numb,shapes[current_box_numb].color); GameOver=1;}else{flag_newbox=false;}Currentaction=0;}else//⾃由下落{if(Currentaction==MoveDown||TimerCounter>(20-speed*2)){if(MoveAble(Curbox_x,Curbox_y,current_box_numb,MoveDown)){EraseBox(Curbox_x,Curbox_y,current_box_numb);Curbox_y+=BSIZE;show_box(Curbox_x,Curbox_y,current_box_numb,shapes[current_box_numb].color); }TimerCounter=0;}}if(GameOver){printf("game over,thank you! your score is %d",score);getch();break;}}getch();KillTimer();closegraph();}//******************************************************************** //显⽰帮助,提⽰⽤户如何进⾏游戏的相关操作//void show_help(int xs,int ys){char stemp[50];setcolor(15);//void far rectangle(int x0,int y0,int x1,int y1)//以(x0,y0)为左上⾓,(x1,x2)为右下⾓画⼀个矩形框rectangle(xs,ys,xs+239,ys+100);//sprintf()//将字串格式化到字符串sprintf(stemp," -Roll -Downwards");stemp[0]=24;stemp[8]=25;setcolor(14);//void far outtextxy(int x,int y,char far *text)//将⽂本输出到指定位置outtextxy(xs+40,ys+30,stemp);sprintf(stemp," -Turn Left -Turn Right");stemp[0]=27;stemp[13]=26;outtextxy(xs+40,ys+45,stemp);outtextxy(xs+40,ys+60,"Esc-Exit");setcolor(FgColor);}//******************************************************************* //对游戏界⾯的初始化void initialize(int x,int y,int m,int n){int i,j,oldx;oldx=x;for(j=0;j<n;j++){for(i=0;i<m;i++){Table_board[j][i].var=0;Table_board[j][i].color=BgColor;line(x,y,x+BSIZE,y);line(x,y,x,y+BSIZE);line(x,y+BSIZE,x+BSIZE,y+BSIZE);line(x+BSIZE,y,x+BSIZE,y+BSIZE);x+=BSIZE;}y+=BSIZE;x=oldx;}Curbox_x=x;Curbox_y=y;flag_newbox=false;speed=1;score=0;ShowScore(score);ShowSpeed(speed);}//*************************************************************//显⽰当前⽤户的成绩void ShowScore(int score){int x,y;char score_str[5];setfillstyle(SOLID_FILL,BgColor);y=100;//确定⼀个以(x0,y0)为左上⾓,(x1,x2)为右下⾓的矩形窗⼝,再按规定图形和颜⾊填充bar(x-BSIZE,y,x+BSIZE*3,y+BSIZE*3);sprintf(score_str,"%3d",score);outtextxy(x,y,"SCORE");outtextxy(x,y+10,score_str);}//**********************************************************//显⽰当前下落速度void ShowSpeed(int speed){int x,y;char speed_str[5];setfillstyle(SOLID_FILL,BgColor);x=LeftWin_x;y=150;bar(x-BSIZE,y,x+BSIZE*3,y+BSIZE*3);sprintf(speed_str,"%3d",speed);outtextxy(x,y,"Level");outtextxy(x,y+10,speed_str);outtextxy(x,y+50,"Nextbox");}//**********************************************************//定义新的时钟中断处理函数void interrupt newtimer(void){//调⽤原来的例程(*oldtimer)();//全局计数器变量加1TimerCounter++;}//********************************************************//设置新的时钟中断处理void SetTimer(void interrupt (*IntProc)(void)){//获取中断号为TIMER的中断处理函数的⼊⼝地址oldtimer=getvect(TIMER);//设置新的时钟中断处理过程时,禁⽌所有中断disable();//将中断号为TIMER的中断处理函数⼊⼝地址改为IntProc()函数的⼊⼝地址setvect(TIMER,IntProc);//开启中断enable();}//*********************************************************//恢复原有的时钟中断处理过程void KillTimer(){disable();setvect(TIMER,oldtimer);enable();}//********************************************************//在(x,y)位置开始,⽤指定的颜⾊显⽰编号为box_num的游戏⽅块void show_box(int x,int y,int box_num,int color){int i,ii,ls_x=x;//指定的游戏⽅块不存在if(box_num<0||box_num>=MAX_BOX)box_num=MAX_BOX/2;//void far setfillstyle(int pattern,int color)//以pattern为填充模式以color为填充颜⾊对指定图形进⾏填充setfillstyle(SOLID_FILL,color);{int mask=128;//掩码,⽤于位运算//单个⽅块填充for(i=0;i<8;i++){if(i%4==0&&i!=0)//表⽰转到游戏⽅块的下⼀⾏了{y+=BSIZE;x=ls_x;}if((shapes[box_num].box[ii])&mask){bar(x,y,x+BSIZE,y+BSIZE);line(x,y,x+BSIZE,y);line(x,y,x,y+BSIZE);line(x,y+BSIZE,x+BSIZE,y+BSIZE);line(x+BSIZE,y,x+BSIZE,y+BSIZE);}x+=BSIZE;mask/=2;}y+=BSIZE;x=ls_x;}}//***************************************************************//清除(x,y)位置开始的编号为box_num的boxvoid EraseBox(int x,int y,int box_num){int mask=128,t_boardx,t_boardy,n,m;setfillstyle(SOLID_FILL,BgColor);for(n=0;n<4;n++){for (m=0;m<4;m++){if(((shapes[box_num].box[n/2])&mask)){bar(x+m*BSIZE,y+n*BSIZE,x+m*BSIZE+BSIZE,y+n*BSIZE+BSIZE);line(x+m*BSIZE,y+n*BSIZE,x+m*BSIZE+BSIZE,y+n*BSIZE);line(x+m*BSIZE,y+n*BSIZE,x+m*BSIZE,y+n*BSIZE+BSIZE);line(x+m*BSIZE,y+n*BSIZE+BSIZE,x+m*BSIZE+BSIZE,y+n*BSIZE+BSIZE); line(x+m*BSIZE+BSIZE,y+n*BSIZE,x+m*BSIZE+BSIZE,y+n*BSIZE+BSIZE); }mask/=2;if(mask==0)mask=128;}}}//*******************************************************//同EraseBox()void ErasePreBox(int x,int y,int box_numb){int mask=128,t_boardx,t_boardy,n,m;setfillstyle(SOLID_FILL,BgColor);for(n=0;n<4;n++){for(m=0;m<4;m++){if(((shapes[box_numb].box[n/2])&mask)){bar(x+m*BSIZE,y+n*BSIZE,x+m*BSIZE+BSIZE,y+n*BSIZE+BSIZE);}mask/=2;if(mask==0)mask=128;}}}//***************************************************************//将新图形的游戏⽅块放置在游戏板上,并返回此游戏⽅块号int MkNextBox(int box_numb){int mask=128,t_boardx,t_boardy,n,m;t_boardx=(Curbox_x-Sys_x)/BSIZE;t_boardy=(Curbox_y-Sys_y)/BSIZE;for(n=0;n<4;n++){for(m=0;m<4;m++){if(((shapes[current_box_numb].box[n/2])&mask)){//设置游戏⽅块Table_board[t_boardy+n][t_boardx+m].var=1;Table_board[t_boardy+n][t_boardx+m].color=shapes[current_box_numb].color;}mask=mask/2;if(mask==0)mask=128;}}setFullRow(t_boardy);//初始化坐标Curbox_x=Sys_x+Begin_boxs_x*BSIZE;Curbox_y=Sys_y;if(box_numb==-1)box_numb=rand()%MAX_BOX;//随机产⽣游戏⽅块current_box_numb=box_numb;flag_newbox=false;return (rand()%MAX_BOX);}//***********************************************************//⽤于找到满⾏,参数t_boardy表⽰当前的游戏⽅块号void setFullRow(int t_boardy){int n,full_numb=0,top=0;//top保存当前游戏主板在消除满⾏后的最⾼点,⽤于游戏主板的重绘register m;//寄存器类型,存取速度快for(n=t_boardy+3;n>=t_boardy;n--){if(n<0||n>=Vertical_boxs)continue;for(m=0;m<Horizontal_boxs;m++){if(!Table_board[n+full_numb][m].var)//发现有⼀个是空的就跳过break;}if(m==Horizontal_boxs)//找到满⾏{if(n==t_boardy+3)top=DelFullRow(n+full_numb);//清除该⾏,并保存最⾼点elseDelFullRow(n+full_numb);full_numb++;//保存满⾏的⾏数}}if(full_numb)//存在满⾏{int oldx,x=Sys_x,y=BSIZE*top+Sys_y;oldx=x;score=score+full_numb*10;for(n=top;n<t_boardy+4;n++){if(n>=Vertical_boxs)continue;//重绘游戏主板for(m=0;m<Horizontal_boxs;m++){if(Table_board[n][m].var){setfillstyle(SOLID_FILL,Table_board[n][m].color);}elsesetfillstyle(SOLID_FILL,BgColor);bar(x,y,x+BSIZE,y+BSIZE);line(x,y,x+BSIZE,y);line(x,y,x,y+BSIZE);line(x,y+BSIZE,x+BSIZE,y+BSIZE);line(x+BSIZE,y,x+BSIZE,y+BSIZE);x+=BSIZE;}y+=BSIZE;x=oldx;}ShowScore(score);if(speed!=score/speed_step){speed=score/speed_step;ShowSpeed(speed);}elseShowSpeed(speed);}}//************************************************************//处理删除⾏,参数y指明具体哪⼀⾏为满⾏int DelFullRow(int y){int n,top=0;register m,totoal;for (n=y;n>=0;n--){totoal=0;for(m=0;m<Horizontal_boxs;m++){if(!Table_board[n][m].var)totoal++;//没有⽅格,对计数器加1//上⾏不等于下⾏就把上⾏传给下⾏,此处为程序优化部分,也可不优化 if(Table_board[n][m].var!=Table_board[n-1][m].var){Table_board[n][m].var=Table_board[n-1][m].var;Table_board[n][m].color=Table_board[n-1][m].color;}}//发现上⾯有连续的空⾏,提前结束if (totoal==Horizontal_boxs){top=n;break;}}return top;//返回最⾼点}//********************************************************8//判断⽅块是否可以移动,(x,y)为当前游戏⽅块位置,box_numb为游戏⽅块号,direction为动作标识int MoveAble(int x,int y,int box_numb,int direction){int n,m,t_boardx,t_boardy;int mask;if(direction==MoveLeft)//如果向左移动{mask=128;x-=BSIZE;t_boardx=(x-Sys_x)/BSIZE;t_boardy=(y-Sys_y)/BSIZE;for(n=0;n<4;n++){for(m=0;m<4;m++){if((shapes[box_numb].box[n/2])&mask){if((x+BSIZE*m)<Sys_x)//碰到最左边return false;else if(Table_board[t_boardy+n][t_boardx+m].var)//左移⼀个单位后,与游戏主板冲突return false;}mask/=2;if(mask==0)mask=128;}}return true;}else if(direction==MoveRight)//右移动{x+=BSIZE;t_boardx=(x-Sys_x)/BSIZE;t_boardy=(y-Sys_y)/BSIZE;mask=128;for(n=0;n<4;n++){for(m=0;m<4;m++){if((shapes[box_numb].box[n/2])&mask){if((x+BSIZE*m)>=(Sys_x+BSIZE*Horizontal_boxs))//碰到最右边return false;else if(Table_board[t_boardy+n][t_boardx+m].var)//与游戏主板冲突return false;}mask/=2;if(mask==0)mask=128;}}return true;}else if(direction==MoveDown)//下移动{mask=128;y+=BSIZE;t_boardx=(x-Sys_x)/BSIZE;t_boardy=(y-Sys_y)/BSIZE;for(n=0;n<4;n++){for(m=0;m<4;m++){if((shapes[box_numb].box[n/2])&mask){if((y+BSIZE*n)>=(Sys_y+BSIZE*Vertical_boxs)||Table_board[t_boardy+n][t_boardx+m].var)//碰到最下边或向下有冲突 {flag_newbox=true;break;}}mask/=2;if(mask==0)mask=128;}}if(flag_newbox)return false;elsereturn true;}else if(direction==MoveRoll)//旋转{mask=128;t_boardx=(x-Sys_x)/BSIZE;t_boardy=(y-Sys_y)/BSIZE;for(n=0;n<4;n++){for(m=0;m<4;m++){if((shapes[box_numb].box[n/2])&mask){if((y+BSIZE*n)>=(Sys_y+BSIZE*Vertical_boxs))//碰到最下边return false;if((x+BSIZE*n)>=(Sys_x+BSIZE*Horizontal_boxs))//碰到最左边return false;if((x+BSIZE*m)>=(Sys_x+BSIZE*Horizontal_boxs))//碰到最右边return false;else if (Table_board[t_boardy+n][t_boardx+m].var)//向下有冲突{return false;}}mask/=2;if(mask==0)mask=128;}}return true;}elsereturn false;}。

C语言编写控制台版俄罗斯方块源码

C语言编写控制台版俄罗斯方块源码

C语言编写控制台版俄罗斯方块源码#include#include#include#include#include#includetypedef unsigned char uint8;typedef unsigned short uint16;typedef unsigned int uint32;typedef uint8 bool;#define APP_WIDTH 20#define APP_HEIGHT 20#define APP_MIN_X 8#define APP_MAX_X (APP_MIN_X + ((APP_WIDTH + 1) * 2)) #define APP_MIN_Y 3#define APP_MAX_Y (APP_MIN_Y + ((APP_HEIGHT + 1)))#define MAP_WIDTH 10#define MAP_HEIGHT 20#define MAP_MIN_X (APP_MIN_X + 2)#define MAP_MAX_X (MAP_MIN_X + (MAP_WIDTH *2))#define MAP_MIN_Y (APP_MIN_Y + 1)#define MAP_MAX_Y (MAP_MIN_Y + (MAP_HEIGHT))#define CTRL_WIDTH 8#define CTRL_HEIGHT 18#define CTRL_MIN_X (MAP_MAX_X + 2)#define CTRL_MAX_X (CTRL_MIN_X + (CTRL_WIDTH *2)) #define CTRL_MIN_Y (MAP_MIN_Y )#define CTRL_MAX_Y (MAP_MAX_Y - 1)#define BLOCK_WIDTH 4#define BLOCK_HEIGHT 4#define BLOCK_MIN_X (MAP_MIN_X + 6)#define BLOCK_MAX_X (MAP_MAX_X - 6)#define BLOCK_MIN_Y (MAP_MIN_Y )#define BLOCK_MAX_Y (MAP_MIN + 4)#define BLOCK_NUM 7#define BLOCK_DIR 4#define DIR_NONE 0#define DIR_UP 1#define DIR_DOWN 2#define DIR_LEFT 3#define DIR_RIGHT 4#define JK_FUNC_KEY 0x00#define JK_CTRL_KEY 0xE0#define JK_ESC 0x001B#define JK_ENTER 0x000D#define JK_SPACE 0x0020#define JK_BKSPACE 0x0008#define JK_TAB 0x0009#define JK_CTRL_Z 0x001A #define JK_CTRL_X 0x0018 #define JK_CTRL_C 0x0003 #define JK_CTRL_A 0x0001 #define JK_CTRL_S 0x0013 #define JK_CTRL_D 0x0004#define JK_LEFT 0xE04B #define JK_RIGHT 0xE04D #define JK_UP 0xE048#define JK_DOWN 0xE050 #define JK_INSERT 0xE052 #define JK_HOME 0xE047 #define JK_PGUP 0xE049 #define JK_DELETE 0xE053 #define JK_END 0xE04F#define JK_PGDW 0xE051#define JK_F1 0xFF3B#define JK_F2 0xFF3C#define JK_F3 0xFF3D#define JK_F4 0xFF3E#define JK_F5 0xFF3F#define JK_F6 0xFF40#define JK_F7 0xFF41#define JK_F8 0xFF42#define JK_F9 0xFF43#define JK_F10 0xFF44#define JK_F11 0xE085#define JK_F12 0xE086#define IS_BOX_IN_BLOCK(n,d,r,c) (BlockTable[(n)][(d)] & (0x00008000>> ((r) *BLOCK_WIDTH + (c))))// 各方块的码表,高16位为旋转掩码,低16位为方块的扫描码static uint32 BlockTable[BLOCK_NUM][BLOCK_DIR] ={{0xEE206C00, 0x66E04620, 0x8EE006C0, 0xECC08C40}, //S{0xE660C600, 0x2EE02640, 0xEE800C60, 0xCCE04C80}, //Z{0xECC088C0, 0xEE20E800, 0x66E06220, 0x8EE002E0}, //L{0x2EE02260, 0xCCE008E0, 0xEE80C880, 0xE660E200}, //J{0x7FCC4444, 0xEF330F00, 0x33FE2222, 0xCCF700F0}, //I{0xCC00CC00, 0xCC00CC00, 0xCC00CC00, 0xCC00CC00}, //O {0xE620E400, 0x26E02620, 0x8CE004E0, 0xEC808C80} //T};#define PRINT_BOX(bs) printf("%2s", BlockSharps[bs])#define IS_IN_MAP(x,y) (((x) >= MAP_MIN_X && (x) < MAP_MAX_X) && ( (y) >=MAP_MIN_Y && (y) < MAP_MAX_Y))#define IS_EMPTY_IN_MAP(x,y) ((MapTable[(y)][(x)]& 0x0F) == 0)char BlockSharps[2][4] = {" ", "■"};typedef struct POINTBLOCK{int x;int y;uint16 blocks;}PointBlock;static uint8 MapTable[30][30] = {{0}};void DrawMap (void);void gotoxy (int x, int y);void DrawBlock (PointBlock *block);uint16 CreateNewBlock (void);uint16 JkGetKey(void);bool JkHasKey(void);void FallDownBlock (PointBlock *nowpos, int *dir);void MoveBlock (PointBlock *nowpos, int * nowdir);void IniBlock (PointBlock *nowpos, PointBlock *nextpos);int CanRotate (int x, int y, uint16 block);int CanMove (int x, int y, uint16 block);void RedrawBlockInMap (int x, int y);int DropBlock (PointBlock *nowpos, PointBlock *nextpos, int *nowspeed, int *level, int *score, int *layer);void ErasePrevBlock(PointBlock *block);void KillLines (int col, int *nowspeed, int *level, int * score, int *layer);void RedrawALLBlock (int floor);void DrawBlockMenu (void);void printscore (int *score, int * layer, int *level);int setCursorVisible(int b);int Menu(void);int SetDifficulty(int *diff);int setCursorVisible(int b){HANDLE hd = GetStdHandle(STD_OUTPUT_HANDLE); CONSOLE_CURSOR_INFO ccInfo; GetConsoleCursorInfo(hd, &ccInfo);ccInfo.bVisible = !!b;return SetConsoleCursorInfo(hd, &ccInfo);}int main (void){int over = 0;int nowdir = DIR_NONE;int pause = 1;int speed = 900;int layer = 0;int score = 0;int level = 1;static PointBlock thisblock;static PointBlock nextblock;SetConsoleTitle ("仿写版俄罗斯方块"); setCursorVisible (0);level = Menu();if (level == 0){over = 0;ShowBye ();return 0;}speed = 1000 - level * 100;if (speed < 100)speed = 100;system ("cls");srand ((unsigned)time (NULL));DrawMap ();DrawBlockMenu();printscore(&score, &layer, &level);IniBlock(&thisblock, &nextblock);while (!over){if (!pause){MoveBlock (&thisblock, &nowdir);if (!DropBlock(&thisblock, &nextblock, &speed, &level, &score, &layer)){over = 1;break;}}if (JkHasKey ()){switch (JkGetKey()){case JK_UP:nowdir = DIR_UP;break;case JK_DOWN:nowdir = DIR_DOWN;break;case JK_LEFT:nowdir = DIR_LEFT;break;case JK_RIGHT:nowdir = DIR_RIGHT;break;case JK_ENTER:pause = !pause;break;case JK_ESC:over = 1;break;case JK_SPACE:if (!pause)FallDownBlock (&thisblock, &nowdir); break;default:break;}fflush(stdin);}}system ("cls");if ('y' == ShowOver(&score))return main();system ("cls");ShowBye();return 0;}void gotoxy (int x, int y){COORD pos;pos.X = x;pos.Y = y;SetConsoleCursorPosition(GetStdHandle(STD_OUTPUT_HA NDLE),pos);}void DrawMap (void){int i, j;//draw APPgotoxy (APP_MIN_X, APP_MIN_Y);printf ("┏");for (i = 0; i < APP_WIDTH; i++)printf ("━");printf ("┓");for (i = 0; i < APP_HEIGHT; i++){gotoxy (APP_MIN_X, APP_MIN_Y + i + 1); printf ("┃");gotoxy (APP_MAX_X, APP_MIN_Y + i +1);printf ("┃");}gotoxy (APP_MIN_X, APP_MAX_Y);printf ("┗");for (i = 0; i < APP_WIDTH; i++)printf ("━");printf ("┛");//draw mapfor (i = 0; i < MAP_WIDTH; i++){for (j = 0; j < MAP_HEIGHT; j++){gotoxy ((MAP_MIN_X + (i * 2)), MAP_MIN_Y + j); printf (" ");}}// draw ctrlgotoxy (CTRL_MIN_X -2, CTRL_MIN_Y);p rintf ("┌");gotoxy (CTRL_MAX_X, CTRL_MIN_Y);printf ("┐");gotoxy (CTRL_MAX_X, CTRL_MAX_Y);printf ("┘");gotoxy (CTRL_MIN_X-2, CTRL_MAX_Y);printf ("└");for (i = 0; i < CTRL_WIDTH; i++){gotoxy (CTRL_MIN_X + (i * 2), CTRL_MIN_Y); printf ("─");gotoxy (CTRL_MIN_X + (i * 2), CTRL_MIN_Y + 5); printf ("─");gotoxy (CTRL_MIN_X + (i * 2), CTRL_MAX_Y); printf ("─");}for (i = 0; i < CTRL_HEIGHT; i++){gotoxy (CTRL_MIN_X - 2, CTRL_MIN_Y + 1 + i); printf ("│");gotoxy (CTRL_MAX_X, CTRL_MIN_Y +1 + i); printf ("│");}gotoxy(CTRL_MIN_X - 2, CTRL_MIN_Y + 5);printf ("├");gotoxy(CTRL_MAX_X, CTRL_MIN_Y + 5);printf ("┤");}uint16 CreateNewBlock (void){uint8 blocknum = (rand () + 255) % BLOCK_NUM; uint8 blockdir = 0;return ((blocknum << 4) | (blockdir));void DrawBlock (PointBlock *block){uint8 blocknum = (block->blocks & 0x00f0) >> 4; uint8 blockdir = (block->blocks & 0x000f);int i, j;for (i = 0; i < BLOCK_HEIGHT; i++){for (j = 0; j < BLOCK_WIDTH; j++){if(IS_BOX_IN_BLOCK(blocknum, blockdir, i, j)) {gotoxy (block->x + j *2, block->y + i);printf ("■");}}}}bool JkHasKey (void){bool k;if (kbhit ())k = 1;elsek = 0;return k;uint16 JkGetKey (){int rk = 0;int k = getch ();if (k == JK_FUNC_KEY){k = getch ();rk = 0xff00 | k;return rk;}if (k == JK_CTRL_KEY){k = getch ();rk = 0xe000 | k;return rk;}rk = 0x0000 |k;return rk;}void FallDownBlock(PointBlock * nowpos, int *dir ) {int hx = nowpos->x;int hy = nowpos->y;while (CanMove (hx, hy, nowpos->blocks))hy++;RedrawBlockInMap(nowpos->x, nowpos->y);nowpos->x = hx;nowpos->y = hy-1;DrawBlock(nowpos);*dir = DIR_NONE;}void MoveBlock (PointBlock *nowpos, int * nowdir) {int hx = nowpos->x;int hy = nowpos->y;uint16 theblock = nowpos->blocks;uint8 bd = theblock & 0x0f;if (*nowdir == DIR_NONE)return ;switch (*nowdir){case DIR_UP:if (CanRotate (hx, hy, theblock)){theblock &= 0xfff0;theblock |= (bd + 1) % BLOCK_DIR;}else{*nowdir = DIR_NONE;return;}break;case DIR_DOWN:hy++;break;case DIR_LEFT:hx -= 2;break;case DIR_RIGHT:hx += 2;break;default:break;}if (CanMove (hx, hy, theblock)){RedrawBlockInMap (nowpos->x, nowpos->y);nowpos->blocks = theblock;nowpos->x = hx;nowpos->y = hy;DrawBlock(nowpos);}*nowdir = DIR_NONE;}void IniBlock (PointBlock * nowpos, PointBlock * nextpos) {nextpos->x = 36;nextpos->y = 5;nextpos->blocks = CreateNewBlock ();DrawBlock (nextpos);nowpos->x = BLOCK_MIN_X;nowpos->y = BLOCK_MIN_Y;nowpos->blocks = CreateNewBlock ();DrawBlock (nowpos);}int CanRotate (int x, int y, uint16 block){int i, j;uint8 blocknum = (block & 0x00f0) >> 4;uint8 blockdir = block & 0x000f;int mx, my;for (i = 0; i < BLOCK_HEIGHT; i++){for (j = 0; j < BLOCK_WIDTH; j++){mx = x + j * 2;my = y + i;if (!IS_BOX_IN_BLOCK (blocknum, blockdir, i, j)) continue;if (!((IS_IN_MAP (mx, my)) && (IS_EMPTY_IN_MAP (mx, my)))) return 0;}}return 1;}int CanMove (int x, int y, uint16 block){int i, j;uint8 blocknum = (block & 0x00f0 ) >> 4;uint8 blockdir = block & 0x000f;int mx, my;for (i = 0; i < BLOCK_HEIGHT; i++){for (j = 0; j < BLOCK_WIDTH; j++){mx = x + j * 2;my = y + i;if (!IS_BOX_IN_BLOCK (blocknum, blockdir, i, j)) continue;if (!(IS_IN_MAP (mx, my) && IS_EMPTY_IN_MAP (mx, my))) return 0;}}return 1;}void RedrawBlockInMap (int x, int y){int i, j;int mx, my ;for (i = 0 ; i < BLOCK_HEIGHT; i++){for (j = 0; j < BLOCK_WIDTH; j++){mx = x + j * 2;my = y + i;if (IS_IN_MAP(mx, my) && IS_EMPTY_IN_MAP (mx, my)){gotoxy (mx, my);printf (" ");}}}}int DropBlock (PointBlock *nowpos, PointBlock *nextpos, int *nowspeed, int *level, int *score, int *layer){int hx = nowpos->x;int hy = nowpos->y;int i, j ;int mx, my;uint8 blocknum = (nowpos->blocks & 0x00f0) >> 4;uint8 blockdir = nowpos->blocks & 0x000f;static long lastclock = 0L;//Sleep (2000);if (clock() - lastclock > *nowspeed){lastclock = clock ();hy++;if (CanMove (hx, hy, nowpos->blocks)){RedrawBlockInMap(nowpos->x, nowpos->y);nowpos->x = hx;nowpos->y = hy;DrawBlock (nowpos);}else{for (i = 0; i < BLOCK_HEIGHT; i++){for (j = 0; j < BLOCK_WIDTH; j++){mx = nowpos->x + j * 2;my = nowpos->y + i;if (IS_BOX_IN_BLOCK (blocknum, blockdir, i, j) && IS_IN_MAP (mx, my)){MapTable[my][mx] = 1;}}}KillLines (nowpos->y, nowspeed, level, score, layer);for (j = 0; j < BLOCK_WIDTH; j++)if (MapTable[MAP_MIN_Y][j] != 0)return 0;nowpos->blocks = nextpos->blocks;ErasePrevBlock(nextpos);nextpos->blocks = CreateNewBlock ();nowpos->x = BLOCK_MIN_X;nowpos->y = BLOCK_MIN_Y;if (!CanMove (nowpos->x, nowpos->y, nowpos->blocks))return 0;DrawBlock (nowpos);DrawBlock (nextpos);}}return 1;}void ErasePrevBlock(PointBlock *block){int i, j;for (i = 0; i < BLOCK_HEIGHT; i++){for (j = 0; j < BLOCK_WIDTH; j++){gotoxy (block->x + j *2, block->y + i);printf (" ");}}}void KillLines(int col, int *nowspeed, int *level, int * score, int *layer){int i, j, k, line, flag, killblock = 0;for (i = 0; i < BLOCK_HEIGHT; i++){flag = 1;for (j = 0; j < MAP_WIDTH; j++){if (IS_EMPTY_IN_MAP (MAP_MIN_X + j*2, col + i)){flag = 0;break;}}if (flag){line = col + i;gotoxy (MAP_MIN_X, line);for (j = 0; j < MAP_WIDTH; j++){printf (" ");}for (k = line; k > 0; k--){for (j = 0; j < MAP_WIDTH ; j++){MapTable[k][MAP_MIN_X + j * 2] = MapTable[k-1][MAP_MIN_X + j * 2];}}killblock++;RedrawALLBlock (col + BLOCK_HEIGHT - 1);}}(*layer) += killblock;(*score) += (10 + killblock + (*level)) * killblock;if ((*layer) > (*level) * 10){(*score) += (*level) * 100;(*level)++;(*nowspeed) = 1000 - *level * 100;if ((*nowspeed) < 100)(*nowspeed) = 100;}printscore(score, layer, level);}void RedrawALLBlock (int floor){int i, j;if (floor >= MAP_HEIGHT +4)floor = MAP_HEIGHT + 3;for (i = floor; i >= 4; i--){for (j = 0; j < MAP_WIDTH; j++){gotoxy (MAP_MIN_X + j *2, i);PRINT_BOX(MapTable[i][MAP_MIN_X + j *2] & 0x0f); }}}void DrawBlockMenu (void){gotoxy (32, 11);printf ("LEVEL :");gotoxy (32, 13);printf ("SCORE :");gotoxy (32, 15);printf ("LAYER :");gotoxy (32, 17);printf ("PAUSE : ENTER");gotoxy (32, 19);printf ("EXIT : ESC");gotoxy (32, 21);printf (" By : MoYu");}void printscore (int *score, int * layer, int *level){gotoxy (38, 11);printf ("%d", *level);gotoxy (38, 13);printf ("%d", *score);gotoxy (38, 15);printf ("%d", *layer);}int Menu()//这里是菜单选择的界面{int choose = 5, ischoose = 1;int diff = 1, i;//display menu interfacesystem("cls");//clear screen首先清屏gotoxy (8,4);printf("************************************************\");gotoxy (8,5);printf(" Start game.\");gotoxy (8,6);printf(" Choose Difficulty.\");gotoxy (8,7);printf(" Quit.\");gotoxy (8,9);printf(" Warning:Please select English input method."); gotoxy (8,10);printf("\\");gotoxy (8,11);printf("************************************************\"); do{for(i = 5; i<= 7; i++){gotoxy(10, i);//光标移到(2,i)处if(i == choose)printf("%c",16);//这里显示的是选择的三角elseprintf(" ");}//get keydownswitch(JkGetKey()){//获取键盘按键,方向键只能通过扫描码获取case JK_UP:if (choose > 5)choose --;break;case JK_DOWN:if (choose < 7)choose++;break;case JK_ENTER:ischoose = 0;break;default:;}}while (ischoose);switch (choose){case 6:SetDifficulty(&diff);//选择难度的界面case 5:return diff;case 7:return 0;}return 0;}int SetDifficulty(int *diff)//显示选择难度的界面{assert (NULL != diff);system("cls");//to show set difficulty level interfacegotoxy(0, 6);printf("%c\\",30);//显示正三角printf(" %c\",31);//显示倒三角printf("\Please press UP or DOWN to choose difficulty level."); while (1){gotoxy(0, 7);printf("Difficulty level: %d",*diff);switch(JkGetKey()){//获取按键信息并选择难度case JK_UP:if (*diff > 1)(*diff) --;break;case JK_DOWN:if (*diff < 9)(*diff) ++;break;case JK_ENTER:return 0;default:;}}}int ShowOver (int *score){int key;gotoxy (16, 9);printf("================================"); gotoxy (16,10);printf(" GAME OVER");gotoxy (16,11);printf("================================"); gotoxy (16,13);printf(" YOU GOT SCORE: %u", *score);Sleep (2000);do{gotoxy (16, 10);printf(" Replay?(y/n) [ ]");do{gotoxy(41, 10);key = getche();}while('y'!=key && 'n'!=key);}while ('\' != getch());*score = 0;return key;}//显示再见void ShowBye (void){system ("cls");gotoxy (20, 9);printf("================================"); gotoxy (20,10);printf(" GOOD Bye!");gotoxy (20,11);printf("================================"); Sleep (2000);}。

c语言俄罗斯方块游戏程序设计报告

c语言俄罗斯方块游戏程序设计报告

C语言课程设计报告主标题: C语言课程设计副标题:俄罗斯方块游戏----界面设计姓名:卢文俊指导教师:刘慧院系:信息工程学院专业:计算机科学与技术班级: 11计本(二)班小组成员:卢文俊,齐伟,陈龙提交日期: 2012-6-7俄罗斯方块程序设计报告一、问题描述:要求支持键盘操作和7种不同类型方块的旋转变换,并且界面上显示下一个方块的提示以及当前的玩家的得分,随着游戏的进行,等级越高,游戏难度越大,即方块的下落速度越快,相应的等级,等级越高,消去一行所得到的分数越高,为玩家提供了不同的选择。

二、功能分析:俄罗斯方块游戏需要解决的问题包括:⑴按任意键开始游戏,随机产生方块并自动下移⑵用Esc键退出游戏。

⑶用键变换方块⑷用键和键左右移动方块⑸用键使方块加速下移⑹用空格键使方块直接下移⑺能正确判断满行并消行、计分、定级别⑻能正确计时⑼设定游戏为不同级别,级别越高难度越大重点:*游戏面包的数据结构:二维数组*7种形状方块的数据结构:结构体保存每种形状方块的坐标、颜色三、程序设计:1、程序总体设计结构:首先初始化进入图形模式,进入欢迎界面,玩家按任意进入主菜单界面,按键进入游戏界面,键然后设置新的时钟中断。

开始游戏后,进入该程序最核心的部分——处理和实现进行过程中的各种事件和函数。

在处理中判断游戏是否结束,如果没有结束,则重新开始游戏,否则结束游戏。

详解如下:(1)、游戏方块预览功能。

在游戏过程中,当在游戏底板中出现一个游戏方块时,必须在游戏方块预览区域中出现下一个游戏方块,这样有利于游戏玩家控制游戏的策略。

由于在此游戏中存在19种不同的游戏方块,所以在游戏方块预览区域中需要显示随机生成的游戏方块。

(2)、游戏方块控制功能。

通过各种条件的判断,实现对游戏方块的左移、右移、快速下移、自由下落、旋转功能,以及行满消除行的功能。

否(3)、游戏显示更新功能。

在判断键值时,有左移VK_LEFT、右移VK_RIGHT、下移VK_DOWN、变形旋转VK_UP、退出VK_ESC键值的判断。

c语言程序设计 俄罗斯方块

c语言程序设计 俄罗斯方块
{"0000200000"},
{"0000110000"},
{"0001001000"},
{"0010000100"},
{"0100000010"}}},
{{{"0000000000"}, //5
{"0000000000"},
{"1011001101"},
{"0101111010"}}},
{{{"0000000000"}, //16
{"0000000000"},
{"0000200000"},
{"0000000000"},
{"1010101010"},
{"0001001000"},
{"0010000100"},
{"0010200100"},
{"0001111000"},
{"0001001000"},
{"0001001000"}}},
{{{"0000000000"}, //6
{"0001201000"},
{"0001111000"},
{"0001111000"}}},
{{{"0000000000"}, //3
{"0000000000"},
{"0000000000"},

C语言程序设计-俄罗斯方块源程序

C语言程序设计-俄罗斯方块源程序

其中的主要逻辑有:(1)由于c的随机性函数不好,所以每次游戏开始根据bios时间设置种子。

(2)得分越高,方块下降速度越快(每200分为单位)。

(3)每下落一个方块加1分,每消除一行加10分,两行加30分,三行加70分,四行加150分。

初试分数为100分。

游戏控制:up-旋转;空格-下落到底;左右下方向键-控制方向。

P-开始或暂停游戏。

ESC-退出。

特点:(1)由于tc不支持中文,所以基本都是英文注释。

(2)函数命名尽可能规范的表达其内部处理目的和过程。

(3)代码加上注释仅有577行。

(我下载过的两个俄罗斯方块代码一个在1087行,一个在993行,我的比它们代码少)。

(4)除了消除空格时算法比较复杂,其他算法都比较简单易读。

(5)绘图效率和局部代码效率扔有待提高。

(6)FrameTime参数可能依据不同硬件环境进行具体设置,InitGame需要正确的TC路径。

俄罗斯方块源于大约9年前上大一时的一个梦,我们在学习c语言时,我的同寝室友邀请我合作一起完成俄罗斯方块(课外作业性质),但是当时限于我们的水平比较菜和学习状态比较懒散,我们没有完成。

大一的时候我在机房里无意发现别人留下的俄罗斯方块程序,运行,老师发现后激动的问我是我写的吗,我惭愧的摇摇头。

那时看到别人做c的大程序深感羡慕(自己只是写几十行的程序)。

数年后我仍然看到有不同样式的实现,但是我一直没有实现它,知道今天忽然有这个想法去做,算是弥补多年前的遗憾和心愿吧。

---------------------------------------------Q&A:----------------------------------------------Q:我编译时出现错误:fatal error C1083: Cannot open include file: 'bios.h': Nosuch file or directory,该如何解决?A:正文中的代码,是使用Borland公司的TC2.0编译的,编译结果运行在Windows的16位虚拟机上。

自己用C语言编写的俄罗斯方块小游戏 hello world级

自己用C语言编写的俄罗斯方块小游戏  hello world级
break;
default : return ;
}
}
void clear_small_screen()
{
int i,j;
int x,y;
for(i=0;i<SMALL_CUBSIZE;i++){
for(j=0;j<SMALL_CUBSIZE;j++){
for (x = X_SMALL_START+j*SMALL_UNIT; x <X_SMALL_START+SMALL_UNIT+j*SMALL_UNIT; x++)
break;
case 17:
for(i=0;i<3;i++)
small_cub[0][i]=1;
small_cub[1][1]=1;
break;
case 18:
for(i=0;i<3;i++)
small_cub[i][1]=1;
small_cub[1][0]=1;
break;
case 7:
for(i=0;i<3;i++)
small_cub[i][0]=1;
small_cub[0][1]=1;
break;
case 8:
for(i=0;i<3;i++)
small_cub[0][i]=1;
small_cub[1][2]=1;
{
int i,j;
for(i=0;i<x;i+Байду номын сангаас){
for(j=0;j<y;j++){
if(chosen==1)

C语言编程俄罗斯方块的算法及源代码

C语言编程俄罗斯方块的算法及源代码

//俄罗斯方块#include "stdio.h"#include "conio.h"#include "stdlib.h"#include "windows.h"#include "time.h"#define N 17#define M 13#define K 19int s[N][M]={{0,0,0},{0,0},{0},{0},{0},{0},{0},{0},{0},{0},{0},{0},{0},{0}, {1},{1,0,0,1},{1,1,1,1,1,1,0,1,1,0,0,1,1}};/*当前状态*/inta[K][3][3]={{0,2,0,2,2,2},{0,2,0,2,2,0,0,2},{0,2,0,0,2,2,0,2},{2,2,2,0,2},{2,2,2,0,0,2 ,0},{2,0,0,2,2,2},{2,0,0,2,0,0,2,2},{0,0,2,0,0,2,0,2,2},{0,0,2,2,2,2},{2,2,2,2,0,0}, {2,2,0,0,2,0,0,2,0},{0,2,2,0,2,0,0,2,0},{{2},{2},{2}},{2,2,2},{2,2,0,2,2,0},{2,0,0,2,2,0,0,2},{0,0,2,0,2,2,0,2},{2,2,0,0,2,2},{0,2,2,2,2,0}};void Disp(){int i,j;for(i=0;i<N;i++){for(j=0;j<M;j++)printf("%c",s[i][j]?48+s[i][j]:' ');printf("┃\n");}printf("━━━━━━━━");printf("\n\n操作说明:A-->左移,D-->右移,W-->变形,ESC-->退出\n");}void Down(){int i,j,k;for(j=0;j<M;j++)if(s[N-1][j]==2)break;/*判断是否在下边界*/if(j<M)/*若方块在下边界则将方块由2变1;因为用两种不同的符号,容易判断方块是否“着陆”及左右移动时,是否碰壁*/{for(i=0;i<N;i++)for(j=0;j<M;j++)if(s[i][j]==2)s[i][j]=1;for(i=N-1;i>=0;i--){for(j=0;j<M;j++)//判断第i行是否有空格if(s[i][j]==0)break;if(j==M)/*若第i行没空格消去第i行*/for(k=i++-1;k>=0;k--)//?for(j=0;j<M;j++)s[k+1][j]=s[k][j];}return;}for(i=0;i<N-1;i++){for(j=0;j<M;j++)if(s[i][j]==2)if(s[i+1][j]!=0&&s[i+1][j]!=2)break;/*方块下方不空说明触到1了退出内循环*/ if(j<M)break;/*方块下方不空退出外循环*/}if(i<N-1||j<M){for(i=0;i<N;i++)//若已触到1则将方块由 2变1*/for(j=0;j<M;j++)if(s[i][j]==2)s[i][j]=1;for(i=N-1;i>=0;i--){for(j=0;j<M;j++)if(s[i][j]==0)break;//判断第i行是否有空格if(j==M)/*若第i行没空格消去第i行*/for(k=i++-1;k>=0;k--)for(j=0;j<M;j++)s[k+1][j]=s[k][j];}return;}for(i=N-1;i>=0;i--)for(j=0;j<M;j++)if(s[i][j]==2)s[i+1][j]=s[i][j],s[i][j]=0;/*方块下移*/}void Right(){int i,j;for(i=0;i<N;i++)if(s[i][M-1]==2)return;/* 已经在右边界退出 */for(i=0;i<N;i++)for(j=0;j<M-1;j++)if(s[i][j]==2)if(s[i][j+1]!=0&&s[i][j+1]!=2)return;/* 方块右方不空,即方块右边有1 退出 */ for(j=M-2;j>=0;j--)for(i=0;i<N;i++)if(s[i][j]==2)s[i][j+1]=s[i][j],s[i][j]=0;/* 方块右移 */}void Left(){int i,j;for(i=0;i<N;i++)if(s[i][0]==2)return;/* 已经在左边界退出 */for(i=0;i<N;i++)for(j=1;j<M;j++)if(s[i][j]==2)if(s[i][j-1]!=0&&s[i][j-1]!=2)return;/* 方块左方不空退出 */ for(j=1;j<M;j++)for(i=0;i<N;i++)if(s[i][j]==2)s[i][j-1]=s[i][j],s[i][j]=0;/* 方块左移 */}int Have()/*判断是否有可移动方块,没有返回1,否则返回0*/{int i,j;for(i=0;i<N;i++)for(j=1;j<M;j++)if(s[i][j]==2)return 0;return 1;}int Add()/*随机生成方块*/{int t,x;/*生成两随机数t和x分别作为第t种方块和第x位置出现*/int i,j;srand((unsigned int)time(NULL));t=rand()%K;x=rand()%(M-3);if(x<0) x=-x%(M-3);//?for(i=0;i<3;i++)for(j=x;j<x+3;j++)//把生成的方块存到初状态中s[i][j]=a[t][i][j-x];}void bianxing(int t,int n){int i,j,k,m,x,y;for(i=0;i<N;i++)//首先扫描是否有移动方块;及方块变形前的位置“行、列”{m=-1;for(j=0;j<M;j++)if(s[i][j]==2){m=i,x=j,y=i;break;//y,x记录所在行、列;并退出内循环}if(m!=-1)//m!=-1证明有移动方块break;//退出外循环}if(m!=-1)//m!=-1证明有移动方块{if(x+3>M||y+3>N) return;//判断是否有可变形空间,没有就返回for(i=y;i<y+3;i++)//判断是否有3*3的变形空间,没有就返回for(j=x;j<x+3;j++)if(s[i][j]==1) return;/*擦除当前移动方块;因为上面判断3*3的移动空间,是从上面开始扫描,遇到第一个小格子时,依他为基点向右下方扫描是否有3*3的空间;显然只进行下面的变形--存储是不行的;如:002002022-->2220020时,显然前面的方格倒数第二个2,留在了3*3变形空间的外面,输出图形将多一个格子,所以要在变形-->存储操作前进行擦除操作*/for(i=y;i<y+3;i++)for(j=0;j<M;j++)if(s[i][j]==2)s[i][j]=0;//变形并把它存储到当前状态中if(t<=3&&t>=0){static int h1;if(h1>n)h1=0;for(i=y;i<y+3;i++)//把方块存储到当前状态中for(j=x;j<x+3;j++)s[i][j]=a[h1][i-y][j-x];h1++;}else if(t<=11&&t>=4){static int h2=4;if(h2>n)h2=4;for(i=y;i<y+3;i++)//把方块存储到当前状态中for(j=x;j<x+3;j++)s[i][j]=a[h2][i-y][j-x];h2++;}else if(t<=13&&t>=12){static int h3=12;if(h3>n)h3=12;for(i=y;i<y+3;i++)//把方块存储到当前状态中for(j=x;j<x+3;j++)s[i][j]=a[h3][i-y][j-x];h3++;}else if(t<=18&&t>=15){static int h4=15;if(h4>n)h4=0;for(i=y;i<y+3;i++)//把方块存储到当前状态中for(j=x;j<x+3;j++)s[i][j]=a[h4][i-y][j-x];h4++;}}void main(){char c;int i=0,t;char str[][50]={" ((`'-\"``\"\"-'`))"," ) - - ( "," / (o _ o) \ "," \ ( 0 ) /"," _'-.._'='_..-'_ "," /`;#'#'#.-.#'#'#;`\ "," \_)) '#' ((_/ "," #. ☆ Game ☆ # "," '#. Over! .#' "," / '#. .#' \ "," _\ \'#. .#'/ /_"," (((___) '#' (___) ",""};system("color 0a");while(1)/*判断是否有按键,没有循环输出i,否则停,conio.h*/{if(!kbhit())/*kbhit用来判断是否有按键输入,若有按键返回非零值,否则返回零;没有按键时c被赋予一个“非操作键值”,它将一直下移;有按键是调用getch函数,读取键值*/c='2';elsec=getch();if(c=='p')//停止键;按任意键可解除停止getch();system("CLS");/*清屏,TC用clrscr();,VC用system("CLS");*/if(Have())//Have()判断是否有可移动方块,没有返回1,否则返回0t=Add();switch(c){case 'a':Left();break; /*左移*/case 'd':Right();break; /*右移*/case 27: system("pause");return; /*按Esc(=27)另存后退出*/default:;}//变形if(c=='w')if(t>=0&&t<=3) bianxing(t,3);else if(t>=4&&t<=11) bianxing(t,11);else if(t==12||t==13) bianxing(t,13);else if(t>=15&&t<=18) bianxing(t,18);c='2';Down();//判断方块的停、走和消除//判断顶层是否有1 有:游戏结束for(i=0;i<M;i++)if(s[0][i]==1){system("CLS");i=0;while(1){if(strlen(str[i])==0)break;printf("%s\n",str[i++]);}system("pause");exit(0);}Disp();//刷屏Sleep(500);/*睡眠ms,windows.h*/}}***********************************************************。

C语言俄罗斯方块试验报告,包括源程序

C语言俄罗斯方块试验报告,包括源程序

stopL()检测方块可左移则方块向左移一小格,向右方向键并且 stopR()检测方块可右移则方块向右移一
小格,向下方向键则方块向下移一小格,空格键则直接下移。
D. 消行与计分模块
当一个方块不能移动时需调用本模块 clrLine()。本模块将从该方块的最下面小方格所在行开始到最
上面小方格所在行结束,从左到右判断每一行是否满行;若满行则消行并且下移该行以上的已填充的小
(以下简称窗口M),高为 210 像素,宽为 120 像素,即由 252(21x12)个 10X10 的小方格组成。右
下的小窗口为绿色,主要显示游戏所用的时间、所得分数、所属级别。
2.方块的实现
首先说一下函数 fangKuai()与函数 clrFangKuai()。函数 fangKuai()在指定位置产生边框为蓝色用白
级,300 分到 700 分为 1 级,依此类推,1800 分到 2500 分为 4 级,超过 2500 分为 5 级。可以看到,除
了每一级要求的分数都比上一级多 100 分外,方块的自动下移速度也加快(0 级的 1/13)以增加游戏的
挑战性。
E. 计时模块
本模块主要是计算游戏所用的时间,由函数 coutTime()完成。游戏开始后,首先用 time(0)取得当前
色 WHITE 填充 的小 方格。 函数 clrFangKuai() 在指 定位 置产生 边框 与填充 色都 是窗口 M的 背景色
DARKGRAY 的小方格。
其次说方块的产生与清除。各方块及其顺时针旋转变换而来的方块统一在 16(=4X4)个小方格的
窗口(以下简称窗口L)中用4个小方格表示,建立基于窗口L的坐标系:窗口L左上角的小方格为
实验内容 游戏程序----俄罗斯方块

c课程设计俄罗斯方块

c课程设计俄罗斯方块

c 课程设计俄罗斯方块一、教学目标本课程的教学目标是让学生掌握C语言编程的基本知识,学会使用俄罗斯方块游戏引擎进行游戏开发。

具体分为以下三个部分:1.知识目标:使学生了解C语言的基本语法、数据类型、运算符、控制结构等,理解面向对象编程的基本概念,掌握游戏引擎的使用方法。

2.技能目标:培养学生具备运用C语言进行简单游戏开发的能力,能够独立完成俄罗斯方块游戏的编写,提高学生的编程实践能力。

3.情感态度价值观目标:激发学生对计算机编程的兴趣,培养学生的创新精神和团队合作意识,使学生在解决实际问题的过程中,体验到编程带来的成就感和乐趣。

二、教学内容教学内容主要包括C语言基础知识、面向对象编程、游戏引擎的使用和俄罗斯方块游戏的开发。

具体安排如下:1.第一章:C语言基础知识,包括数据类型、运算符、控制结构等。

2.第二章:面向对象编程,包括类与对象、继承与多态等。

3.第三章:游戏引擎的使用,包括引擎的基本功能、事件处理、图形渲染等。

4.第四章:俄罗斯方块游戏的开发,包括游戏逻辑、界面设计、音效处理等。

三、教学方法本课程采用讲授法、案例分析法、实验法等多种教学方法相结合的方式进行教学。

1.讲授法:用于讲解C语言基本语法、数据类型、运算符、控制结构等知识。

2.案例分析法:通过分析经典游戏案例,使学生掌握游戏引擎的使用方法和游戏开发技巧。

3.实验法:安排多次上机实验,让学生亲手编写代码,培养学生的实际编程能力。

四、教学资源教学资源包括教材、参考书、多媒体资料和实验设备等。

1.教材:选用《C程序设计原理与应用》作为主要教材,辅助以《C语言编程实战》等参考书。

2.多媒体资料:制作PPT、视频教程等,用于辅助讲解和演示。

3.实验设备:提供计算机实验室,让学生进行上机实验。

4.网络资源:推荐学生访问一些优秀的编程,如CSDN、StackOverflow等,以便于学生自主学习和交流。

五、教学评估本课程的评估方式包括平时表现、作业、考试等部分,以全面客观地评价学生的学习成果。

c语言怎样编写俄罗斯方块

c语言怎样编写俄罗斯方块

linesCleared++; for (int k = i; k > 0; k--) {
for (int j = 0; j < WIDTH; j++) { board[k][j] = board[k - 1][j];
} } for (int j = 0; j < WIDTH; j++) {
board[0][j] = 0; } } } printf("Lines cleared: %d\n", linesCleared); }
if (kbhit()) { char key = getch(); switch (key) { case 'a': if (!checkCollision(shapeX - 1, shapeY, shape)) { shapeX--; } break; case 'd': if (!checkCollision(shapeX + 1, shapeY, shape)) { shapeX++; } break; case 's': if (!checkCollision(shapeX, shapeY + 1, shape)) { shapeY++; } break; case 'w': int tempShape[4][4]; for (int i = 0; i < 4; i++) { for (int j = 0; j < 4; j++) { tempShape[i][j] = shape[i][j]; } } rotateShape(tempShape); if (!checkCollision(shapeX, shapeY, tempShape)) { rotateShape(shape); } break; case 'q': exit(0); }

俄罗斯方块C语言代码(计算机类)

俄罗斯方块C语言代码(计算机类)

#include <stdio.h>#include <dos.h>#include <conio.h>#include <graphics.h>#include <stdlib.h>#ifdef__cplusplus#define __CPPARGS ...#else#define __CPPARGS#endif#define MINBOXSIZE 15 /* 最小方块的尺寸*/#define BGCOLOR 7 /* 背景着色*/#define GX 200#define GY 10#define SJNUM 10000 /* 每当玩家打到一万分等级加一级*/ /* 按键码*/#define VK_LEFT 0x4b00#define VK_RIGHT 0x4d00#define VK_DOWN 0x5000#define VK_UP 0x4800#define VK_HOME 0x4700#define VK_END 0x4f00#define VK_SPACE 0x3920#define VK_ESC 0x011b#define VK_ENTER 0x1c0d/* 定义俄罗斯方块的方向(我定义他为4种)*/#define F_DONG 0#define F_NAN 1#define F_XI 2#define F_BEI 3#define NEXTCOL 20 /* 要出的下一个方块的纵坐标*/#define NEXTROW 12 /* 要出的下一个方块的横从标*/#define MAXROW 14 /* 游戏屏幕大小*/#define MAXCOL 20#define SCCOL 100 /*游戏屏幕大显示器上的相对位置*/#define SCROW 60int gril[22][16]; /* 游戏屏幕坐标*/int col=1,row=7; /* 当前方块的横纵坐标*/int boxfx=0,boxgs=0; /* 当前寺块的形壮和方向*/int nextboxfx=0,nextboxgs=0,maxcol=22;/*下一个方块的形壮和方向*/ int minboxcolor=6,nextminboxcolor=6;int num=0; /*游戏分*/int dj=0,gamedj[10]={18,16,14,12,10,8,6,4,2,1};/* 游戏等级*//* 以下我用了一个3维数组来纪录方块的最初形状和方向*/int boxstr[7][4][16]={{{1,1,0,0,0,1,1,0,0,0,0,0,0,0,0,0},{0,1,0,0,1,1,0,0,1,0,0,0,0,0,0,0},{1,1,0,0,0,1,1,0,0,0,0,0,0,0,0,0},{0,1,0,0,1,1,0,0,1,0,0,0,0,0,0,0}},{{0,1,1,0,1,1,0,0,0,0,0,0,0,0,0,0},{1,0,0,0,1,1,0,0,0,1,0,0,0,0,0,0},{0,1,1,0,1,1,0,0,0,0,0,0,0,0,0,0},{1,0,0,0,1,1,0,0,0,1,0,0,0,0,0,0}},{{1,1,0,0,0,1,0,0,0,1,0,0,0,0,0,0},{1,1,1,0,1,0,0,0,0,0,0,0,0,0,0,0},{1,0,0,0,1,0,0,0,1,1,0,0,0,0,0,0},{0,0,1,0,1,1,1,0,0,0,0,0,0,0,0,0}},{{1,1,0,0,1,0,0,0,1,0,0,0,0,0,0,0},{1,0,0,0,1,1,1,0,0,0,0,0,0,0,0,0},{0,1,0,0,0,1,0,0,1,1,0,0,0,0,0,0},{1,1,1,0,0,0,1,0,0,0,0,0,0,0,0,0}},{{0,1,0,0,0,1,0,0,0,1,0,0,0,1,0,0},{0,0,0,0,1,1,1,1,0,0,0,0,0,0,0,0},{0,1,0,0,0,1,0,0,0,1,0,0,0,1,0,0},{0,0,0,0,1,1,1,1,0,0,0,0,0,0,0,0}},{{1,1,0,0,1,1,0,0,0,0,0,0.0,0,0,0},{1,1,0,0,1,1,0,0,0,0,0,0.0,0,0,0},{1,1,0,0,1,1,0,0,0,0,0,0.0,0,0,0},{1,1,0,0,1,1,0,0,0,0,0,0.0,0,0,0}},{{0,0,0,0,1,1,1,0,0,1,0,0,0,0,0,0},{1,0,0,0,1,1,0,0,1,0,0,0,0,0,0,0},{0,1,0,0,1,1,1,0,0,0,0,0.0,0,0,0},{0,1,0,0,1,1,0,0,0,1,0,0,0,0,0,0}}};/* 随机得到当前方块和下一个方块的形状和方向*/void boxrad(){minboxcolor=nextminboxcolor;boxgs=nextboxgs;boxfx=nextboxfx;nextminboxcolor=random(14)+1;if(nextminboxcolor==4||nextminboxcolor==7||nextminboxcolor==8) nextminboxcolor=9;nextboxfx=F_DONG;nextboxgs=random(7);}/*初始化图形模试*/void init(int gdrive,int gmode){int errorcode;initgraph(&gdrive,&gmode,"e:\\tc");errorcode=graphresult();if(errorcode!=grOk){printf("error of: %s",grapherrormsg(errorcode));exit(1);}}/* 在图形模式下的清屏*/void cls(){setfillstyle(SOLID_FILL,0);setcolor(0);bar(0,0,640,480);}/*在图形模式下的高级清屏*/void clscr(int a,int b,int c,int d,int color){setfillstyle(SOLID_FILL,color);setcolor(color);bar(a,b,c,d);}/*最小方块的绘制*/void minbox(int asc,int bsc,int color,int bdcolor){int a=0,b=0;a=SCCOL+asc;b=SCROW+bsc;clscr(a+1,b+1,a-1+MINBOXSIZE,b-1+MINBOXSIZE,color);if(color!=BGCOLOR){setcolor(bdcolor);line(a+1,b+1,a-1+MINBOXSIZE,b+1);line(a+1,b+1,a+1,b-1+MINBOXSIZE);line(a-1+MINBOXSIZE,b+1,a-1+MINBOXSIZE,b-1+MINBOXSIZE); line(a+1,b-1+MINBOXSIZE,a-1+MINBOXSIZE,b-1+MINBOXSIZE); }}/*游戏中出现的文字*/void txt(int a,int b,char *txt,int font,int color){setcolor(color);settextstyle(0,0,font);outtextxy(a,b,txt);}/*windows 绘制*/void win(int a,int b,int c,int d,int bgcolor,int bordercolor){clscr(a,b,c,d,bgcolor);setcolor(bordercolor);line(a,b,c,b);line(a,b,a,d);line(a,d,c,d);line(c,b,c,d);}/* 当前方块的绘制*/void funbox(int a,int b,int color,int bdcolor){int i,j;int boxz[4][4];for(i=0;i<16;i++)boxz[i/4][i%4]=boxstr[boxgs][boxfx][i];for(i=0;i<4;i++)for(j=0;j<4;j++)if(boxz[i][j]==1)minbox((j+row+a)*MINBOXSIZE,(i+col+b)*MINBOXSIZE,color,bdcolor); }/*下一个方块的绘制*/void nextfunbox(int a,int b,int color,int bdcolor){int i,j;int boxz[4][4];for(i=0;i<16;i++)boxz[i/4][i%4]=boxstr[nextboxgs][nextboxfx][i];for(i=0;i<4;i++)for(j=0;j<4;j++)if(boxz[i][j]==1)minbox((j+a)*MINBOXSIZE,(i+b)*MINBOXSIZE,color,bdcolor);}/*时间中断定义*/#define TIMER 0x1cint TimerCounter=0;void interrupt ( *oldhandler)(__CPPARGS);void interrupt newhandler(__CPPARGS){TimerCounter++;oldhandler();}void SetTimer(void interrupt (*IntProc)(__CPPARGS)){oldhandler=getvect(TIMER);disable();setvect(TIMER,IntProc);enable();}/*由于游戏的规则,消掉都有最小方块的一行*/void delcol(int a){int i,j;for(i=a;i>1;i--)for(j=1;j<15;j++){minbox(j*MINBOXSIZE,i*MINBOXSIZE,BGCOLOR,BGCOLOR); gril[i][j]=gril[i-1][j];if(gril[i][j]==1)minbox(j*MINBOXSIZE,i*MINBOXSIZE,minboxcolor,0);}}/*消掉所有都有最小方块的行*/void delete(){int i,j,zero,delgx=0;char *nm="00000";for(i=1;i<21;i++){zero=0;for(j=1;j<15;j++)if(gril[j]==0)zero=1;if(zero==0){delcol(i);delgx++;}}num=num+delgx*delgx*10;dj=num/10000;sprintf(nm,"%d",num);clscr(456,173,500,200,4);txt(456,173,"Number:",1,15);txt(456,193,nm,1,15);}/*时间中断结束*/void KillTimer(){disable();setvect(TIMER,oldhandler);enable();}/* 测试当前方块是否可以向下落*/int downok(){int i,j,k=1,a[4][4];for(i=0;i<16;i++)a[i/4][i%4]=boxstr[boxgs][boxfx][i]; for(i=0;i<4;i++)for(j=0;j<4;j++)if(a[j] && gril[col+i+1][row+j])k=0;return(k);}/* 测试当前方块是否可以向左行*/ int leftok(){int i,j,k=1,a[4][4];for(i=0;i<16;i++)a[i/4][i%4]=boxstr[boxgs][boxfx][i]; for(i=0;i<4;i++)for(j=0;j<4;j++)if(a[j] && gril[col+i][row+j-1])k=0;return(k);}/* 测试当前方块是否可以向右行*/ int rightok(){int i,j,k=1,a[4][4];for(i=0;i<16;i++)a[i/4][i%4]=boxstr[boxgs][boxfx][i]; for(i=0;i<4;i++)for(j=0;j<4;j++)if(a[j] && gril[col+i][row+j+1])k=0;return(k);}/* 测试当前方块是否可以变形*/int upok(){int i,j,k=1,a[4][4];for(i=0;i<4;i++)for(i=0;i<16;i++)a[i/4][i%4]=boxstr[boxgs][boxfx+1][i]; for(i=3;i>=0;i--)for(j=3;j>=0;j--)if(a[j] && gril[col+i][row+j])k=0;return(k);}/*当前方块落下之后,给屏幕坐标作标记*/void setgril(){int i,j,a[4][4];funbox(0,0,minboxcolor,0);for(i=0;i<16;i++)a[i/4][i%4]=boxstr[boxgs][boxfx][i];for(i=0;i<4;i++)for(j=0;j<4;j++)if(a[j])gril[col+i][row+j]=1;col=1;row=7;}/*游戏结束*/void gameover(){int i,j;for(i=20;i>0;i--)for(j=1;j<15;j++)minbox(j*MINBOXSIZE,i*MINBOXSIZE,2,0);txt(103,203,"Game Over",3,10);}/*按键的设置*/void call_key(int keyx){switch(keyx){case VK_DOWN: { /*下方向键,横坐标加一。

C语言编写俄罗斯方块实验报告

C语言编写俄罗斯方块实验报告

`````````学院:数计学院班级:13级数媒班学号:姓名:摘要……………………………………………………………………………………………………..关键字:目录第一部分设计总概........................................................................................................................... 摘要…………………………………………………………………………………………………一、设计目的.............................................................................................................................二、设计要求.............................................................................................................................三、设计内容.............................................................................................................................四、系统分析与设计................................................................................................................. 第二部分数据结构设计................................................................................................................... 第三部分功能实现与程序调试………………………………………………………………….第四部分完成设计...........................................................................................................................一、实习日记.............................................................................................................................二、实习总结.............................................................................................................................三、教师评语.............................................................................................................................四、程序使用说明书………………………………………………………………………….第一部分设计总概一、设计目的二、设计要求三、设计内容四、系统分析与设计第二部分数据结构设计第三部分功能实现与程序调试第四部分完成设计一、实习日记:二、实习总结:………………………三、教师评语:设计成绩:指导老师签名:摘要使用C语言编写一个俄罗斯方块游戏系统,要求程序运行后有一个图形用户界面,实现各种方块的生产,包括形状和颜色等信息,完成左右下旋转的功能,在消行的同时分数加10,在点击暂停或者按下空格的时候暂停或开始游戏,最后结束游戏.关键字:音乐、背景、按键控制、暂停、继续、停止,难度级别第一部分设计总概一、设计目的:本课程设计是一个综合性的实践教学环节,目的在于促进学生复习和巩固计算机软件设计知识,加深对软件设计方法、软件设计技术和设计思想的理解,并能运用所学知识进行开发。

C语言实现俄罗斯方块源代码

C语言实现俄罗斯方块源代码

C语⾔实现俄罗斯⽅块源代码本⽂实例为⼤家分享了C语⾔实现俄罗斯⽅块的具体代码,供⼤家参考,具体内容如下GitHub:Head.h#ifndef _HEAD_H_#define _HEAD_H_#include<graphics.h>#include<stdio.h>#include<conio.h>#include<stdlib.h>#include<time.h>#include<string.h>#define _CRT_SECURE_NO_WARNINGS 1//界⾯的相关的参数#define WALL_SQUARE_WIDTH 10 //围墙⽅块的宽度#define xWALL_SQUARE_NUM 30 //x轴⽅向的⽅块的数⽬#define yWALL_SQUARE_WIDTH 46 //y轴⽅向的⽅块的数⽬#define GAME_WALL_WIDTH (WALL_SQUARE_WIDTH*xWALL_SQUARE_NUM) //游戏区域的宽度 300#define GAME_WALL_HTGH (WALL_SQUARE_WIDTH*yWALL_SQUARE_WIDTH) //游戏区域的⾼度 460#define WINDOW_WIDTH 480 // 游戏总窗⼝宽度 480#define WINDOW_HIGH 460 // 游戏总窗⼝⾼度 460//定义俄罗斯⽅块的相关参数#define ROCK_SQUARE_WIDTH (2*WALL_SQUARE_WIDTH) //俄罗斯⽅块的⼤⼩是围墙的两倍 20#define xROCK_SQUARE_NUM ((GAME_WALL_WIDTH -20)/ROCK_SQUARE_WIDTH) // 游戏区x轴放的⽅块数⽬:14 #define yROCK_SQUARE_NUM ((GAME_WALL_HTGH -20)/ROCK_SQUARE_WIDTH) // 游戏区y轴放的⽅块数⽬:22 //定义移动⽅块的相关操作#define DIRECT_UP 3#define DIRECT_DOWN 2#define DIRECT_LEFT -1#define DIRECT_RIGHT 1/*数据结构-线性表(结构体数组)*/typedef struct ROCK{//⽤来表⽰⽅块的形状(每⼀个字节是8位,⽤每4位表⽰⽅块中的⼀⾏)unsigned short rockShapeBits;int nextRockIndex; //下⼀个⽅块,在数组中的下标} RockType;//⽅块在图形窗⼝中的位置(即定位4*4⼤块的左上⾓坐标)typedef struct LOCATE{int left;int top;} RockLocation_t;//全局变量-游戏板的状态描述(即表⽰当前界⾯哪些位置有⽅块)//0表⽰没有,1表⽰有(多加了两⾏和两列,形成⼀个围墙,便于判断⽅块是否能够移动)int game_board[yROCK_SQUARE_NUM + 2][xROCK_SQUARE_NUM + 2] = { 0 };int game_socres = 0; //全局分数// 把俄罗斯⽅块的19种类放到数组中int rockTypeNum = 19;RockType RockArray[19] = { (0, 0) };//预览区的⽅块的位置RockLocation_t preRockLocation = {GAME_WALL_WIDTH+70,70};//每次⽣成初始化⽅块的位置RockLocation_t initRockLocation = { (WALL_SQUARE_WIDTH + 100), WALL_SQUARE_WIDTH };//分数显⽰的位置//各个⽂件中的函数void DisplayRock(int rockIdx, RockLocation_t* LocatePtr, bool displayed);//初始化Init源⽂件void InitGame();//game.hvoid PlayGame();bool IsGameOver();#endifDraw.h#include"Head.h"//画出游戏界⾯void DrawGameWindow(){//先画出围墙setcolor(BLUE);setlinestyle(PS_SOLID,NULL,0);setfillcolor(BLUE);//画出上下围墙for (int x = WALL_SQUARE_WIDTH; x <= GAME_WALL_WIDTH; x += WALL_SQUARE_WIDTH){fillrectangle(x - WALL_SQUARE_WIDTH, 0, x, WALL_SQUARE_WIDTH); //上fillrectangle(x - WALL_SQUARE_WIDTH, GAME_WALL_HTGH - WALL_SQUARE_WIDTH, x, GAME_WALL_HTGH);//下 }//画出左右围墙for (int y = WALL_SQUARE_WIDTH; y <= GAME_WALL_HTGH; y += WALL_SQUARE_WIDTH){fillrectangle(0, y, WALL_SQUARE_WIDTH, y + WALL_SQUARE_WIDTH);//左fillrectangle(GAME_WALL_WIDTH - WALL_SQUARE_WIDTH, y, GAME_WALL_WIDTH, y + WALL_SQUARE_WIDTH);//右 }//画出右边统计分数及相关东西//画出分割线setcolor(WHITE);setlinestyle(PS_DASH,2);line(GAME_WALL_WIDTH + 20, 0, GAME_WALL_WIDTH + 20, GAME_WALL_HTGH);//设置字体LOGFONT font;gettextstyle(&font);settextstyle(18, 0, _T("宋体"));font.lfQuality = ANTIALIASED_QUALITY;//设置输出效果为抗锯齿//1显⽰预览形状outtextxy(GAME_WALL_WIDTH + 80, 30, _T("预览"));outtextxy(GAME_WALL_WIDTH + 80, 170, _T("分数"));outtextxy(GAME_WALL_WIDTH + 65, 250, _T("操作说明"));outtextxy(GAME_WALL_WIDTH + 40, 290, _T("w a s d控制⽅向"));outtextxy(GAME_WALL_WIDTH + 40, 335, _T("空格暂停"));//显⽰分数setcolor(RED);outtextxy(GAME_WALL_WIDTH + 90, 200, '0');}//在游戏区显⽰编号为rockIdx的⽅块void DisplayRock(int rockIdx, RockLocation_t* LocatePtr, bool displayed){int color;//⽅块的填充颜⾊int lineColor = WHITE;//线的颜⾊int boardFalg = 0;int xRock = 0;int yRock = 0;unsigned short rockCode = RockArray[rockIdx].rockShapeBits;//如果displayed为true的话,将⽅块块颜⾊设置为white,game_board对应的位置设置为1;//如果displayed为false的话,将⽅块块颜⾊设置为black,game_board对应的位置设置为0;displayed ? (color = RED, boardFalg = 1) : (color = BLACK,lineColor = BLACK, boardFalg = 0);setcolor(lineColor);setlinestyle(PS_SOLID);//设置为实线,xRock = LocatePtr->left;yRock = LocatePtr->top;int count = 0;//每4个换⾏,记录坐标偏移量unsigned short mask = 1;for (int i = 1; i <= 16; ++i){mask = 1 << (16 - i);if ((rockCode & mask) != 0) //如果不为0的话,就画出⼩⽅块{fillrectangle(xRock , yRock, xRock + ROCK_SQUARE_WIDTH, yRock + ROCK_SQUARE_WIDTH); }if (i % 4 == 0) //换⾏{yRock = yRock + ROCK_SQUARE_WIDTH;xRock = xRock = LocatePtr->left;}else{xRock += ROCK_SQUARE_WIDTH;}}}Init.h#include"Head.h"static void ShapeStrToBit(unsigned char *rockShapeStr, unsigned short& rockShapeBit);static void ReadRcok();void InitGame(){//把全局游戏游戏版初始化,边界初始化为1for (int i = 0; i < xROCK_SQUARE_NUM + 2; i++){game_board[0][i] = 1; //上边界game_board[yROCK_SQUARE_NUM + 1][i] = 1; //下边界}for (int i = 0; i < yROCK_SQUARE_NUM + 2; i++){game_board[i][0] = 1 ; //左边界game_board[i][xROCK_SQUARE_NUM + 1] = 1; //右边界}//读取俄罗斯⽅块ReadRcok();}//从⽂件中读取⽅块的形状存储到rockArray中void ReadRcok(){FILE* fp = fopen("RockShape.ini","r");if (NULL == fp){printf("打开⽂件失败\n");return;}unsigned char readBuf[1024]; //fp读取到字符串readbuf中unsigned short rockShapeBit = 0;//存放⽅块形状,占16⽐特位unsigned char rockShapeStr[16];//存放⽅块字符串int ShapeStrIdx = 0;int rockNum = 0;//统计⽅块的个数以及存放⽅块数组RockArray的下标int rocknext = 0;//⽅块数组中下⼀个形状int rockShapeStart = 0;//同⼀类型的形状while (true){size_t readSize = fread(readBuf, 1, 1024, fp);if (readSize == 0)break;//处理readbuffor (size_t idx = 0; idx < readSize; ++idx){//将字符存放到rockShapeStr中if (readBuf[idx] == '@' || readBuf[idx] == '#'){rockShapeStr[ShapeStrIdx] = (unsigned char)readBuf[idx];++ShapeStrIdx;}++idx; //可能idx == readSize了if (readBuf[idx] == '*')//修改上⼀次⽅块的next值{idx += 5;RockArray[--rockNum].nextRockIndex = rockShapeStart;rockNum++;rockShapeStart = rockNum;rocknext = rockShapeStart ;}}//可能没有填满if (ShapeStrIdx < 16){break;}else //填满shapestr{ShapeStrIdx = 0;//置0//将rockShapeStr 转为rockShapeBitShapeStrToBit(rockShapeStr, rockShapeBit);rocknext++;RockArray[rockNum].rockShapeBits = rockShapeBit;RockArray[rockNum].nextRockIndex = rocknext;rockNum++;}}}fclose(fp);}//将从⽂件中读取的字符串(长度默认为16)转换成 unsigned shortvoid ShapeStrToBit(unsigned char *rockShapeStr, unsigned short& rockShapeBit){rockShapeBit = 0;for (size_t idx = 0; idx < 16; ++idx){if (rockShapeStr[idx] == '@') //1{rockShapeBit |= (1 << (16 - idx - 1));}// #为0 不需要处理}}game.h#include"Head.h"#define _CRT_SECURE_NO_WARNINGS 1bool MoveAble(int rockIndex, RockLocation_t* currentLocatePtr, int f_direction);void SetGameBoardFlag(int rockIdx, RockLocation_t* curRockLocation);void UserHitKeyBoard(char userHit, int* RockIndex, RockLocation_t* curRockLocation); void FullLine();void UpdateSocres(int scores);void DelCurLine(int rowIdx);bool IsGameOver();void PlayGame(){char userHit = 0;//⽤户敲击键盘int curRockIndex = 0;//当前⽅块的rockArray下标int nextRockIndex = 0;//下次RockLocation_t curRockLocation;curRockLocation.left = initRockLocation.left;curRockLocation.top = initRockLocation.top;DWORD oldtime = 0;srand((unsigned int)time(NULL));curRockIndex = rand() % rockTypeNum;nextRockIndex = rand() % rockTypeNum;//画出预览区初始化⽅块//在初始位置和预览区显⽰⽅块形状bool moveAbled = false;while (true){//判断当前⽅块是否落地(判断能否再下移):如果落地,判断是否满⾏,再判断是否结束游戏,改变game_board ,画出下次初始化的⽅块,以及⽣成新的预览⽅块 //moveAbled = MoveAble(curRockIndex, &curRockLocation, DIRECT_DOWN);if (!moveAbled) //判断是否落地,不能下移表⽰落地{//修改game_board的值SetGameBoardFlag(curRockIndex, &curRockLocation);FullLine();if (IsGameOver()){MessageBox(NULL, _T("游戏结束"), _T("GAME OVER"), MB_OK);exit(0);}//为下次⽣成模块开始准备DisplayRock(nextRockIndex, &preRockLocation, false);//擦除旧的⽅块curRockIndex = nextRockIndex;nextRockIndex = rand() % rockTypeNum; //⽣成新的预览⽅块DisplayRock(curRockIndex, &initRockLocation, 1);DisplayRock(nextRockIndex, &preRockLocation, 1);FlushBatchDraw();//修改curRockLocation的值curRockLocation.left = initRockLocation.left;curRockLocation.top = initRockLocation.top;}if (kbhit()) //如果敲击键盘了就处理按键{userHit = getch();UserHitKeyBoard(userHit, &curRockIndex, &curRockLocation);}//没有就⾃动下移⼀个单位 :不能⽤else,因为可能按键不是上下左右DWORD newtime = GetTickCount();if (newtime - oldtime >= (unsigned int)(300) && moveAbled == TRUE){oldtime = newtime;DisplayRock(curRockIndex, &curRockLocation, false);curRockLocation.top += ROCK_SQUARE_WIDTH; //下落⼀格}//AutomaticDownMove(curRockIndex, &curRockLocation);//画出新⽅块DisplayRock(curRockIndex, &curRockLocation, 1);FlushBatchDraw();Sleep(20);}}//响应键盘命令时间void UserHitKeyBoard(char userHit, int* RockIndex, RockLocation_t* curRockLocation){switch (userHit){case 'W':case 'w'://↑if (MoveAble(RockArray[*RockIndex].nextRockIndex, curRockLocation, DIRECT_UP)){DisplayRock(*RockIndex, curRockLocation, false);*RockIndex = RockArray[*RockIndex].nextRockIndex;}break;case 'S':case 's'://↓if (MoveAble(*RockIndex, curRockLocation, DIRECT_DOWN)){DisplayRock(*RockIndex, curRockLocation, false);curRockLocation->top += 2 * (ROCK_SQUARE_WIDTH);if (!MoveAble(*RockIndex, curRockLocation, DIRECT_DOWN)){curRockLocation->top -= ROCK_SQUARE_WIDTH;}}break;case 'A':if (MoveAble(*RockIndex, curRockLocation, DIRECT_LEFT)){DisplayRock(*RockIndex, curRockLocation, false);curRockLocation->left -= ROCK_SQUARE_WIDTH;}break;case 'D':case 'd': //→if (MoveAble(*RockIndex, curRockLocation, DIRECT_RIGHT)){DisplayRock(*RockIndex, curRockLocation, FALSE);curRockLocation->left += ROCK_SQUARE_WIDTH;}break;case ' ': //暂停while (1){userHit = getch();if (userHit == ' ')break;}break;default:break;}}//判断是否满⾏,满⾏消除,然后计算得分void FullLine(){bool linefull = true;int idx = yROCK_SQUARE_NUM;//从最后⼀⾏往上查找 22int count = 0;while (count != xROCK_SQUARE_NUM ) //遇到空⾏ 14{linefull = true;count = 0;for (int i = 1; i <= xROCK_SQUARE_NUM; ++i){if (game_board[idx][i] == 0){linefull = false;count++;}}if (linefull) //满⾏,消除当前⾏,更新分数{DelCurLine(idx);game_socres += 3;UpdateSocres(game_socres);idx++;//因为下⾯要减1}idx--;}}void UpdateSocres(int scores){setcolor(RED);TCHAR s[10];_stprintf(s, _T("%d"), scores);outtextxy(GAME_WALL_WIDTH + 90, 200, s);}//消除当前⾏void DelCurLine(int rowIdx){//擦除当前⾏setcolor(BLACK);setfillcolor(BLACK);for (int i = 1; i < xROCK_SQUARE_NUM; ++i){fillrectangle(WALL_SQUARE_WIDTH + (i - 1)*ROCK_SQUARE_WIDTH, (rowIdx - 1)*ROCK_SQUARE_WIDTH + WALL_SQUARE_WIDTH, WALL_SQUARE_WIDTH + i*ROCK_SQUARE_WIDTH, rowIdx*ROCK_SQUARE_WIDTH + WALL_SQUARE_WIDTH);}//把上⾯的向下移int cnt = 0;while (cnt != xROCK_SQUARE_NUM) //直到遇到是空⾏的为⽌cnt = 0;for (int i = 1; i <= xROCK_SQUARE_NUM; i++){game_board[rowIdx][i] = game_board[rowIdx - 1][i];//擦除上⾯的⼀⾏setcolor(BLACK);setfillcolor(BLACK);fillrectangle(WALL_SQUARE_WIDTH + ROCK_SQUARE_WIDTH*i - ROCK_SQUARE_WIDTH , WALL_SQUARE_WIDTH + ROCK_SQUARE_WIDTH*(rowIdx - 1) - ROCK_SQUARE_WIDTH , WALL_SQUARE_WIDTH + ROCK_SQUARE_WIDTH*i,WALL_SQUARE_WIDTH + ROCK_SQUARE_WIDTH*(rowIdx - 1));//显⽰下⾯的⼀⾏if (game_board[rowIdx][i] == 1){setcolor(WHITE);setfillcolor(RED);fillrectangle(WALL_SQUARE_WIDTH + ROCK_SQUARE_WIDTH*i - ROCK_SQUARE_WIDTH , WALL_SQUARE_WIDTH + ROCK_SQUARE_WIDTH*rowIdx - ROCK_SQUARE_WIDTH ,WALL_SQUARE_WIDTH + ROCK_SQUARE_WIDTH*i,WALL_SQUARE_WIDTH + ROCK_SQUARE_WIDTH*rowIdx);}if (game_board[rowIdx][i] == 0)cnt++; //统计⼀⾏是不是都是空格}//forrowIdx--;}}//是否可以移动⽅块bool MoveAble(int rockIndex, RockLocation_t* currentLocatePtr, int f_direction){int mask;int rockX;int rockY;rockX = currentLocatePtr->left;rockY = currentLocatePtr->top;mask = (unsigned short)1 << 15;for (int i = 1; i <= 16; i++){//与掩码相与为1的即为⽅块上的点if ((RockArray[rockIndex].rockShapeBits & mask) != 0){//判断能否移动(即扫描即将移动的位置是否与设置的围墙有重叠)//若是向上(即翻滚变形)if (f_direction == DIRECT_UP){//因为此情况下传⼊的是下⼀个⽅块的形状,故我们直接判断此⽅块的位置是否已经被占//判断下⼀个⽅块if (game_board[(rockY - WALL_SQUARE_WIDTH) / ROCK_SQUARE_WIDTH + 1][(rockX - WALL_SQUARE_WIDTH) / ROCK_SQUARE_WIDTH + 1] == 1)return false;}//如果是向下⽅向移动else if (f_direction == DIRECT_DOWN){if (game_board[(rockY - WALL_SQUARE_WIDTH) / ROCK_SQUARE_WIDTH + 2][(rockX - WALL_SQUARE_WIDTH) / ROCK_SQUARE_WIDTH + 1] == 1)return false;}else //如果是左右⽅向移动{ //f_direction的DIRECT_LEFT为-1,DIRECT_RIGHT为1,故直接加f_direction即可判断。

C语言课程设计俄罗斯方块源代码

C语言课程设计俄罗斯方块源代码

1、新建“。

h”头文件,将“头文件”代码粘贴至其中,2、新建“.c”源文件,将“源代码”代码粘贴到其中。

3、新建空白工程,将头文件和源代码添加进去,调试使用。

//头文件//1。

自定义枚举类型,定义7种形态的游戏方块typedef enum tetris_shape{ZShape=0,SShape,LineShape,TShape,SquareShape,LShape,MirroredLShape}shape;//2.函数声明//(1)操作方块函数int maxX();//取得当前方块的最大x坐标int minX();//取得当前方块的最小x坐标void turn_left();//当前方块逆时针旋转90度void turn_right();int out_of_table();void transform();int leftable();int rightable();int downable();void move_left();void move_right();//(2)操作游戏桌面的函数int add_to_table();void remove_full();//(3)控制游戏函数void new_game();void run_game();void next_shape();int random(int seed);//(4)绘图函数void paint();void draw_table();//(5)其他功能函数void key_down(WPARAM wParam);void resize();void initialize();void finalize();//(6)回调函数,用来处理Windows消息LRESULT CALLBACK WndProc (HWND,UINT,WPARAM,LPARAM);//源代码//1.文件包含#include〈windows.h>#include〈time.h>#include〈stdio。

使用C语言写俄罗斯方块

使用C语言写俄罗斯方块

我设想的俄罗斯方块如下图:我们先弹出一个窗口。

首先,新建一个windows应用工程,如下图:然后删除工程里预写好的代码,添加如下代码:然后再点击“编译并运行”按钮,弹出窗口:这样,我们的第一步,就算完成了,呵。

以后的我们的所有代码都是在上边代码的基础上添加而成的。

如图:上图是一种方块变形的四种情况,为表示以上所有的四的情况,我们需要建立一个三维数组:上边建立的三维数组应该不难理解吧,m_olshapePiece[0][x][y]就表示第一种形状,m_olshapePiece[1][x][y]表示第二种形状,m_olshapePiece[2[x][y]表示第三种形状,m_olshapePiece[3][x][y]表示第四种形状。

我们按照同样的方法,把其它几种形状的矩阵弄好,并且把它们设为全局变量,如下:接下来,让我们来看仔细看看我们游戏的布局:如上图所示,我们的游戏由五大块组成:一、按钮:这个就是完成一些特定功能的,比如开始、停止、暂停等等,第一个按钮在窗口上的坐标是(12,16)。

二、BigMap:它是我们游戏的主要区域,它由二维数组BigMap[12][21]来储存该格子是已有方块,BigMap由DrawBigMap()函数完成在窗口上的绘制。

它在窗口上的坐标是(12,66)。

三、CurPiece:它是当前正在掉落的方块,它由三维数组CurPiece[4][5][5]来储存,CupPiece是一个5*5的二维平面,但因为它有4种变形,所以我们需要准备4个二维平面。

CurPiece由DrawCurPiece()函数完成在窗口上的绘制。

它在窗口上的坐标由变量xPos、yPos储存。

四、NextPiece:它表示下一个要掉落的方块,它由三维数组NextPiece[4][5][5]来储存,由DrawNextPiece()函数完成在窗口上的绘制。

它在窗口上的坐标是(277,66)。

五、Score:它表示当前得分和游戏等级,由变量score和level储存(为了方便,我们还需要同时字符串scoreString[20]和levelString[20]储存),由DrawScore()函数完成在窗口上的绘制。

c语言数据结构程序设计俄罗斯方块

c语言数据结构程序设计俄罗斯方块

课程论文 ( 设计 )课程名称《数据结构》课程设计指导老师所在学院专业年级提交日期成绩小组成员表课程设计实验起止日期:2012-2013学年第二学期一、需求分析我们对俄罗斯方块这个游戏一点也不陌生,知道游戏的玩法和实现后,我们很快就着手开干。

游戏要有出现场景、方块、消除方块得分、判断游戏结束等几个大功能。

结构清晰简洁便于分工。

二、算法原理介绍游戏主要使用了数组这个数据结构。

不过与以往的程序不同,这个游戏有一个大数组包含很多个小数组,大数组不断的吸收小数组内的元素,达到条件得分。

三、概要设计1、功能块各函数列表2、场景的设置int map[28][17]={{0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0},{0,1,1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,1,1}, {0,1,1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,1,1}, {0,1,1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,1,1}, {0,1,1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,1,1}, {0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1},{0,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1}};void showmap(){int i,j;for(i=5;i<28;i++){for(j=1;j<17;j++){gotoxy(2*j,i);if(j==1||j==2||j==15||j==16){printf("┃");}else if(i==26||i==27){printf("━");}else if(map[i][j]==1) printf("■");else if(map[i][j]==0) printf("□");}}}3、其余功能的实现(如方块的出现下落旋转得分计算游戏结束条件判断等)(1)旋转void roll(){ int i,j;p_xnext=p_x;p_ynext=p_y;for(i=0;i<5;i++)for(j=0;j<5;j++){box_next_step[4-j][i]=box[i][j];}}(2)得分计算void score()int i,j,k;for(i=25;i>5;i--){for(j=3;j<15;j++){if(map[i][j]==1) flags=1;else {flags=0;break;}}if(flags==1){pointrank++;for(j=3;j<15;j++){for(k=i;k>5;k--){map[k][j]=map[k-1][j];}}i++;}}switch(pointrank){case 1:scores=scores+10;break;case 2:scores=scores+25;break;case 3:scores=scores+40;break;case 4:scores=scores+60;break;default:scores=scores+0;}gotoxy(40,15);printf("Your Score:%d",scores);pointrank=0;showmap();Sleep(300);}(3)游戏结束判断int gameover(){int i;for(i=3;i<15;i++){if(map[5][i]==1)return 1;}return 0;}四、测试分析1、游戏开始界面。

C语言小游戏源代《俄罗斯方块》

C语言小游戏源代《俄罗斯方块》

C语言小游戏源代码《俄罗斯方块》#include <stdlib.h>#include <stdio.h>#include <graphics.h>#define ESC 27#define UP 328#define DOWN 336#define LEFT 331#define RIGHT 333#define BLANK 32#define BOTTOM 2#define CANNOT 1#define CAN 0#define MAX 30#define F1 315#define ADD 43#define EQUAL 61#define DEC 45#define SOUNDs 115#define SOUNDS 83#define PAUSEP 80#define PAUSEp 112void Init();void Down();void GoOn();void ksdown();void Display(int color);void Give();int Touch(int x,int y,int dx,int dy);int GeyKey();void Select();void DetectFill();void GetScores();void Fail();void Help();void Quit();void DrawBox(int x,int y,int Color);void OutTextXY(int x,int y,char *String); void DispScore(int x,int y,char Ch);void DrawNext(int Color);int Heng=12,Shu=20; /*横竖*/int Position[MAX][MAX];int middle[MAX][MAX];int ActH,ActS;int Act,Staus;int i,j,k;int Wid=10;int NoPass=CAN;float Delays=15000;int BeginH=250,BeginS=7;float Seconds=0;int Scores=0;int flag=1;int Sounds=CAN;int PreAct,NextAct;int a[8][4][4][4]={{{1,0,0,0,1,0,0,0,1,0,0,0,1,0,0,0}, {1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0},{1,0,0,0,1,0,0,0,1,0,0,0,1,0,0,0},{1,1,1,1,0,0,0,0,0,0,0,0,0,0,0,0}},{{1,1,0,0,1,1,0,0,0,0,0,0,0,0,0,0},{1,1,0,0,1,1,0,0,0,0,0,0,0,0,0,0},{1,1,0,0,1,1,0,0,0,0,0,0,0,0,0,0},{1,1,0,0,1,1,0,0,0,0,0,0,0,0,0,0}},{{1,1,1,0,0,1,0,0,0,0,0,0,0,0,0,0},{0,1,0,0,1,1,0,0,0,1,0,0,0,0,0,0},{0,1,0,0,1,1,1,0,0,0,0,0,0,0,0,0},{1,0,0,0,1,1,0,0,1,0,0,0,0,0,0,0}},{{1,0,0,0,1,1,0,0,0,1,0,0,0,0,0,0},{0,1,1,0,1,1,0,0,0,0,0,0,0,0,0,0},{1,0,0,0,1,1,0,0,0,1,0,0,0,0,0,0},{0,1,1,0,1,1,0,0,0,0,0,0,0,0,0,0}},{{0,1,0,0,1,1,0,0,1,0,0,0,0,0,0,0},{1,1,0,0,0,1,1,0,0,0,0,0,0,0,0,0},{0,1,0,0,1,1,0,0,1,0,0,0,0,0,0,0},{1,1,0,0,0,1,1,0,0,0,0,0,0,0,0,0}},{{1,0,0,0,1,1,1,0,0,0,0,0,0,0,0,0},{1,1,0,0,1,0,0,0,1,0,0,0,0,0,0,0},{1,1,1,0,0,0,1,0,0,0,0,0,0,0,0,0}, {0,1,0,0,0,1,0,0,1,1,0,0,0,0,0,0}}, {{0,0,1,0,1,1,1,0,0,0,0,0,0,0,0,0}, {1,0,0,0,1,0,0,0,1,1,0,0,0,0,0,0}, {1,1,1,0,1,0,0,0,0,0,0,0,0,0,0,0}, {1,1,0,0,0,1,0,0,0,1,0,0,0,0,0,0}}, {{1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0}, {1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0}, {1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0}, {1,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0}}}; int b[4][4];main(int argc,char *argv[]){if (argc!=1){if (argv[1]!="")Heng=atoi(argv[1]);if (argv[2]!="")Shu=atoi(argv[2]);}Init(); /*初始化界面*/PreAct=random(8); /*取得当前的方块*/ for(;;) /*以下是游戏流程*/{NextAct=random(8); /*取得下一个方块*/ DrawNext(1); /*画出下一个方块*/Act=PreAct;if (Heng%2==0) ActH=Heng/2;else ActH=(Heng-1)/2;ActS=0; /*方块开始从游戏空间的中间下落*/Staus=0; /*取开始的状态*/NoPass=CAN; /*物体可以下落*/Give(); /*取得当前的方块*/Display(Act+1); /*显示当前的方块,每种方块的颜色不同*/ GoOn(); /*游戏的算法精髓所在*/PreAct=NextAct; /*方块下落完毕,取得下一个方块*/ DrawNext(0);}}void Init(){int GraphDriver=DETECT,GraphMode;registerbgidriver(EGAVGA_driver);initgraph(&GraphDriver,&GraphMode,"");if (kbhit()) Sounds=CANNOT;setcolor(1);OutTextXY(10,10,"Tetris");OutTextXY(30,30,"Version 2.0");OutTextXY(10,120,"Help:");OutTextXY(20,140,"+ :Faster");OutTextXY(20,160,"- :Slower");OutTextXY(20,180,"Esc :Quit");OutTextXY(20,200,"F1 :Help");OutTextXY(10,310,"Copyright(c) 1998.2.22");OutTextXY(10,320,"By Mr. Unique");outtextxy(10,250,"Score: 00000");rectangle(BeginH-3,BeginS-3,BeginH+Heng*(Wid+2)+2,BeginS+Shu*(Wid+2)+2);rectangle(BeginH-5,BeginS-5,BeginH+Heng*(Wid+2)+4,BeginS+Shu*(Wid+2)+4);rectangle(BeginH+(Heng+4)*(Wid+2)-2,BeginS+10,BeginH+(Heng+8)*(Wid+2)+2,BeginS+12+4*( Wid+2));for (i=0;i<MAX;i++)for (j=0;j<MAX;j++){Position[i][j]=1;middle[i][j]=-1;}for (i=0;i<Heng;i++)for (j=0;j<Shu;j++)Position[i][j]=0;for (i=0;i<Heng;i++)for (j=0;j<Shu;j++)DrawBox(i,j,0);randomize();}void GoOn(){for(;;){Seconds+=0.2; /*控制方块的下落速度*/if (Seconds>=Delays){Down();Seconds=0;if (NoPass==BOTTOM){DetectFill();middle[ActH][ActS]=Act;if (ActS==0)Fail();return;}}if (kbhit())Select();}}void Down() /*方块下降*/{Display(0);if (Touch(ActH,ActS,0,1)==CAN) ActS++;elsemiddle[ActH][ActS]=Act; Display(Staus+1);}int Touch(int x,int y,int dx,int dy) {NoPass=CAN;for (i=0;i<4;i++)for (j=0;j<4;j++)Position[x+dx+i][y+dy+j]+=b[i][j];for (i=0;i<MAX;i++)for (j=0;j<MAX;j++)if (Position[i][j]>1)NoPass=CANNOT;for (i=0;i<4;i++)for (j=0;j<4;j++){Position[x+dx+i][y+dy+j]-=b[i][j]; middle[x+dx+i][y+dy+j]=Act;}if (NoPass==CANNOT && dx==0 && dy==1) {for (i=0;i<4;i++)for (j=0;j<4;j++)Position[x+i][y+j]+=b[i][j];NoPass=BOTTOM;}return NoPass;}int GetKey(void){int Ch,Low,Hig;Ch=bioskey(0);Low=Ch&0x00ff;Hig=(Ch&0xff00)>>8;return(Low==0?Hig+256:Low);}void Select(){int OldStaus,acts=ActS;switch(GetKey()){case ESC :Quit();break;case DOWN :Seconds+=14500;break;case LEFT :Display(0);if (ActH>0 && Touch(ActH,ActS,-1,0)==CAN) { ActH--;}Display(Act+1);break;case RIGHT :Display(0);if (ActH<Heng && Touch(ActH,ActS,1,0)==CAN) { ActH++;}Display(Act+1);break;case BLANK : Display(0);ksdown();Display(Act+1);break;case F1 :Help();break;case EQUAL :case ADD :if (Delays>300) Delays-=100;break; case DEC :if (Delays<3000) Delays+=100;break; case PAUSEP :case PAUSEp :getch();break;case SOUNDS :case SOUNDs :if (Sounds==CAN)Sounds=CANNOT;elseSounds=CAN;break;case UP :if(Act==7){while(acts<Shu-1&&Position[ActH][acts]!=1) acts++;Position[ActH][acts]=0;DrawBox(ActH,acts,0);acts=ActS;break;}else{Display(0);OldStaus=Staus;switch(Act){case 0:case 3:case 4:if (Staus==1) Staus=0;else Staus=1;break; case 1:break;case 2:case 5:case 6:if (Staus==3) Staus=0;else Staus++;break; }Give();if (Touch(ActH,ActS,0,0)==CANNOT){Staus=OldStaus;Give();}Display(Act+1);break;}}}void ksdown(){while(flag){if(Touch(ActH,ActS,0,0)==CAN){ActS++;}else {ActS--;flag=0;}}flag=1;}void Quit(){int ch,TopScore;FILE *fp;if ((fp=fopen("Russian.scr","r+"))!=NULL) {fscanf(fp,"%d",&TopScore);if (Scores>TopScore){setcolor(1);outtextxy(470,80,"Hello !");outtextxy(470,100,"In all the players,"); outtextxy(470,120,"You are the First !"); outtextxy(470,140,"And your score will"); outtextxy(470,160,"be the NEW RECORD !"); fseek(fp,0L,0);fprintf(fp,"%d",Scores);}fclose(fp);}setcolor(1);OutTextXY(470,220,"Are You Sure (Yes/no)?");ch=getch();if (ch=='y'||ch=='Y'){closegraph();delay(20);exit(0);}setcolor(0);outtextxy(470,220,"Are You Sure (Yes/no)?"); }void OutTextXY(int x,int y,char *String) {int i=0;char a[2];moveto(x,y);a[1]='\0';while (*(String+i)!='\0'){a[0]=*(String+i);outtext(a);if (Sounds==CAN && a[0]!=' '){sound(3000);delay(50);nosound();}i++;}}void Help(){unsigned Save;void *Buf;Save=imagesize(160,120,500,360);Buf=malloc(Save);getimage(160,120,500,360,Buf);setfillstyle(1,1);bar(160,120,500,280);setcolor(0);OutTextXY(170,130," About & Help");OutTextXY(170,150," # # # ########## # # # "); OutTextXY(170,160," # ## # # # # # # ###### ### "); OutTextXY(170,170," ########## ########## ## # # "); OutTextXY(170,180," # # # # # # # ## #### "); OutTextXY(170,190," # ## # #### ## # # # "); OutTextXY(170,200," # ## # # # # # ## # # # "); OutTextXY(170,210," # # # ## ## # ###### # # # "); OutTextXY(170,220," ## # ## # ## # # # # "); OutTextXY(170,230," # ## # #### # ## # "); OutTextXY(170,260," Good Luckly to You !!! ");getch();putimage(160,120,Buf,0);free(Buf);}void GetScores(){int Sec10000,Sec1000,Sec100,Sec10,Sec1; setfillstyle(0,1);bar(60,250,109,260);Sec1=Scores%10;Sec10=(Scores%100-Scores%10)/10;Sec100=(Scores%1000-Scores%100)/100;Sec1000=(Scores%10000-Scores%1000)/1000; Sec10000=(Scores%100000-Scores%10000)/10000; DispScore(60,250,'0'+Sec10000);DispScore(70,250,'0'+Sec1000);DispScore(80,250,'0'+Sec100);DispScore(90,250,'0'+Sec10);DispScore(100,250,'0'+Sec1);DispScore(110,250,'0');DispScore(120,250,'0');}void DispScore(int x,int y,char Ch){char a[2];a[1]='\0';a[0]=Ch;outtextxy(x,y,a);void Give(){for (i=0;i<4;i++)for (j=0;j<4;j++)b[i][j]=a[Act][Staus][i][j];}void Display(int color){for (i=0;i<4;i++)for (j=0;j<4;j++)if (b[i][j]==1) DrawBox(ActH+i,ActS+j,color); }void DrawBox(int x,int y,int Color){x=BeginH+x*(Wid+2);y=BeginS+y*(Wid+2);setfillstyle(1,Color);bar(x+2,y+2,x+Wid-1,y+Wid-1);if (Color==0)setcolor(9);elsesetcolor(Act+1);rectangle(x+4,y+4,x+Wid-4,y+Wid-4);}void DrawNext(int Color)for (i=0;i<4;i++)for (j=0;j<4;j++)if (a[NextAct][0][i][j]==1) DrawBox(Heng+4+i,1+j,Color); }void DetectFill(){int Number,Fall,FallTime=0;for (i=Shu-1;i>=0;i--){Number=0;for (j=0;j<Heng;j++)if (Position[j][i]==1) Number++;if (Number==Heng){FallTime++;if (Sounds==CAN){sound(500);delay(500);nosound();}for (Fall=i;Fall>0;Fall--)for (j=0;j<Heng;j++){Position[j][Fall]=Position[j][Fall-1];middle[j][Fall]=middle[j][Fall-1];if (Position[j][Fall]==0) DrawBox(j,Fall,0); else DrawBox(j,Fall,middle[j][Fall]+1);}i++;}}switch(FallTime){case 0:break;case 1:Scores+=1;break;case 2:Scores+=3;break;case 3:Scores+=6;break;case 4:Scores+=10;break;}if (FallTime!=0){GetScores();if (Scores%100==0) Delays-=100;}}void Fail(){if (Sounds==CAN){for (k=0;k<3;k++){sound(300);delay(200);nosound();}}setcolor(1);OutTextXY(440,200,"Game over!"); Quit();closegraph();exit(0);}。

  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

课程名称《数据结构》课程设计指导老师所在学院专业年级提交日期成绩小组成员表课程设计实验一、需求分析我们对俄罗斯方块这个游戏一点也不陌生,知道游戏的玩法和实现后,我们很快就着手开干。

游戏要有出现场景、方块、消除方块得分、判断游戏结束等几个大功能。

结构清晰简洁便于分工。

二、算法原理介绍游戏主要使用了数组这个数据结构。

不过与以往的程序不同,这个游戏有一个大数组包含很多个小数组,大数组不断的吸收小数组内的元素,达到条件得分。

三、概要设计1、功能块各函数列表2、场景的设置int map[28][17]={{0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0},{0,1,1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,1,1},{0,1,1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,1,1},{0,1,1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,1,1},{0,1,1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1},{0,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1}};void showmap(){int i,j;for(i=5;i<28;i++){for(j=1;j<17;j++){gotoxy(2*j,i);if(j==1||j==2||j==15||j==16){printf("┃");}else if(i==26||i==27){printf("━");}else if(map[i][j]==1) printf("■");else if(map[i][j]==0) printf("□");}}}3、其余功能的实现(如方块的出现下落旋转得分计算游戏结束条件判断等)(1)旋转void roll(){ int i,j;p_xnext=p_x;p_ynext=p_y;for(i=0;i<5;i++)for(j=0;j<5;j++){box_next_step[4-j][i]=box[i][j];}}(2)得分计算void score(){int i,j,k;for(i=25;i>5;i--){for(j=3;j<15;j++){if(map[i][j]==1) flags=1;else {flags=0;break;}}if(flags==1){pointrank++;for(j=3;j<15;j++){for(k=i;k>5;k--){map[k][j]=map[k-1][j];}}i++;}}switch(pointrank){case 1:scores=scores+10;break;case 2:scores=scores+25;break;case 3:scores=scores+40;break;case 4:scores=scores+60;break;default:scores=scores+0;}gotoxy(40,15);printf("Your Score:%d",scores);pointrank=0;showmap();Sleep(300);}(3)游戏结束判断int gameover(){int i;for(i=3;i<15;i++){if(map[5][i]==1)return 1;}return 0;}四、测试分析1、游戏开始界面。

2、游戏进行中,操作键为键盘数字2、4、6、8,其中2为加速下落,4为左移,6为右移,8为旋转。

3、游戏介绍,按任意键退出游戏。

游戏结束条件:当方块高度到达顶部时,游戏自动停止,并提示Game Over。

总结:需求分析方面:我们对俄罗斯方块这个游戏一点也不陌生,知道游戏的玩法和实现后,我们很快就着手开干。

游戏要有出现场景·方块·消除方块得分·判断游戏结束等几个大功能。

结构清晰简洁便于分工。

问题:设计过程中遇到了些许难题,那就是如何才能可以在屏幕上指定位置显示内容。

一开始发现很困难,不过在和组员讨论过后,我们发现gotoxy()函数,十分简单的就解决了这个难题。

数据结构:游戏主要使用了数组这个数据结构。

不过与以往的程序不同,这个游戏有一个大数组包含很多个小数组,大数组不断的吸收小数组内的元素,达到条件得分。

代码#include<stdio.h>#include<stdlib.h>#include<windows.h>#include<time.h>#include<conio.h>#define MAX_BOX 7intp_x=5,p_y=1,map_x=1,map_y=1,p_xnext=5,p_ynext=1,scores=0,key1=0,flags=0,gamespeed=200,gamespeed1=20 0,pointrank=0;int MAX_X=17,MAX_Y=28;char key;int box[5][5]={0};int box_next_step[5][5]={0};int nextbox[5][5]={0};int boxtype[MAX_BOX][5][5]={ {{0,0,0,0,0},{0,0,1,0,0},{0,0,1,0,0},{0,0,1,0,0},{0,0,1,0,0}},{{0,0,0,0,0},{0,0,1,0,0},{0,1,1,1,0},{0,0,0,0,0},{0,0,0,0,0}},{{0,0,0,0,0},{0,1,1,0,0},{0,0,1,1,0},{0,0,0,0,0},{0,0,0,0,0}},{{0,0,0,0,0},{0,0,1,1,0},{0,1,1,0,0},{0,0,0,0,0},{0,0,0,0,0}},{{0,0,0,0,0},{0,0,1,1,0},{0,0,1,1,0},{0,0,0,0,0},{0,0,0,0,0}},{{0,0,0,0,0},{0,0,1,0,0},{1,1,1,0,0},{0,0,0,0,0},{0,0,0,0,0}},{{0,0,0,0,0},{0,0,1,0,0},{0,0,1,1,1},{0,0,0,0,0},{0,0,0,0,0}}};int map[28][17]={{0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0},{0,1,1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,1,1},{0,1,1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,1,1},{0,1,1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,1,1},{0,1,1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,0,0,0,0,0,0,0,0,0,0,0,0,1,1},{0,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1},{0,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1}};extern void showlogo();void gotoxy(int x,int y){//gotoxy在TC中是在system.h库文件里的一个函COORD c;c.X=x-1; c.Y=y-1;SetConsoleCursorPosition (GetStdHandle(STD_OUTPUT_HANDLE), c); }void showmap(){int i,j;for(i=5;i<28;i++){for(j=1;j<17;j++){gotoxy(2*j,i);if(j==1||j==2||j==15||j==16){printf("┃");}else if(i==26||i==27){printf("━");}else if(map[i][j]==1) printf("■");else if(map[i][j]==0) printf("□");}}}void next_box(){int type,i,j;srand(time(NULL));type=rand()%6;for(i=0;i<5;i++)for(j=0;j<5;j++){nextbox[i][j]=boxtype[type][i][j];}gotoxy(40,6);printf("Next:");gotoxy(40,7);for(i=0;i<5;i++)for(j=0;j<5;j++){gotoxy(40+2*j,7+i);if(nextbox[i][j]==1) printf("■");else printf(" ");}}int judgein(){int i,j;for(i=0;i<5;i++){for(j=0;j<5;j++){if(box_next_step[i][j]==1){if(map[p_ynext+i][p_xnext+j]==1)return 0;}}}return 1;}int gameover(){int i;for(i=3;i<15;i++){if(map[5][i]==1)return 1;}return 0;}void roll(){p_xnext=p_x;p_ynext=p_y;int i,j;for(i=0;i<5;i++)for(j=0;j<5;j++){box_next_step[4-j][i]=box[i][j];}}void score(){int i,j,k;for(i=25;i>5;i--){for(j=3;j<15;j++){if(map[i][j]==1) flags=1;else {flags=0;break;}}if(flags==1){pointrank++;for(j=3;j<15;j++){for(k=i;k>5;k--){map[k][j]=map[k-1][j];}}i++;}}switch(pointrank){case 1:scores=scores+10;break;case 2:scores=scores+25;break;case 3:scores=scores+40;break;case 4:scores=scores+60;break;default:scores=scores+0;}gotoxy(40,15);printf("Your Score:%d",scores);pointrank=0;showmap();Sleep(300);}void main(){showlogo();gotoxy(50,20);printf("w 转向s 加速下降");gotoxy(50,21);printf("a 左 d 右");int type,flag1=1,i,j,flag=0,flag2=1;showmap();next_box();Sleep(1000);srand(time(NULL));type=rand()%6;for(i=0;i<5;i++)for(j=0;j<5;j++){box[i][j]=boxtype[type][i][j];}for(i=0;i<5;i++){for(j=0;j<5;j++){gotoxy(2*p_x+2*j,p_y+i);if(box[i][j]==1&&map[p_y+i][p_x+j]==0){printf("■");}}}gotoxy(40,15);printf("Your Score:0");Sleep(gamespeed);Here:while(1){if(!kbhit()){for(i=0;i<5;i++)for(j=0;j<5;j++){box_next_step[i][j]=box[i][j];}p_xnext=p_x;p_ynext=p_y+1;flag1=judgein();if(flag1==0){for(i=0;i<5;i++){for(j=0;j<5;j++){gotoxy(2*p_x+2*j,p_y+i);if(box[i][j]==1&&map[p_y+i][p_x+j]==0){printf("■");}}}for(i=0;i<5;i++)for(j=0;j<5;j++){if(box[i][j]==1)map[p_y+i][p_x+j]=1;}flag=gameover();if(flag!=0){gotoxy(10,10);printf(" ");gotoxy(10,12);printf(" ");gotoxy(10,11);printf(" Game Over ");gotoxy(40,20);break;//应该修改!!!!!}else{score();p_x=5;p_y=1;for(i=0;i<5;i++)for(j=0;j<5;j++){box[i][j]=nextbox[i][j];}next_box();Sleep(300);}}else{for(i=0;i<5;i++)for(j=0;j<5;j++){gotoxy(2*p_x+2*j,p_y+i);if(box[i][j]==1&&map[p_y+i][p_x+j]==0){printf("□");}}p_y++;for(i=0;i<5;i++){for(j=0;j<5;j++){gotoxy(2*p_x+2*j,p_y+i);if(box[i][j]==1&&map[p_y+i][p_x+j]==0){printf("■");}}}Sleep(gamespeed);gamespeed=gamespeed1;}goto Here;}else {key=getch();switch(key){case'w':case'W':roll();flag2=judgein();if(flag2==1){for(i=0;i<5;i++)for(j=0;j<5;j++){gotoxy(2*p_x+2*j,p_y+i);if(box[i][j]==1&&map[p_y+i][p_x+j]==0){printf("□");}}for(i=0;i<5;i++)for(j=0;j<5;j++){box[i][j]=box_next_step[i][j];}}goto Here;case'a':case'A':p_xnext=p_x-1;p_ynext=p_y;flag2=judgein();if(flag2==1){for(i=0;i<5;i++)for(j=0;j<5;j++){gotoxy(2*p_x+2*j,p_y+i);if(box[i][j]==1&&map[p_y+i][p_x+j]==0){printf("□");}}p_x--;}goto Here;case'd':case'D':p_xnext=p_x+1;p_ynext=p_y;flag2=judgein();if(flag2==1){for(i=0;i<5;i++)for(j=0;j<5;j++){gotoxy(2*p_x+2*j,p_y+i);if(box[i][j]==1&&map[p_y+i][p_x+j]==0){printf("□");}}p_x++;}goto Here;case's':case'S':gamespeed=50;goto Here;default: goto Here;}}}}。

相关文档
最新文档