java 实现的小游戏——俄罗斯方块

分析规则、搭建框架:

类名

作用

Grid

单位小方格的属性和操作

GridController

组合方格的属性和操作

RulesController

控制一系列的游戏规则和操作

Test

入口

设计操作方式

按键

作用

按键

作用

P

暂停

左移一格

C

继续

右移一格

旋转

空格

直降到底

下移一格

S

重新开始

 设计界面元素

 

 

背景音乐:先輩、優しくするならちゃんと最後まで優しくしてください

方块消除音效:Technology Electronic Button Beep Digital Camera 04

注:音效下载地址 (这里面有非常多的音效 免费下载 很棒)

类和方法:

Grid

属性名

描述

row

小方格所在行

col

小方格所在列

image

小方格对应样式图片

 

方法名

描述

Grid(int row, int col, Image image)

构造函数

getRow()

获取行

setRow()

设置行

getCol()

获取列

setCol()

设置列

getImage()

获取图形

moveRight()

右移1格

moveLeft()

左移1格

moveDown()

下降1格

 

GridController

属性名

描述

grids[]

四个小方格构成的组合

State[]

旋转状态

 

方法名

描述

randomTetris()

随机生成方块

getGrids()

返回组合方块

softDrop()

组合方块下降一格

moveRight()

组合方块右移一格

moveLeft()

组合方块左移一格

spinRight()

组合方块向右旋转

spinLeft()

组合方块向左旋转

 

内部类名

描述

State

记录旋转状态

Yellow

黄色组合方格

Orangish

橘色组合方格

Cyan

深蓝组合方格

Gray

深灰色组合方格

Green

绿色组合方格

Blue

蓝色组合方格

Red

红色组合方格

 

RulesControllers

属性名

描述

ROWS

游戏区高20格子

COLS

游戏区宽10个格子

CELL_SIZE

单位小格子边长41

mound[][]

下方已落下的方块

ingGrids

正在下落的方块

nextGrids

下一个下落方块

lines

已消除的行数

score

分数

background

背景图片

Orangish

单位小格子图片

Gray

单位小格子图片

Cyan

单位小格子图片

Green

单位小格子图片

Blue

单位小格子图片

Red

单位小格子图片

Yellow

单位小格子图片

pause

是否暂停

gameOver

游戏是否结束

timer

计时器

FONT_COLOR

右边文字区域文字颜色

FONT_SIZE

右边文字区域字号

gridsCanDrop()

判断能不能继续落下

 

方法名

描述

checkGameOver()

判断游戏是否结束

startAction()

重新开始/游戏就绪

action()

控制游戏进行

paint()

绘制一系列呈现的内容

outOfBound()

判断是否碰到了边界

isCoincide()

判断是否碰到了其他格子

slowlyDropAction()

下移

moveRightAction()

右移

moveLeftAction()

左移

spinRightAction()

向右旋转

spinLeftAction()

向左旋转

directlyDropAction()

直接下落到底

gridLandToWall()

落到下面

destroyLines()

消除一行并积分

Music1()

播放消除一行并得分的音效

Music2()

播放背景音乐

实现代码:

Grid类:

package Tetris;
import java.awt.Image;

public class Grid {
	
	private int row;  //行
	private int col;   //列
	private Image image;   //格子的图
	
	public Grid(int row, int col, Image image) {   //构造函数 行 列  贴图 确定一个格子
		super();
		this.row = row;
		this.col = col;
		this.image = image;
	}
	
	//下面是获取和设置行列贴图
	public int getRow() {
		return row;
	}

	public void setRow(int row) {
		this.row = row;
	}

	public int getCol() {
		return col;
	}

	public void setCol(int col) {
		this.col = col;
	}
	
	
	public Image getImage() {
		return image;
	}

	public void setImage(Image image) {
		this.image = image;
	}

	//下面是一系列移动方式
	public void moveRight(){
		col++;
	}
	
	public void moveLeft(){
		col--;
	}
	
	public void moveDown(){
		row++;
	}
	
	@Override
	public String toString() {
		return "["+row+","+col+"]";
	}


}

GridController类:

package Tetris;

import java.util.Arrays;
import java.util.Random;



public class GridController {
	
	protected class State{     //内部类  用于记录旋转的状态
		int row0,col0,row1,col1,row2,col2,row3,col3;
		public State(int row0, int col0, int row1, int col1,
				int row2, int col2,
				int row3, int col3) {
			this.row0 = row0;
			this.col0 = col0;
			this.row1 = row1;
			this.col1 = col1;
			this.row2 = row2;
			this.col2 = col2;
			this.row3 = row3;
			this.col3 = col3;
		}	  
	}
	
	protected Grid[] grids = new Grid[4];
	protected State[] states;  //保存旋转的相对于轴位置状态
	
	
	public static GridController randomTetris(){  //随机生成方块
		Random r = new Random();
		int type = r.nextInt(7);
		switch(type){
		case 0: return new Yellow();
		case 1: return new Orangish();
		case 2: return new Gray();
		case 3: return new Cyan();
		case 4: return new Red();
		case 5: return new Green();
		case 6: return new Blue();
		}
		return null;
	}
	
	
	public Grid[] getGrids() {
		return grids;
	}
	
	
	//以下 下落左移右移
	public void softDrop(){       //下落
		for(int i=0; i<grids.length; i++){
			grids[i].moveDown();
		}
	}
	public void moveRight(){
		for(int i=0; i<grids.length; i++){
			this.grids[i].moveRight();
		}
	} 
	public void moveLeft(){
		for(int i=0; i<grids.length; i++){
			grids[i].moveLeft();
		}
	}
	
	private int index=100000;
	
	public void spinRight() {
		index++;
		State s = states[index%states.length];//s1
		Grid o = grids[0];//获取当前的轴
		//轴与相对位置的和作为旋转以后的格子位置
		grids[1].setRow(o.getRow()+s.row1);
		grids[1].setCol(o.getCol()+s.col1);
		grids[2].setRow(o.getRow()+s.row2);
		grids[2].setCol(o.getCol()+s.col2);
		grids[3].setRow(o.getRow()+s.row3);
		grids[3].setCol(o.getCol()+s.col3);
	}
	
	public void spinLeft() {
		index--;//index = 10001
		// index % states.length = 10001 % 4 = 1
		State s = states[index%states.length];//s1
		// [0] + s1 = [1]
		Grid o = grids[0];//获取当前的轴
		grids[1].setRow(o.getRow()+s.row1);
		grids[1].setCol(o.getCol()+s.col1);
		grids[2].setRow(o.getRow()+s.row2);
		grids[2].setCol(o.getCol()+s.col2);
		grids[3].setRow(o.getRow()+s.row3);
		grids[3].setCol(o.getCol()+s.col3);
	}
	
	@Override
	public String toString() {
		return Arrays.toString(grids); 
	}
	

}




class Yellow extends GridController{
	public Yellow() {
		grids[0] = new Grid(0, 4, RulesController.Yellow);
		grids[1] = new Grid(0, 3, RulesController.Yellow);
		grids[2] = new Grid(0, 5, RulesController.Yellow);
		grids[3] = new Grid(1, 4, RulesController.Yellow);
		states = new State[]{
				new State(0,0, 0,-1, 0,1, 1, 0),
				new State(0,0, -1,0, 1,0, 0,-1),
				new State(0,0, 0,1,  0,-1, -1,0),
				new State(0,0, 1,0, -1,0, 0,1)};
	}
}
class Orangish extends GridController{
	public Orangish() {
		grids[0] = new Grid(0, 4, RulesController.Orangish);
		grids[1] = new Grid(0, 3, RulesController.Orangish);
		grids[2] = new Grid(0, 5, RulesController.Orangish);
		grids[3] = new Grid(0, 6, RulesController.Orangish);
		states = new State[]{
				new State(0,0, 0,1, 0,-1, 0,-2),
				new State(0,0, -1,0, 1,0,2,0)};
	}
}
class Cyan extends GridController{
	public Cyan() {
		grids[0] = new Grid(0, 4,RulesController.Cyan);
		grids[1] = new Grid(0, 3,RulesController.Cyan);
		grids[2] = new Grid(0, 5, RulesController.Cyan);
		grids[3] = new Grid(1, 3,RulesController.Cyan);
		states = new State[]{
				new State(0,0, 0,-1, 0,1, 1,-1 ),
				new State(0,0, -1,0, 1,0, -1,-1),
				new State(0,0, 0,1, 0,-1, -1,1),
				new State(0,0, 1,0, -1,0, 1,1)};	
	}
}

class Gray extends GridController{
	public Gray() {
		grids[0] = new Grid(0, 4, RulesController.Gray);
		grids[1] = new Grid(0, 3, RulesController.Gray);
		grids[2] = new Grid(0, 5, RulesController.Gray);
		grids[3] = new Grid(1, 5, RulesController.Gray);
		states = new State[]{
				new State(0,0, 0,-1, 0,1, 1,1),
				new State(0,0, -1,0, 1,0, 1,-1),
				new State(0,0, 0,1, 0,-1, -1,-1),
				new State(0,0, 1,0, -1,0, -1,1 )};
	}
}

class Green extends GridController{
	public Green() {
		grids[0] = new Grid(0, 4, RulesController.Green);
		grids[1] = new Grid(0, 5, RulesController.Green);
		grids[2] = new Grid(1, 3, RulesController.Green);
		grids[3] = new Grid(1, 4, RulesController.Green);
		states = new State[]{
			new State(0,0, 0,1, 1,-1, 1,0 ),
			new State(0,0, -1,0, 1,1, 0,1 )};
	}
}

class Blue extends GridController{
	public Blue() {
		grids[0] = new Grid(1, 4, RulesController.Blue);
		grids[1] = new Grid(0, 3, RulesController.Blue);
		grids[2] = new Grid(0, 4, RulesController.Blue);
		grids[3] = new Grid(1, 5, RulesController.Blue);
		states = new State[]{
				new State(0,0, -1,-1, -1,0, 0,1 ),
				new State(0,0, -1,1, 0,1, 1,0 )};
	}
}

class Red extends GridController {
	public Red() {
		grids[0] = new Grid(0, 4, RulesController.Red);
		grids[1] = new Grid(0, 5, RulesController.Red);
		grids[2] = new Grid(1, 4, RulesController.Red);
		grids[3] = new Grid(1, 5, RulesController.Red);
		states = new State[]{
				new State(0,0, 0,1, 1,0, 1,1 ),
				new State(0,0, 0,1, 1,0, 1,1 )};
	}
	
}


RulesController类:

package Tetris;


import java.applet.Applet;
import java.applet.AudioClip;
import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.Image;
import java.awt.event.KeyAdapter;
import java.awt.event.KeyEvent;
import java.io.File;
import java.net.URI;
import java.net.URL;
import java.util.Arrays;
import java.util.Timer;
import java.util.TimerTask;
import javax.imageio.ImageIO;
import javax.swing.JPanel;

public class RulesController extends JPanel {
	public static final int ROWS=20;  //游戏区高20个格子
	public static final int COLS=10;  //游戏区宽10个格子
	public static final int CELL_SIZE = 41;  //一方格的边长
	private Grid[][] mound = new Grid[ROWS][COLS];    //存落下的方块
	private GridController ingGrids;    //正在下落的方块
	private GridController nextGrids;   //下一个下落的方块
	private int lines; //消掉的行数
	private int score ;//得分
	
	private static Image background;//背景图片
	
	public static Image Orangish;
	public static Image Gray;
	public static Image Cyan;
	public static Image Green;
	public static Image Blue;
	public static Image Red;
	public static Image Yellow;
	

	static {     //加载图片
		try {
			background = ImageIO.read(
					RulesController.class.getResource("tetris3.png"));
				Yellow=ImageIO.read(RulesController.class.getResource("Yellow.png"));
				Orangish=ImageIO.read(RulesController.class.getResource("Orangish.png"));
				Green=ImageIO.read(RulesController.class.getResource("Green.png"));
				Blue=ImageIO.read(RulesController.class.getResource("Blue.png"));
				Cyan=ImageIO.read(RulesController.class.getResource("Cyan.png"));
				Gray=ImageIO.read(RulesController.class.getResource("Gray.png"));
				Red=ImageIO.read(RulesController.class.getResource("Red.png"));
		}catch(Exception e){
			e.printStackTrace();
		}
	}
	
	
	/************************
	 * 下面搞 控制游戏开始结束暂停继续
	 * **********************/
	
	private boolean pause;   //布尔变量pause表示是否暂停
	private boolean gameOver;  //布尔变量gameOver表示游戏是否结束
	private Timer timer;
	
	public void checkGameOver(){  //判断游戏是否该结束了
		if(mound[0][4]==null){
			return;
		}
		gameOver = true;
		timer.cancel();
		repaint();// 重绘此组件
	}
	
	
	public void startAction(){   //重新开始 开始前就绪
		for(int row=0; row<ROWS; row++){
			Arrays.fill(mound[row], null);
		}
		ingGrids = GridController.randomTetris();
		nextGrids = GridController.randomTetris();
		lines = 0; score = 0;	
		pause=false; gameOver=false;
		timer = new Timer();
		timer.schedule(new TimerTask(){
			public void run() {
				slowlyDropAction();   //下降
				repaint();
			}
		}, 700, 700);
	}
	
	
	public void action(){    //开始
		startAction();
		repaint();
         Music2();
		KeyAdapter l = new KeyAdapter() {
			public void keyPressed(KeyEvent e) {
				int key = e.getKeyCode();
				if(key == KeyEvent.VK_Q){    //按下Q退出
					System.exit(0);//退出当前的Java进程
				}
				if(gameOver){
					if(key==KeyEvent.VK_S){     //如果结束了 按S重新开始
						startAction();
					}
					return;
				}
				
				//如果暂停并且按键是[C]就继续动作
				if(pause){//pause = false
					if(key==KeyEvent.VK_C)
					{	
						timer = new Timer();
						timer.schedule(new TimerTask() {
							public void run() {
								slowlyDropAction();
								repaint();
							}
						}, 700, 700);  //每700执行700
						pause = false;
						repaint();
					}
					return;
				}
				
				//否则处理其它按键
				switch(key){
				case KeyEvent.VK_RIGHT: moveRightAction(); break;  //右
				case KeyEvent.VK_LEFT: moveLeftAction(); break;    //左
				case KeyEvent.VK_DOWN: slowlyDropAction() ; break;     //下
				case KeyEvent.VK_UP: spinRightAction() ; break;    //转
				case KeyEvent.VK_SPACE: directlyDropAction() ; break;     //直接下到底

				case KeyEvent.VK_P:   //P暂停
					{
						timer.cancel(); //停止定时器
						pause = true;
						repaint();
					}; break;
				}
				repaint();
			}
		};
		
		this.requestFocus();
		this.addKeyListener(l);
	}
	
	
	
     /***********************
      * 搞一系列呈现的内容
      * *********************/
	
	public static final int FONT_COLOR = 0x2F4F2F;  //字体颜色
	public static final int FONT_SIZE = 0x20;  //字号
	
	
	
	public void paint(Graphics g){
		g.drawImage(background, 0, 0, null);//使用this 作为观察者
		g.translate(20, 20);//平移绘图坐标系
		
        //绘制正在下落的方块
		Grid[] cells = ingGrids.getGrids();
		for(int i=0; i<cells.length; i++){
			Grid c = cells[i];
			int x = c.getCol() * CELL_SIZE-1;
			int y = c.getRow() * CELL_SIZE-1;
			g.drawImage(c.getImage(), x, y, null);
		}		
		//画墙
		for(int row=0; row<mound.length; row++){
			Grid[] line = mound[row];
			for(int col=0; col<line.length; col++){
				Grid cell = line[col]; 
				int x = col*CELL_SIZE; 
				int y = row*CELL_SIZE;
				if(cell==null){
				}else{
					g.drawImage(cell.getImage(), x-1, y-1, null);
				}
			}
		}
		
		// 画即将下落的方块
		Grid[] cells1 = nextGrids.getGrids();
		for(int i=0; i<cells1.length; i++){
			Grid c = cells1[i];
			int x = (c.getCol()+10) * CELL_SIZE-1;
			int y = (c.getRow()+1) * CELL_SIZE-1;
			g.drawImage(c.getImage(), x-60, y+50, null);
		}	
		
		// 右边的文字提示区
		Font f = getFont();//获取当前的 面板默认字体
		Font font = new Font(
				f.getName(), Font.BOLD, FONT_SIZE);
		int x = 450;
		int y = 300;
		
		g.setColor(new Color(FONT_COLOR));
		g.setFont(font);
		String str = "分数:"+this.score;
		g.drawString(str, x, y);
		y+=56;
		str = "已消除:"+this.lines+"行";
		g.drawString(str, x, y);
		y+=56;
		
		str = "下一个:";
		g.drawString(str, 433, 59);
		y+=15;
		str = "操作方法:";
		g.drawString(str, x, y);
		y+=56;
		str = "[↑]:旋转";
		g.drawString(str, x, y);
		y+=56;
		str = "[←]:左移";
		g.drawString(str, x, y);
		y+=56;
		str = "[→]:右移";
		g.drawString(str, x, y);
		y+=56;
		str = "[空格]:落底";
		g.drawString(str, x, y);
		y+=56;
		str = "[P]暂停";
		if(pause){str = "[C]继续";}         //布尔变量pause:是否暂停 
		if(gameOver){	str = "[S]重新开始";}     // 布尔变量gameOver:是否结束
		g.drawString(str, x, y);
	}
	
	
	
	/****************************
	 * 下面搞游戏区方块的各种运动
	 ****************************/
	
	private boolean outOfBound(){    //判断碰到了边界
		Grid[] grids = ingGrids.getGrids();
		for(int i=0; i<grids.length; i++){
			Grid grid = grids[i];
			int col = grid.getCol();
			if(col<0 || col>=COLS){
				return true;//出界了
			}
		}
		return false;
	}
	

	private boolean isCoincide(){   //判断 碰到了其他格子
		Grid[] grids = ingGrids.getGrids();
		//for each 循环、迭代,简化了"数组迭代书写"
		//Java 5 以后提供增强版for循环  :for (循环变量类型 循环变量名称 : 要被遍历的对象) 循环体
		for(Grid grid: grids){
			int row = grid.getRow();
			int col = grid.getCol();
			if(row<0 || row>=ROWS || col<0 || col>=COLS || 
					mound[row][col]!=null){
				return true; //墙上有格子对象,发生重合
			}
		}
		return false;
	} 
	
	
	public boolean gridsCanDrop(){  //判断能不能继续落下
		Grid[] grids = ingGrids.getGrids();
		for(int i = 0; i<grids.length; i++){
			Grid grid = grids[i];
			int row = grid.getRow(); int col = grid.getCol();
			if(row == ROWS-1){return false;}//到底就不能下降了
		}
		for(int i = 0; i<grids.length; i++){
			Grid grid = grids[i];
			int row = grid.getRow(); int col = grid.getCol();
			if(mound[row+1][col] != null){
				return false;//下方墙上有方块就不能下降了
			}
		}
		return true;
	}
	
	public void slowlyDropAction(){   //一格一格下落
		if(gridsCanDrop()){
			ingGrids.softDrop();
		}else{
			gridLandToWall();
			destroyLines();//破坏满的行
			checkGameOver();
			ingGrids = nextGrids;
			nextGrids = GridController.randomTetris();
		}
	}
	
	
	
	public void directlyDropAction(){     //直接下落到底
		while(gridsCanDrop()){
			ingGrids.softDrop();
		}
		gridLandToWall();
		destroyLines();
		checkGameOver();
		ingGrids = nextGrids;
		nextGrids = GridController.randomTetris();
	}
	
	
	public void moveRightAction(){  //
		ingGrids.moveRight();
		if(outOfBound() || isCoincide()){
			ingGrids.moveLeft();
		}
	}
	public void moveLeftAction(){
		ingGrids.moveLeft();
		if(outOfBound() || isCoincide()){
			ingGrids.moveRight();
		}
	}
	
	public void spinRightAction(){  //向右旋转
		ingGrids.spinRight();
		if(outOfBound() || isCoincide()){
			ingGrids.spinLeft();
		}
	}
	
	
	public void spinLeftAction(){  //向左旋转
		ingGrids.spinLeft();
		if(outOfBound() || isCoincide()){
			ingGrids.spinRight();
		}
	}
	
	
	
	public void gridLandToWall(){ //落在墙上
		Grid[] cells = ingGrids.getGrids();
		for(int i=0; i<cells.length; i++){
			Grid cell = cells[i];
			int row = cell.getRow();
			int col = cell.getCol();
			mound[row][col] = cell;
		}
	}
	
	
	public boolean fullRows(int row){//判断是不是填满了一行
		Grid[] line = mound[row];
		for(int i=0; i<line.length; i++){
			if(line[i]==null){//如果有空格式就不是满行
				return false;
			}
		}
		return true;
	}
	

	public void destroyLines(){  //判断满没  消除整行 并且积分
		for(int row = 0; row<mound.length; row++){
			if(fullRows(row)){
				for(int i=row; i>=1; i--){
					System.arraycopy(mound[i-1], 0, mound[i], 0, COLS);
				}
				Music1();
				Arrays.fill(mound[0], null);
				this.lines = this.lines+1;
				this.score=this.score+10;
			}
			
		}
	}
	
	    public void Music1(){  
	    	   try {      
	    		   File f;
	    		   URI uri;
	    			 URL url; 	    			    
	    	       f = new File("D:\\学习资料\\大二\\java\\LYTetris\\src\\Tetris\\bi.wav"); 
	    	      uri = f.toURI();
	    	      url = uri.toURL();  //解析地址
	    	      AudioClip aau; 
	    	      aau = Applet.newAudioClip(url);
	    	       aau.play();  //
	    	   } catch (Exception e) 
	    	   { e.printStackTrace();
	    	   } 
	    	 }
	    
	    public void Music2(){  
	    	   try {     
	    		   File f;
	    		   URI uri;
	    			 URL url; 
	    	       f = new File("D:\\学习资料\\大二\\java\\LYTetris\\src\\Tetris\\backgroundmusic.wav"); 
	    	      uri = f.toURI();
	    	      url = uri.toURL();  //解析地址
	    	      AudioClip aau; 
	    	      aau = Applet.newAudioClip(url);
	    	       aau.loop();  //
	    	   } catch (Exception e) 
	    	   { e.printStackTrace();
	    	   } 
	    	 }

	
}


Test类:

package Tetris;

import javax.swing.JFrame;
import javax.swing.JPanel;


public class Test extends JPanel{

	public static void main(String[] args) {
		JFrame frame = new JFrame();
		RulesController tetris = new RulesController();
		frame.add(tetris);
		frame.setSize(713, 910);   //以上加载页面格式    宽 高
		frame.setUndecorated(false);  //true去掉窗口框!
		frame.setTitle("刘妍的俄罗斯方块");
		frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
		//Location 位置 RelativeTo相对于 
		frame.setLocationRelativeTo(null);//使当前窗口居中
		frame.setVisible(true);
		tetris.action();
	}

}

 实现效果:

 

 

 

参考博客:https://www.cnblogs.com/Renyi-Fan/p/7220327.html

java学习了一个学期,第一次做一个比较大、比较完整的小项目,有很多地方都参考了前辈的作品。

 俄罗斯方块小时候经常在电视机上或者游戏机上玩的游戏,现在能自己亲自动手实现一个自己的俄罗斯方块,我觉得很开心。

一开始的时候觉得这个游戏实现起来不会难,因为规则很简单,就是控制一些方块的运动而已,但是真正开始做的时候,很无措,这并不像之前的作业题,只是简单的几个类几个包就能搞定,以前的题目都会有要求或者提示说,“建几个包设置几个内部类、几个接口”,没有这些提示的话,就会不知从何入手,所以面临的第一个问题就是,怎样搭建一个框架,设置几个类,都干什么用。这个问题是我之前很少深思熟虑过的。思考过程中发现这其实很难划分合理,可能有重叠或者遗漏的部分。网上有几个现成的例子,基本都是按照[单位格子][格子组合][规则控制]设置三个类,按照平时的习惯,我自己增加了一个Test类作为程序的入口。

一开始决定好整体的框架之后就直接开始写具体的代码了,写着写着就发现,不能这样毫无根据的码,因为脑子里没有这个游戏的样子,就很难去真正实现它,我需要一个直观的界面和详细的规则,之前做项目的时候,老师就特意提醒过我们,“盲目”开发是不行的,方案需求一定要准备好,有根据地去开发。做好界面、方块格子、设计好操作方式和规则之后,思路更清晰,写起来就容易多了。

在具体实现过程中,也遇到很多问题,之前一学期学过的知识完全不够用,或者说,以前学过的东西知识浮于表面,缺乏进一步的理解和实际操作的经验,

有很多功能的实现要用到很多以前没见过的新方法

比如说:

计时器的使用、键盘的控制、布尔变量的应用、Arrays.fill数组填充、AudioClip接口播放音频、repaint()函数重绘组件、requestFocus()方法聚焦、键盘监听事件addKeyListener()、增强版FOR循环等

如果不去真正动手去做,去遇到问题的话,这些问题是很难有机会遇到并解决的,所以说,动手实践真的很重要。

除了以上这些,我发现编程对于思维的锻炼真的很神奇,由于这次做的东西比以往都要复杂,并且要独立完成,所以一整个做下来的过程中,经常被自己写的各种变量和方法绕晕,在写代码的过程中不全神贯注就很容易一团糟,要在脑子里理清楚各种方法和属性和类的关系,这个过程很过瘾。

并且,如何找资源如何借鉴前辈的经验,也是一个问题,网上有很多资料,多去看,多去了解,可以增长很多见识。

这个游戏做完,还有很多需要完善的地方,比如说增加注册登录的功能,添加一个排名,每消除一行得十分得规则可以改进,可以添加更多更好玩得音效和视觉效果等等

这次的课设真的学到很多东西,受益匪浅。

 

 

猜你喜欢

转载自blog.csdn.net/weixin_40406659/article/details/81214495