import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
import java.awt.image.*;
class Bzw{
int column;
int row;
int color;
Bzw(int column,int row,int color){
this.column=column;
this.row=row;
this.color=color;
}
boolean InBounds(){
return(column>=0&&column<D.cols&&
row>=0&&row<D.rows+4);
}
boolean IsEqual(Bzw s){
return (column==s.column)&&(row==s.row)&&(color==s.color);
}
}
public class D extends JFrame implements Runnable{
private static final long serialVersionUID = 1L;
static int sqlength;
static final int xoffset=150;
static int cols;
static int rows;
int field[][];
int oldField[][];
Bzw curPiece[]=new Bzw[4];
boolean gameInPlay;
boolean needNewPiece;
Thread theThread=null;
Color colors[];
int theScore=0;
int playLevel;
int totalPieces;
boolean moveBzws(Bzw from[],Bzw to[]){
outerlabel:
for(int i=0;i<to.length;i++){
if(to[i].InBounds()==false) return false;
if(field[to[i].column][to[i].row]!=0){
for(int j=0;j<from.length;j++)
if(to[i].IsEqual(from[j]))
continue outerlabel;
return false;
}
}
for(int i=0;i<from.length;i++)
if(from[i].InBounds())
field[from[i].column][from[i].row]=0;
for(int i=0;i<to.length;i++)
field[to[i].column][to[i].row]=to[i].color;
return true;
}
void newPiece(){
Bzw old[]=new Bzw[4];
old[0]=old[1]=old[2]=old[3]=new Bzw(-1,-1,0);
int middle=cols/2;
int top=rows;
switch((int)(Math.random()*7)){
case 0:
curPiece[0]=new Bzw(middle-1,top-1,1);
curPiece[1]=new Bzw(middle-2,top-1,1);
curPiece[2]=new Bzw(middle,top-1,1);
curPiece[3]=new Bzw(middle+1,top-1,1);
break;
case 1:
curPiece[0]=new Bzw(middle,top-2,5);
curPiece[1]=new Bzw(middle,top-1,5);
curPiece[2]=new Bzw(middle-1,top-2,5);
curPiece[3]=new Bzw(middle+1,top-2,5);
break;
case 2:
curPiece[0]=new Bzw(middle,top-2,2);
curPiece[1]=new Bzw(middle-1,top-1,2);
curPiece[2]=new Bzw(middle,top-1,2);
curPiece[3]=new Bzw(middle+1,top-2,2);
break;
case 3:
curPiece[0]=new Bzw(middle,top-2,7);
curPiece[1]=new Bzw(middle+1,top-1,7);
curPiece[2]=new Bzw(middle,top-1,7);
curPiece[3]=new Bzw(middle-1,top-2,7);
break;
case 4:
curPiece[0]=new Bzw(middle-1,top-1,3);
curPiece[1]=new Bzw(middle,top-1,3);
curPiece[2]=new Bzw(middle-1,top-2,3);
curPiece[3]=new Bzw(middle,top-2,3);
break;
case 5:
curPiece[0]=new Bzw(middle,top-1,6);
curPiece[1]=new Bzw(middle-1,top-1,6);
curPiece[2]=new Bzw(middle+1,top-1,6);
curPiece[3]=new Bzw(middle+1,top-2,6);
break;
case 6:
curPiece[0]=new Bzw(middle,top-1,4);
curPiece[1]=new Bzw(middle+1,top-1,4);
curPiece[2]=new Bzw(middle-1,top-1,4);
curPiece[3]=new Bzw(middle-1,top-2,4);
break;
}
gameInPlay=moveBzws(old, curPiece);
}
private synchronized boolean movecurPiece(int byx,int byy,boolean rotate)
{
Bzw newpos[]=new Bzw[4];
for(int i=0;i<4;i++){
if(rotate){
int dx=curPiece[i].column-curPiece[0].column;
int dy=curPiece[i].row-curPiece[0].row;
newpos[i]=new Bzw(curPiece[0].column-dy,
curPiece[0].row+dx,curPiece[i].color);
}else{
newpos[i]=new Bzw(curPiece[i].column+byx,
curPiece[i].row+byy, curPiece[i].color);
}
}
if(moveBzws(curPiece,newpos)==false) return false;
curPiece=newpos;
return true;
}
void removelines(){
outerlabel:
for(int j=0;j<rows;j++){
for(int i=0;i<cols;i++)
if(field[i][j]==0)
continue outerlabel;
for(int k=j;k<rows-1;k++)
for(int i=0;i<cols;i++)
field[i][k]=field[i][k+1];
theScore+=100;
totalPieces+=1;
playLevel=0+totalPieces/10;
j-=1;
}
}
public D(){
setBackground(Color.GRAY);
sqlength=20;
cols=10;
rows=19;
addKeyListener(new MykeyListener());
requestFocus();
field=new int[cols][rows+4];
oldField=new int[cols][rows+4];
colors=new Color[8];
colors[0]=new Color(40,40,40);
colors[1]=new Color(255,0,0);
colors[2]=new Color(0,200,0);
colors[3]=new Color(0,200,255);
colors[4]=new Color(255,255,0);
colors[5]=new Color(255,150,0);
colors[6]=new Color(210,0,240);
colors[7]=new Color(40,0,240);
}
public void start(){
for(int i=0;i<cols;i++){
for(int j=0;j<rows+4;j++){
field[i][j]=0;
oldField[i][j]=-1;
}
}
playLevel=0;
theScore=0;
totalPieces=0;
needNewPiece=true;
gameInPlay=true;
theThread=new Thread(this);
theThread.start();
requestFocus();
}
public synchronized void stop(){
if(theThread!=null)
theThread=null;
}
static int delay_map[]={
600,600,600,600,500,400,300,250,200,150,100};
public void run(){
while(gameInPlay){
try{
int t;
if(playLevel>10) t=75;
else t=delay_map[playLevel];
Thread.sleep(t);
}catch(InterruptedException e) {}
if(needNewPiece){
removelines();
newPiece();
needNewPiece=false;
}else{
needNewPiece=!movecurPiece(0,-1,false);
}
repaint();
}
theThread=null;
}
class MykeyListener implements KeyListener{
public void keyPressed(KeyEvent evt){
int key=evt.getKeyCode();
switch(key){
case KeyEvent .VK_ENTER :
stop();
start();
break;
case KeyEvent.VK_Q:
stop();
System.exit(0);
break;
case KeyEvent.VK_A :
case KeyEvent.VK_LEFT:
movecurPiece(-1,0,false);
needNewPiece=false;
repaint();
break;
case KeyEvent.VK_D :
case KeyEvent.VK_RIGHT:
movecurPiece(1,0,false);
needNewPiece=false;
repaint();
break;
case KeyEvent.VK_W :
case KeyEvent.VK_SPACE :
movecurPiece(0,0,true);
repaint();
break;
case KeyEvent.VK_S :
case KeyEvent.VK_DOWN:
while(movecurPiece(0,-1,false))
repaint();
break;
}
}
public void keyReleased(KeyEvent e){
}
public void keyTyped(KeyEvent e){}
}
public synchronized void paint(Graphics g1){
BufferedImage bu=new BufferedImage(getSize().width,getSize().height,
BufferedImage.TYPE_INT_ARGB);
Graphics2D g=bu.createGraphics();
g.setFont(new Font("helvetica",0,18));
int gx=sqlength;
int gy=sqlength*rows/4;
g.setColor(Color.GRAY);
g.fillRect(0,0,120,400);
g.setColor(Color.white);
g.drawString("目前的分数:"+theScore,gx-20,gy);
gy+=40;
g.drawString("目前的等级:"+playLevel,gx-20,gy);
g.drawString("开始键按 Enter",gx-10,430);
g.drawString("退出键按 Q",gx+160,430);
g.drawString(" 变换键按 空格 " ,gx+300,430 );
for(int i=0;i<cols;i++)
for(int j=0;j<rows;j++){
if(
oldField[i][rows-1-j]==-1||
oldField[i][rows-1-j]!=field[i][rows-1-j]){
g.setColor(colors[field[i][rows-1-j]]);
g.fill3DRect(
xoffset+sqlength*i,
sqlength+sqlength*j,
sqlength,sqlength,true);
}
oldField[i][rows-1-j]=field[i][rows-1-j];
}
g1.drawImage(bu,0,0,this);
}
public static void main(String args[]){
D aa=new D();
aa.addWindowListener(new WindowAdapter(){
public void windowClosing(WindowEvent e){
System.exit(0);
}
});
aa.setTitle("白贞伟_俄罗斯方块游戏");
aa.setSize(500,830);
aa.setResizable(false);
aa.setVisible(true);
aa.start();
}
}