单机版火拼俄罗斯方块源程序
發(fā)表日期:2005年11月12日????? 已經(jīng)有3587位讀者讀過此文
?
/*這是我在參考別人的的俄羅斯方塊的基礎(chǔ)上,寫的一個單機版火拼俄羅斯方塊源程序,*/
/*如果有須要下載可到www.jxnczyp.ys168.com中的個人小程序中下載己編譯好的程序*/
/*如果想自己編譯要先在DOS輸入:bgiobj egavga*/
/*再輸入tlib graphics.lib+egavga.obj這樣就把你自己的圖形驅(qū)動程序加到你的小程序中了。只有一個文件也能運行*/
/*這個程序?qū)懙糜悬c爛,不過謝天謝地總算能用了。*/
/*如果有什么不清楚的地方,可以回QQ:254849895*/
/**/
/**/
/**/
/**/
/**/
/**/
/**/
/**/
?
?
#include<stdlib.h>/**/
#include<graphics.h>/**/
#include<dos.h>/**/
#include<time.h>/**/
#include<stdio.h>/**/
#include<string.h>/**/
#include<bios.h>/**/
#define ESC 0x11b
#define ANUM1 0x231
#define ANUM2 0x332
#define BNUM1 0x4f31
#define BNUM2 0x5032
#define LEFTA 0x1e61
#define RIGHTA 0x2064
#define UPA 0x1177
#define ADDOWN 0x3920
#define ACHANG 0x266c
#define LEFTB 0x4b00
#define RIGHTB 0x4d00
#define UPB 0x4800
#define BDDOWN 0x5230
#define BCHANG 0x1c0d
struct Map_Type{/*定義地圖,type為類形:當(dāng)其它 1為一般的方塊,2為加行的道具。3為減行的道具,4為加速道具。5為減速道具*/
? int type;
? int num;
}map[2][22][12],tool[2][12];/**/
int Block_Type[7][4][4]={/*定義七種基本方塊類型*/
? {{0,0,0,0},{0,1,0,0},{0,1,0,0},{0,1,1,0}},
? {{0,0,0,0},{0,0,1,0},{0,0,1,0},{0,1,1,0}},
? {{0,1,0,0},{0,1,0,0},{0,1,0,0},{0,1,0,0}},
? {{0,1,0,0},{0,1,1,0},{0,0,1,0},{0,0,0,0}},
? {{0,0,1,0},{0,1,1,0},{0,1,0,0},{0,0,0,0}},
? {{0,1,1,1},{0,0,1,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}}
?};
typedef struct{/**/
? int d[4][4];
}Block;
Block AB[2],AB_Temp[2],AB_Next[2];/*AB為正在移動的方塊,AB——Next為下一個方塊*/
int AB_X[2],AB_Y[2];/*移動方塊的位置*/
int AB_Tool_Num[2];/*道具的數(shù)目*/
int AB_X0[2]={10,230};/*第一,第二玩家的初始坐標(biāo)*/
int Speed_AB[2],Score_AB[2];/*速度和分?jǐn)?shù)*/
/**/
void InitGraph();/*初始化圖形*/
void CloseGraph();/*關(guān)閉圖形*/
void DrawBK();/*畫背景*/
void DrawMap(int mode);/*畫地圖*/
/*當(dāng)mode=0時對第一玩家進(jìn)行操作,當(dāng)mode=1時對第二玩家進(jìn)行操作*/
void DrawPerBlock(int x1,int y1,int x2,int y2,int ch,int num);/*畫每一個具體的方塊*/
void DrawSS(int mode);/*顯示分?jǐn)?shù)*/
void DrawTool(int mode);/*顯示道具*/
void DrawNextBlock(int mode);/*顯示下一個方塊*/
void DrawBlock(int k,int mode);/*顯示下在移動的方塊*/
void CreatBlock(Block *src);/*創(chuàng)建新的方塊*/
void RotateBlock(Block *src,Block *dest);/*轉(zhuǎn)動方塊*/
int CheckMap(int Y,int X,int mode);/*檢查地圖*/
int CheckBlock(int mode);/*檢查方塊的位置合格性*/
int IsLife();/*是不結(jié)束游戲*/
void InsertOneLineBlock(int mode);/*增加一行*/
void ReduceOneLineBlock(int mode);/*送去一行*/
void CopyBlock(int mode);/*把移動的方塊拷貝到地圖上*/
void AnotherBlock(int mode);/**/
void DelectBlock(int mode);/*檢查是否有該消去的行,*/
void Attack(struct Map_Type t,int mode);/*使用道具*/
void ChangeTool(int mode);/*道具的轉(zhuǎn)換*/
void DelectTool(int mode);/*刪除使用過的道具*/
void GameControl();/*主控程序*/
main(){
? int i;
? InitGraph();
? DrawBK();
? DrawMap(0);
? DrawMap(1);
? DrawSS(0);
? DrawSS(1);
? DrawTool(0);
? DrawTool(1);
? GameControl();
? CloseGraph();
}
void GameControl(){
? int key,count=0,i;
? CreatBlock(&AB[0]);for(i=0;i<8;i++)delay(5000);/*先創(chuàng)建要顯示的方塊,和將要顯示的方塊*/
? CreatBlock(&AB[1]);delay(5000);/**/
? CreatBlock(&AB_Next[0]);delay(5000);/**/
? CreatBlock(&AB_Next[1]);delay(5000);/**/
? DrawNextBlock(0);
? DrawNextBlock(1);/**/
? AB_X[0]=3;AB_Y[0]=-4;/*初始入方塊的位置*/
? AB_X[1]=3;AB_Y[1]=-4;/**/
? while(1){
??? while(!kbhit()){
????? DrawBlock(1,0);/*顯示方塊*/
????? DrawBlock(1,1);/**/
????? for(i=0;i<4;i++)delay(5000);/**/
????? DrawBlock(0,0);/*擦去方塊*/
????? DrawBlock(0,1);/**/
????? count++;/**/
????? if((count%(10-Speed_AB[0]))==0)AB_Y[0]++;/**/
????? if((count%(10-Speed_AB[1]))==0)AB_Y[1]++;/**/
????? if((count%((10-Speed_AB[0])*(10-Speed_AB[1])))==0)count=0;/**/
????? for(i=0;i<2;i++){/**/
?if(!CheckBlock(i)){/*如果移動方塊不合格就把下一個廣場給移動方塊*/
? AnotherBlock(i);/**/
?}
????? }
??? }
??? key=bioskey(0);/*取得按鍵值*/
??? switch(key){
????? case ESC:/**/
?CloseGraph();
?break;
????? case LEFTA:/*向左*/
?AB_X[0]--;
?if(!CheckBlock(0))AB_X[0]++;
?break;
????? case LEFTB:
?AB_X[1]--;
?if(!CheckBlock(1))AB_X[1]++;
?break;
????? case RIGHTA:/*向右*/
?AB_X[0]++;
?if(!CheckBlock(0))AB_X[0]--;
?break;
????? case RIGHTB:
?AB_X[1]++;
?if(!CheckBlock(1))AB_X[1]--;
?break;
????? case UPA:/*轉(zhuǎn)動方塊*/
?AB_Temp[0]=AB[0];
?RotateBlock(&AB[0],&AB_Temp[1]);
?AB[0]=AB_Temp[1];
?if(!CheckBlock(0))AB[0]=AB_Temp[0];
?break;
????? case UPB:
?AB_Temp[0]=AB[1];
?RotateBlock(&AB[1],&AB_Temp[1]);
?AB[1]=AB_Temp[1];
?if(!CheckBlock(1))AB[1]=AB_Temp[0];
?break;
????? case ADDOWN:/*讓方塊直接下落*/
?for(;CheckBlock(0);){
?? DrawBlock(1,0);
?? DrawBlock(0,0);
?? AB_Y[0]++;
?}
?AnotherBlock(0);
?break;
????? case BDDOWN:
?for(;CheckBlock(1);){
?? DrawBlock(1,1);
?? DrawBlock(0,1);
?? AB_Y[1]++;
?}
?AnotherBlock(1);
?break;
????? case ANUM1:/*對自己使用道具*/
?if(AB_Tool_Num[0]>0){
?? Attack(tool[0][0],0);
?? DelectTool(0);
?}
?DrawTool(0);
?DrawSS(0);
?break;
????? case BNUM1:
?if(AB_Tool_Num[1]>0){
?? Attack(tool[1][0],1);
?? DelectTool(1);
?}
?DrawTool(1);
?DrawSS(1);
?break;
????? case ANUM2:/*對對手使用道具*/
?if(AB_Tool_Num[0]>0){
?? Attack(tool[0][0],1);
?? DelectTool(0);
?}
?DrawTool(0);
?DrawSS(1);
?break;
????? case BNUM2:
?if(AB_Tool_Num[1]>0){
?? Attack(tool[1][0],0);
?? DelectTool(1);
?}
?DrawTool(1);
?DrawSS(0);
?break;
????? case ACHANG:/*道具轉(zhuǎn)換*/
?ChangeTool(0);
?break;
????? case BCHANG:
?ChangeTool(1);
?break;
??? }
??? if(IsLife()) CloseGraph();/*是不結(jié)束游戲*/
? }
}
int CheckMap(int Y,int X,int mode){
? if(X<0||X>=12||Y>22||Y<0) return 0;/*地圖是是否有方塊*/
? return map[mode][Y][X].type;
}
int CheckBlock(int mode){
? int i,j,m,n;
? for(i=3;i>=0;i--){
??? for(j=0;j<4;j++){
????? m=i+AB_Y[mode];
????? n=j+AB_X[mode];
????? if(AB[mode].d[i][j]&&(n<0||n>=12||(m==21)))return 0;/*方塊是否出了地圖外面*/
????? if(CheckMap(m+1,n,mode)&&AB[mode].d[i][j]) return 0;/*判斷下一個位置的地圖上是否有方塊是*/
??? }
? }
? return 1;
}
void DelectTool(int mode){
? int i;
? for(i=0;i<AB_Tool_Num[mode]-1;i++){
??? tool[mode][i]=tool[mode][i+1];
? }
? tool[mode][AB_Tool_Num[mode]-1].type=0;/**/
? tool[mode][AB_Tool_Num[mode]-1].num=0;
? AB_Tool_Num[mode]--;
}
void ChangeTool(int mode){
? int i;
? struct Map_Type t;
? t=tool[mode][0];
? for(i=0;i<AB_Tool_Num[mode]-1;i++){
??? tool[mode][i]=tool[mode][i+1];
? }
? tool[mode][AB_Tool_Num[mode]-1]=t;
? DrawTool(mode);
}
void Attack(struct Map_Type t,int mode){
? int i;
? switch(t.type){
??? case 2:/*增加幾行*/
????? for(i=0;i<t.num;i++){
?InsertOneLineBlock(mode);
????? }
????? break;
??? case 3:/*減去幾行*/
????? for(i=0;i<t.num;i++){
?ReduceOneLineBlock(mode);
????? }
????? break;
??? case 4:/*加速*/
????? if((Speed_AB[mode]+t.num)<=10)Speed_AB[mode]++;
????? break;
??? case 5:/*減速*/
????? if((Speed_AB[mode]-t.num)>0)Speed_AB[mode]--;
????? break;
? }
}
void DelectBlock(int mode){
? int i,j,count=0,sum=0,k=0;
? for(i=21;i>=0;i--){
??? count=0;
??? for(j=0;j<12;j++){/*檢查是否該消去*/
????? if(map[mode][i][j].type)count++;/**/
??? }
??? if(count==12){/*該消去*/
????? for(k=i;k>0;k--){
?for(j=0;j<12;j++){/*把地圖上的道具給道具數(shù)組,并往下移一行*/
?? if(map[mode][i][j].type>1&&AB_Tool_Num[mode]<12&&(k==i)){
???? tool[mode][AB_Tool_Num[mode>=map[mode][i][j];
???? AB_Tool_Num[mode]++;
??? }
?? map[mode][k][j]=map[mode][k-1][j];
?}
????? }
????? Score_AB[mode]+=12;/*加分*/
????? sum++;/*統(tǒng)計消去幾行*/
????? i++;/*使往下一行后,行坐標(biāo)仍指向這行*/
?? }
?? for(j=0;j<12;j++){
???? map[mode][0][j].type=0;
???? map[mode][0][j].num=0;
?? }
? }
? mode=1-mode;/*把操作模式變成對對方mode=0為第一玩家,mode=1為第二玩家*/
? if(sum>=3){/*如果消去3行以上就給對廣場增加一行*/
??? for(i=0;i<sum-1;i++){
????? InsertOneLineBlock(mode);
??? }
? }
? mode=1-mode;/*把操作模式轉(zhuǎn)給自己*/
? randomize();
? k=random(6);/*根據(jù)你消去的行數(shù)來設(shè)置產(chǎn)生道具的概率*/
? if(k<sum){/**/
??? do{
????? i=random(22);
????? j=random(12);
??? }while(map[mode][i][j].type!=1);
??? count=random(4)+2;/*產(chǎn)生道具類型*/
??? sum=random(3)+1;/**/
??? map[mode][i][j].type=count;/**/
??? map[mode][i][j].num=sum;
? }
? DrawMap(mode);
? DrawTool(mode);
? DrawSS(mode);
}
void AnotherBlock(int mode){
?CopyBlock(mode);
?DrawMap(mode);
?DelectBlock(mode);
?AB[mode]=AB_Next[mode];
?CreatBlock(&AB_Next[mode]);
?DrawNextBlock(mode);
?AB_X[mode]=3;/*重新定義方塊位置*/
?AB_Y[mode]=-4;/**/
}
int IsLife(){
?? int i,j;
?? for(i=0;i<2;i++){
???? for(j=0;j<12;j++){/**/
?????? if(map[i][1 ][j].type){
?????? return 1;
?????? }
???? }
?? }
?? return 0;
}
void CopyBlock(int mode){
? int i,j,m,n;
? for(i=0;i<4;i++){/*如果有方塊就拷到地圖上*/
??? for(j=0;j<4;j++){
?????? m=i+AB_Y[mode];
?????? n=j+AB_X[mode];
????? if(AB[mode].d[i][j]&&m>=0&&m<22&&n>=0&&n<12){
?map[mode][m][n].type=1;
?map[mode][m][n].num=0;
????? }
??? }
? }
}
void ReduceOneLineBlock(int mode){
? int i,j;
? for(i=21;i>0;i--){
??? for(j=0;j<12;j++){
????? map[mode][i][j]=map[mode][i-1][j];
??? }
? }
? for(j=0;j<12;j++){
??? map[mode][0][j].type=0;
??? map[mode][0][j].num=0;
? }
? DrawMap(mode);
}
void InsertOneLineBlock(int mode){
? int i,j;
? for(i=0;i<21;i++){
??? for(j=0;j<12;j++){
????? map[mode][i][j]=map[mode][i+1][j];
???? }
? }
? i=(map[mode][21][0].type>0)?1:0;
? for(j=0;j<12;j++){
??? map[mode][21][j].type=0;
??? map[mode][21][j].num=0;
? }
? for(j=i;j<12;j+=2){
??? map[mode][21][j].type=1;
??? map[mode][21][j].num=0;
? }
? DrawMap(mode);
}
void DrawBlock(int k,int mode){
? register int i,j;
? int x1,y1,x2,y2;
? for(i=0;i<4;i++){
??? for(j=0;j<4;j++){
????? x1=(AB_X[mode]+j)*12+AB_X0[mode]+1;/*算出方塊中每一個小方塊的具體坐標(biāo)*/
????? y1=(AB_Y[mode]+i)*12+21;
????? x2=x1+10;
????? y2=y1+10;
????? if(y1>20&&k&&AB[mode].d[i][j]){/*當(dāng)K=1時顯示方塊*/
?DrawPerBlock(x1,y1,x2,y2,1,0);
????? }
????? if(y1>20&&(k==0)&&AB[mode].d[i][j]){/*當(dāng)k=0時擦去方塊*/
?DrawPerBlock(x1,y1,x2,y2,0,0);
????? }
??? }
? }
}
void RotateBlock(Block *src,Block *dest){/*轉(zhuǎn)動方塊*/
? int i,j;
? for(i=0;i<4;i++){
??? for(j=0;j<4;j++){
????? dest->d[j][i]=src->d[i][3-j];
??? }
? }
}
void CreatBlock(Block *src){
? int i,j,k;
? randomize();
? k=random(7);
? for(i=0;i<4;i++){/*隨機產(chǎn)生是七種方塊中的一種*/
??? for(j=0;j<4;j++){
????? src->d[i][j]=Block_Type[k][i][j];
??? }
? }
? i=random(4);
? for(;i>0;i--,*src=AB_Temp[0]){/*隨機轉(zhuǎn)動0~3次*/
??? RotateBlock(src,&AB_Temp[0]);
? }
}
void DrawNextBlock(int mode){
? int i,j,x1,y1=20,x2,y2=78;
? x1=154+AB_X0[mode];
? x2=x1+58;
? setcolor(LIGHTCYAN);
? setfillstyle(SOLID_FILL,BLACK);
? rectangle(x1,y1,x2,y2);
? for(i=0;i<4;i++){
??? for(j=0;j<4;j++){/*算出每一個小方塊的具體坐標(biāo),并畫出*/
????? x1=j*12+160+AB_X0[mode];
????? y1=i*12+26;
????? x2=x1+10;
????? y2=y1+10;
????? DrawPerBlock(x1,y1,x2,y2,AB_Next[mode].d[i][j],0);
??? }
? }
}
void DrawTool(int mode){/*顯示道具*/
? int i,x1,y1=294,x2,y2=306;
? x1=AB_X0[mode];
? x2=x1+144;
? setcolor(GREEN);
? setfillstyle(SOLID_FILL,BLACK);
? rectangle(x1,y1,x2,y2);
? bar(x1+1,y1+1,x2-1,y2-1);
? for(i=0;i<AB_Tool_Num[mode];i++){
??? x1=i*12+1+AB_X0[mode];
??? x2=x1+10;
??? y1=295;
??? y2=305;
??? DrawPerBlock(x1,y1,x2,y2,tool[mode][i].type,tool[mode][i].num);
? }
}
void DrawSS(int mode){/*顯示分?jǐn)?shù)和速度*/
? int x1,y1,x2,y2;
? char str[6];
? setcolor(CYAN);
? setfillstyle(SOLID_FILL,BLACK);
? x1=AB_X0[mode]+154;
? x2=x1+58;
? y1=88;
? y2=136;
? rectangle(x1,y1,x2,y2);
? bar(x1+1,y1+1,x2-1,y2-1);
? setcolor(WHITE);
? outtextxy(x1+5,y1+1,"score");
? sprintf(str,"%d",Score_AB[mode]);
? outtextxy(x1+5,y1+13,str);
? outtextxy(x1+5,y1+25,"speed");
? sprintf(str,"%d",Speed_AB[mode]);
? outtextxy(x1+5,y1+37,str);
}
void DrawPerBlock(int x1,int y1,int x2,int y2,int ch,int num){
? char str[4];
? setcolor(BLACK);
? setfillstyle(SOLID_FILL,WHITE);/*產(chǎn)生立休效果*/
? bar(x1,y1,x2,y2);
? setfillstyle(SOLID_FILL,DARKGRAY);/**/
? bar(x1+1,y1+1,x2,y2);
? strcpy(str," ");
? switch(ch){
??? case 0:
????? setfillstyle(SOLID_FILL,BLACK);
????? break;
??? case 1:
????? setfillstyle(SOLID_FILL,BROWN);
????? break;
??? case 2:
????? setfillstyle(SOLID_FILL,RED);
????? sprintf(str,"%d",num);
????? break;
??? case 3:
????? setfillstyle(SOLID_FILL,BLUE);
????? sprintf(str,"%d",num);
????? break;
??? case 4:
????? setfillstyle(SOLID_FILL,LIGHTRED);
????? str[0]=0x18;/*產(chǎn)生向上方向,向上加速*/
????? break;
??? case 5:
????? setfillstyle(SOLID_FILL,LIGHTBLUE);
????? str[0]=0x19;/*產(chǎn)生向下方向,向下減速*/
????? break;
??? }
??? setcolor(WHITE);
??? bar(x1+1,y1+1,x2-1,y2-1);
??? outtextxy(x1+2,y1+2,str);
??? if(ch==0){
????? setfillstyle(SOLID_FILL,BLACK);
????? bar(x1,y1,x2,y2);
??? }
}
void DrawMap(int mode){/*顯示地圖*/
? int i,j,x1,y1=20,x2,y2=284;
? x1=AB_X0[mode];
? x2=x1+144;
? setcolor(YELLOW);
? setfillstyle(SOLID_FILL,BLACK);
? rectangle(x1,y1,x2,y2);
? for(i=0;i<22;i++){
??? for(j=0;j<12;j++){
????? x1=j*12+1+AB_X0[mode];
????? y1=i*12+21;
????? x2=x1+10;
????? y2=y1+10;
????? DrawPerBlock(x1,y1,x2,y2,map[mode][i][j].type,map[mode][i][j].num);
??? }
? }
}
void DrawBK(){/*畫背景*/
? int x1,y1,x2,y2;
? x1=getmaxx();
? x1=(getmaxx()-452)/2;
? x2=x1+452;
? y1=getmaxy();
? y1=(getmaxy()-316)/2;
? y2=y1+316;
? setbkcolor(BLACK);
? setcolor(LIGHTBLUE);
? setviewport(x1,y1,x2,y2,1);
? rectangle(0,0,452,316);
? rectangle(2,+2,450,314);
? setcolor(RED);
? outtextxy(180,6,"FIRE RUSS");
}
void InitGraph(){
? int driver,mode,x,y;
? driver=DETECT;
? registerbgidriver(EGAVGA_driver);/*把圖形驅(qū)動程序連到可執(zhí)行文件中,這樣一個文件就可以執(zhí)行了*/
? initgraph(&driver,&mode,"G://program//tc");
? x=getmaxx();
? y=getmaxy();
? if(x<317||y<452){
??? outtextxy(10,10,"The scree is too small");
??? getch();
??? CloseGraph();
? }
}
void CloseGraph(){
?? cleardevice();
?? outtextxy(50,100,"Thank you for you use this program");
?? closegraph();
?? exit(0);
}
?
?
?
總結(jié)
以上是生活随笔為你收集整理的单机版火拼俄罗斯方块源程序的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: column属性 extjs_extjs
- 下一篇: 卧槽!百度网盘 VIP 开放免费领取!亲