俄罗斯方块(JAVA实训)

import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.GridLayout;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import java.util.Random;

import javax.swing.*;

public class Lt extends JFrame implements KeyListener{
	//无参构造
	public Lt() {//按顺序写 否则会有函数失效
		initExplainPanel();//初始化说明(左右)面板
		initGamePanel();//初始化面板
		initWindow();//窗口初始化
		game_begin();		
	}
	
	public static void main(String[] args) {
           new Lt();
	}
	
/*方块左移和右移*/
	@Override
	public void keyPressed(KeyEvent e) {
		if(e.getKeyCode()==37){
            if(!isrunning){
                return;
            }
            if(game_pause){
                return;
            }
            if(y<=1){
                return;
            }
            int temp = 0x8000;
            for (int i = x; i <x+4 ; i++) {
                for (int j = y; j <y+4 ; j++) {
                    if((rect&temp)!=0){
                        if(data[i][j-1]==1){
                            return;
                        }
                    }
                    temp>>=1;
                }
            }
            //首先清除目前方块
            clear(x,y);
            y--;
            draw(x,y);
        }
        //右移
        if(e.getKeyCode()==39){
            if(!isrunning){
                return;
            }
            if(game_pause){
                return;
            }
            if(y>=(game_y-2)){
                return;
            }
            int temp = 0x8000;
            for (int i = x; i <x+4 ; i++) {
                for (int j = y; j <y+4 ; j++) {
                    if((rect&temp)!=0){
                        if(data[i][j+1]==1){
                            return;
                        }
                    }
                    temp>>=1;
                }
            }
            //首先清除目前方块
            clear(x,y);
            y++;
            draw(x,y);
        }
        if(e.getKeyCode()==40){
            if(!isrunning){
                return;
            }
            if(game_pause){
                return;
            }
            if(!canFall(x,y)){
                return;
            }
            clear(x,y);
            x++;
            draw(x,y);
        }
		
	}
/*方块左移和右移结束*/
	
	@Override
	public void keyReleased(KeyEvent e) {
		// TODO Auto-generated method stub
		
	}
/*游戏暂停和方块变形*/
	int pause_times=0;
    boolean game_pause=false;
    @Override
    public void keyTyped(KeyEvent e) {
        //控制游戏暂停
        if(e.getKeyChar()=='p'){
            if(!isrunning){
                return;
            }
            pause_times++;
            //暂停
            if(pause_times==1){
                game_pause=true;
                label1.setText("游戏状态:暂停中!");
            }
            //继续
            if(pause_times==2){
                game_pause=false;
                pause_times=0;
                label1.setText("游戏状态:正在进行中!");
            }
        }
        //控制方块变形
        if(e.getKeyChar()==KeyEvent.VK_SPACE){
            if(!isrunning){
                return;
            }
            //判断游戏是否暂停
            if(game_pause){
                return;
            }
            //定义变量  存储目前方块的索引
            int old;
            for (old = 0; old <allRect.length ; old++) {
                //判断是否是当前方块
                if(rect==allRect[old]){
                    break;
                }
            }
            //定义变量存储变形后方块
            int next;
            //判断是方块
            if(old==0){
                return;
            }
            //清除当前方块
            clear(x,y);
            if (old == 1 || old == 2) {
                next = allRect[old == 1 ? 2 : 1];

                if (canTurn(next,x,y)) {
                    rect = next;
                }
            }

            if (old >= 3 && old <= 6) {
                next = allRect[old + 1 > 6 ? 3 : old + 1];

                if (canTurn(next,x,y)) {
                    rect = next;
                }
            }
            if (old >= 9 && old <= 12) {
                next = allRect[old + 1 > 12 ? 9 : old + 1];

                if (canTurn(next,x,y)) {
                    rect = next;
                }
            }

            if (old == 7 || old == 8) {
                next = allRect[old == 7 ? 8 : 7];

                if (canTurn(next,x,y)) {
                    rect = next;
                }
            }
            if (old == 13 || old == 14) {
                next = allRect[old == 13 ? 14 : 13];

                if (canTurn(next,x,y)) {
                    rect = next;
                }
            }

            if (old >= 15 && old <= 18) {
                next = allRect[old + 1 > 18 ? 15 : old + 1];

                if (canTurn(next,x,y)) {
                    rect = next;
                }
            }
            //重新绘制变形后方块
            draw(x,y);
        }
    }
    
    public boolean canTurn(int a,int m,int n){
        int temp = 0x8000;
        for (int i = 0; i <4 ; i++) {
            for (int j = 0; j <4 ; j++) {
                if((a&temp)!=0){
                    if(data[m][n]==1){
                        return false;
                    }
                }
                n++;
                temp>>=1;
            }
            m++;
            n=n-4;
        }
        return true;
    }
/*游戏暂停和方块变形结束*/
      
/*创建游戏界面*/
	private static final int game_x = 26;
	private static final int game_y = 12;
	JTextArea[][] text = new JTextArea[game_x][game_y];//文本域数组 每一个文本域对象相当于一个小方格子
	int[][] data = new int[game_x][game_y];	//二维数组 填充面板的 0 1
/*创建游戏界面结束*/	

/*编写刷新界面的方法*/   
	public void reflesh(int row){//刷新移除某一行后的游戏界面
    for (int i=row;i>=1;i--){
        for(int j=1;j<=(game_y-2);j++){
        //进行覆盖
        if(data[i][j]==1){
                 text[i][j].setBackground(Color.BLUE);
           }else{
                 text[i][j].setBackground(Color.white);
          }
        }
      }
   }
/*编写刷新界面的方法*/ 

/*编写消除行的方法*/
    int score=0;
    //移除某一行的所有方块,令以上方块掉落
    public void removeRow(int row){
    int temp = 100;
     for (int i=row;i>=1;i--){
    	for(int j=1;j<=(game_y-2);j++){
    	//进行覆盖
    	data[i][j] = data[i-1][j];
    	    }
    	}
    	//刷新游戏区域
    	 reflesh(row);
    	 score+=temp;
    	label.setText("游戏得分:"+score);
}
/*编写消除行的方法*/ 
    
/*改变不可下降方块区域值*/ 
    public void changData(int m,int n){
    	int temp = 0x8000;
    	for (int i = 0; i <4 ; i++) {
    	    for (int j = 0; j <4 ; j++) {
    	         if((temp&rect)!=0){
    	             data[m][n]=1;
    	          }
    	       n++;
    	       temp>>=1;
    	     }
    	   m++;
    	   n=n-4;
    	}
   }
/*改变不可下降方块区域值结束*/ 
    
/*判断方块是否可以继续下落*/
    public boolean canFall(int m,int n){
    //定义一个变量
    int temp = 0x8000;
    //遍历4*4方格
    for (int i = 0; i <4 ; i++) {
       for (int j = 0; j <4 ; j++) {
         if((temp&rect)!=0){
    //判断该位置的下一行是否有方块
          if(data[m+1][n]==1){
             return false;
          }
        }
      n++;
      temp>>=1;
     }
   m++;
   n=n-4;
  }
 return true;
}
/*判断方块是否可以继续下落结束*/

/*编写下落方法*/    
  //下落方法
    public void fall(int m,int n){
       if(m>0){
       clear(m-1,n);
     }
    //重新绘制方块
    draw(m,n);
}
    //清除方块掉落后,上一层有颜色的地方
    public void clear(int m,int n){
     int temp = 0x8000;
     for (int i = 0; i <4 ; i++) {
         for (int j = 0; j <4 ; j++) {
             if((temp&rect)!=0){
                 text[m][n].setBackground(Color.WHITE);
             }
          n++;
          temp>>=1;
          }
       m++;
       n=n-4;
      }
}
    //绘制
    public void draw(int m,int n){
    int temp = 0x8000;
    for (int i = 0; i <4 ; i++) {
        for (int j = 0; j <4 ; j++) {
            if((temp&rect)!=0){
            text[m][n].setBackground(Color.BLUE);
            }
          n++;
          temp>>=1;
         }
      m++;
      n=n-4;
     }
   }
/*编写下落方法结束*/
    
/*创建游戏运行方法*/   
  //运行游戏
    int x;
    int y;
    //设置睡眠时间
    int time=300;
    public void game_run(){
    Random random= new Random();
    //产生随机数 产生随机方块
      rect = allRect[random.nextInt(19)];
    //方块下落位置
     x=0;
     y=5;
    for (int i = 0; i <game_x ; i++) {
        try {
        Thread.sleep(time);
         //判断是否可以下落
         if(!canFall(x,y)){
         //将data置为1,表示有方块占用
             changData(x,y);
             //循环遍历4层,看是否有行可以消除
              for (int j = x; j <x+4 ; j++) {
                   int sum = 0;
                      for (int k = 1; k <=(game_y-2) ; k++) {
                           if(data[j][k]==1){
                           sum++;
                          }
                      }
    //判断是否有一行可以被消除
                if(sum==(game_y-2)){
    //消除j这一行
    	        removeRow(j);
           }
    }
    //判断游戏是否失败
    for (int j = 1; j <=(game_y-2) ; j++) {
         if(data[3][j]==1){
           isrunning=false;
           break;
         }
     }
         break;
    }else{
            x++;
            fall(x,y);
         }
    } catch (InterruptedException e) {
                e.printStackTrace();
             }
        }
    }
/*创建游戏运行方法结束*/    

/*开始游戏*/    
    //创建存放方块的数组
    boolean isrunning = true;
	int[] allRect = new int[]{
			0x00cc,0x8888,0x000f,0x044c,
			0x008e,0x0c88,0x00e2,0x00c6,
		    0x04c8,0x004e,0x04c4,0x00e4,
		    0x08c8,0x006c,0x08c4,0x088c,
		    0x00e8,0x0c44,0x002e,0x8888,
		    0x000f,0x008f,0x888a,0x444a,
		    0x001f
    };
	//存放当前方块的变量
	int rect;
	//开始游戏的方法
	public void game_begin(){
    while(true){
    //判断游戏是否结束
    if(!isrunning){
    break;
    }
    //进行游戏
    game_run();
    }
    label1.setText("游戏状态:游戏结束!");
}
/*开始游戏结束*/

/*初始化说明面板*/	
	//显示游戏状态
	JLabel label1=new JLabel("游戏状态:正在游戏");
	//显示游戏分数
	JLabel label =new JLabel("游戏分数:0");
	//初始化游戏说明面板
	public void initExplainPanel(){
		//创建游戏的左面板
		JPanel left = new JPanel();
		//创建游戏的右面板
		JPanel right = new JPanel();
		//设置行列
		left.setLayout(new GridLayout(4,1));
		right.setLayout(new GridLayout(2,1));
		//左面板添加说明文字
		left.add(new JLabel("按空格键,方块变形"));
		left.add(new JLabel("按左箭头,方块左移"));
		left.add(new JLabel("按右箭头,方块右移"));
		left.add(new JLabel("按下箭头,方块下落"));
		//设置标签内容为红色字体
		label1.setForeground(Color.red);
		//右面板添加状态和分数
		right.add(label);
		right.add(label1);
		//将左面板添加到窗口的左侧
		this.add(left,BorderLayout.WEST);
		this.add(right,BorderLayout.EAST);
	}
/*初始化说明面板结束*/
	
/*窗口初始化操作*/
	public void initWindow() {
	    	//设置窗口大小
	    	this.setSize(600,850);
	    	//设置窗口是否可见
	    	this.setVisible(true);
	    	//设置窗口居中
	    	this.setLocationRelativeTo(null);
	    	//设置释放窗体
	    	this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
	    	//设置窗口大小不可变
	    	this.setResizable(false);
	    	//设置标题
	    	this.setTitle("俄罗斯方块");      	
	}
/*窗口初始化操作结束*/

/*创建游戏面板*/
	public void initGamePanel() {
    	JPanel game_main = new JPanel();
    	game_main.setLayout(new GridLayout(game_x,game_y,1,1));
    	//初始化面板
    	for (int i = 0; i <text.length ; i++) {
    		for (int j = 0; j <text[i].length ; j++) {
		    		//设置文本域的对象
		    		text[i][j] = new JTextArea();
		    		//设置文本域的背景颜色
		    		text[i][j].setBackground(Color.WHITE);
		    		//设置键盘监听事件
		    		text[i][j].addKeyListener(this);
		    		//初始化游戏边界
		    		if(j==0||j==text[i].length-1||i==text.length-1){
			    		text[i][j].setBackground(Color.CYAN);
			    		data[i][j]=1;
		  			}
		    		//设置文本域不可编辑
		    		text[i][j].setEditable(false);
		    		//文本区域添加到主面板上
		    		game_main.add(text[i][j]);
		   	}
  		}
   		//添加到窗口中
   		this.add(game_main,BorderLayout.CENTER);
	}
/*创建游戏面板结束*/
}
  • 0
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值