溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務條款》

java如何實現(xiàn)俄羅斯方塊游戲

發(fā)布時間:2021-04-14 13:59:43 來源:億速云 閱讀:225 作者:小新 欄目:編程語言

這篇文章主要介紹java如何實現(xiàn)俄羅斯方塊游戲,文中介紹的非常詳細,具有一定的參考價值,感興趣的小伙伴們一定要看完!

具體內容如下

1.功能需求
2.軟件功能架構圖
3.界面設計
4.程序邏輯圖
5.實現(xiàn)代碼

  • 創(chuàng)建控制面板并添加按鈕

  • 初始化界面

  • 添加事件監(jiān)聽

  • 創(chuàng)建方塊

  • 實現(xiàn)對方塊操作

  • 游戲主類,實現(xiàn)游戲控制


功能需求

1、 在二維平面里面用各種隨機產(chǎn)生的方塊堆積木,每滿一行消去一行,當達到頂部時,游戲結束。
2、 玩家通過方向鍵來控制方塊轉動,左移,右移和直落。
3、 每種類型的方塊都有顏色。
4、 玩家能夠在玩的過程中給出分數(shù),分數(shù)是由方塊的類型決定的,每堆積一個方塊就把分數(shù)累加到總分中。
5、 游戲有暫停,開始,結束,游戲規(guī)則和游戲說明等控制

軟件功能架構圖

java如何實現(xiàn)俄羅斯方塊游戲

界面設計

游戲主類繼承JFrame類,負責游戲的全局控制。內含:
(1)GameCanvas畫布類的實例對象(用來存放小方格)
(2)一個保存當前活動塊的(RussiaBlock)實例的對象
(3)一個保存當前控制面板(ControlPanel)實例的對象

程序邏輯圖

java如何實現(xiàn)俄羅斯方塊游戲

代碼實現(xiàn)

1、創(chuàng)建控制面板并添加按鈕

public class ControlPanel extends JPanel {
 private static final long serialVersionUID = 3900659640646175724L;// 用來表明不同版本之間類的兼容性

 // 定義文本框
 private JTextField tfLevel = new JTextField("" + RussiaBlocksGame.DEFAULT_LEVEL), tfScore = new JTextField("0"),
 tfTime = new JTextField(" ");

 // 定義按鈕
 private JButton btPlay = new JButton("開始"), btPause = new JButton("暫停"), btStop = new JButton("停止"),
 btTurnLevelUp = new JButton("增加難度"), btTurnLevelDown = new JButton("降低難度");

 // 創(chuàng)建面板容器類為邊界布局BorderLayout()
 private JPanel plTip = new JPanel(new BorderLayout());

 private TipPanel plTipBlock = new TipPanel();

 // 創(chuàng)建信息面板容器類為網(wǎng)格布局GridLayout(4,1),4行1列
 private JPanel plInfo = new JPanel(new GridLayout(4, 1));

 // 創(chuàng)建按鈕面板容器類為網(wǎng)格布局GridLayout(6,1)
 private JPanel plButton = new JPanel(new GridLayout(6, 1));

 // 定義時間類
 // private Timer timer;

 // 創(chuàng)建組件邊框Boreder,EtchedBorder“浮雕化”邊框
 private Border border = new EtchedBorder(EtchedBorder.RAISED, Color.white, new Color(148, 145, 140));

 /*
 * 控制面板類的構造函數(shù)
 */
 public ControlPanel(final RussiaBlocksGame game) {
 // TODO Auto-generated constructor stub

 // 創(chuàng)建網(wǎng)格布局,GridLayout(3,1,0,2), 指定 行數(shù) 和 列數(shù) 的網(wǎng)格布局, 并指定 水平 和 豎直 網(wǎng)格間隙
 setLayout(new GridLayout(3, 1, 0, 2));

 // 添加組件
 plTip.add(new JLabel("下一個方塊"), BorderLayout.NORTH);
 plTip.add(plTipBlock);
 plTip.setBorder(border);

 plInfo.add(new JLabel("難度系數(shù)"));
 plInfo.add(tfLevel);
 plInfo.add(new JLabel("得分"));
 plInfo.add(tfScore);
 plInfo.setBorder(border);

 plButton.add(btPlay);
 btPlay.setEnabled(true);
 plButton.add(btPause);
 btPause.setEnabled(false);
 plButton.add(btStop);
 btStop.setEnabled(false);
 plButton.add(btTurnLevelDown);
 plButton.add(btTurnLevelUp);
 plButton.setBorder(border);

 tfLevel.setEnabled(false);
 tfScore.setEnabled(false);
 tfTime.setEnabled(false);

 add(plTip);
 add(plInfo);
 add(plButton);
 }

2、初始化界面

 // 初始化菜單欄
 private JMenuBar bar = new JMenuBar();
 private JMenu mGame = new JMenu(" 游戲"), mControl = new JMenu(" 控制"), mInfo = new JMenu("幫助");
 private JMenuItem miNewGame = new JMenuItem("新游戲"), miSetBlockColor = new JMenuItem("設置方塊顏色..."),
 miSetBackColor = new JMenuItem("設置背景顏色..."), miTurnHarder = new JMenuItem("升高游戲難度"),
 miTurnEasier = new JMenuItem("降低游戲難度"), miExit = new JMenuItem("退出"), miPlay = new JMenuItem("開始"),
 miPause = new JMenuItem("暫停"), miResume = new JMenuItem("恢復"), miStop = new JMenuItem("終止游戲"),
 miRule = new JMenuItem("游戲規(guī)則"), miAuthor = new JMenuItem("關于本游戲");

 /**
 * 建立并設置窗口菜單
 */
 private void creatMenu() {
 bar.add(mGame);
 bar.add(mControl);
 bar.add(mInfo);

 mGame.add(miNewGame);
 mGame.addSeparator();
 mGame.add(miSetBlockColor);
 mGame.add(miSetBackColor);
 mGame.addSeparator();
 mGame.add(miTurnHarder);
 mGame.add(miTurnEasier);
 mGame.addSeparator();
 mGame.add(miExit);
 mControl.add(miPlay);
 miPlay.setEnabled(true);
 mControl.add(miPause);
 miPause.setEnabled(false);
 mControl.add(miResume);
 miResume.setEnabled(false);
 mControl.add(miStop);
 miStop.setEnabled(false);

 mInfo.add(miRule);
 mInfo.add(miAuthor);
 setJMenuBar(bar);

 miNewGame.addActionListener(new ActionListener() {
 @Override
 public void actionPerformed(ActionEvent e) {
 stopGame();
 reset();
 setLevel(DEFAULT_LEVEL);
 }
 });

 // 設置方塊顏色
 miSetBlockColor.addActionListener(new ActionListener() {
 @Override
 public void actionPerformed(ActionEvent e) {
 Color newFrontColor = JColorChooser.showDialog(RussiaBlocksGame.this, "設置方塊顏色",
 canvas.getBackgroundColor());
 if (newFrontColor != null) {
 canvas.setBlockColor(newFrontColor);
 }
 }
 });

 // 設置背景顏色
 miSetBackColor.addActionListener(new ActionListener() {
 @Override
 public void actionPerformed(ActionEvent e) {
 Color newBackColor = JColorChooser.showDialog(RussiaBlocksGame.this, "設置背景顏色",
 canvas.getBackgroundColor());
 if (newBackColor != null) {
 canvas.setBackgroundColor(newBackColor);
 }
 }
 });

 // 定義菜單欄"關于"的功能,彈出確認框。
 miAuthor.addActionListener(new ActionListener() {
 @Override
 public void actionPerformed(ActionEvent e) {
 JOptionPane.showMessageDialog(null, "軟件工程(4)班\n3115005372\n楊宇杰\n©一切解釋權歸楊宇杰所有", "關于俄羅斯方塊 - 2016", 1);
 }
 });

 // 游戲規(guī)則說明
 miRule.addActionListener(new ActionListener() {
 @Override
 public void actionPerformed(ActionEvent e) {
 JOptionPane.showMessageDialog(null,
 "由小方塊組成的不同形狀的板塊陸續(xù)從屏幕上方落下來,\n玩家通過調整板塊的位置和方向,使它們在屏幕底部拼\n出完整的一條或幾條。這些完整的橫條會隨即消失,給新\n落下來的板塊騰出空間,與此同時,玩家得到分數(shù)獎勵。\n沒有被消除掉的方塊不斷堆積起來,一旦堆到屏幕頂端,\n玩家便告輸,游戲結束。",
 "游戲規(guī)則", 1);
 }
 });

 // 增加難度
 miTurnHarder.addActionListener(new ActionListener() {
 @Override
 public void actionPerformed(ActionEvent e) {
 int curLevel = getLevel();
 if (!playing && curLevel < MAX_LEVEL) {
 setLevel(curLevel + 1);
 }
 }
 });

 // 減少難度
 miTurnEasier.addActionListener(new ActionListener() {
 @Override
 public void actionPerformed(ActionEvent e) {
 int curLevel = getLevel();
 if (!playing && curLevel > 1) {
 setLevel(curLevel - 1);
 }
 }
 });

 // 退出按鈕動作響應
 miExit.addActionListener(new ActionListener() {
 @Override
 public void actionPerformed(ActionEvent e) {
 System.exit(0);
 }
 });

 }

3、添加事件監(jiān)聽

 /*
 * 添加事件監(jiān)聽
 */
 /*
 * 開始游戲
 */
 btPlay.addActionListener(new ActionListener() {

 @Override
 public void actionPerformed(ActionEvent ae) {
 // TODO Auto-generated method stub
 game.playGame();

 }
 });

 /*
 * 暫停游戲
 */
 btPause.addActionListener(new ActionListener() {

 @Override
 public void actionPerformed(ActionEvent ae) {
 // TODO Auto-generated method stub
 if (btPause.getText().equals("暫停")) {
 game.pauseGame();
 } else {
 game.resumeGame();
 }
 }
 });

 /*
 * 停止游戲
 */
 btStop.addActionListener(new ActionListener() {

 @Override
 public void actionPerformed(ActionEvent ae) {
 // TODO Auto-generated method stub
 game.stopGame();

 }
 });

 /*
 * 升高難度
 */
 btTurnLevelUp.addActionListener(new ActionListener() {

 @Override
 public void actionPerformed(ActionEvent ae) {
 // TODO Auto-generated method stub
 try {
 int level = Integer.parseInt(tfLevel.getText());
 if (level < RussiaBlocksGame.MAX_LEVEL) {
 tfLevel.setText("" + (level + 1));

 }
 } catch (NumberFormatException e) {
 // TODO: handle exception
 requestFocus();
 }
 }
 });

 /*
 * 降低游戲難度
 */
 btTurnLevelDown.addActionListener(new ActionListener() {

 @Override
 public void actionPerformed(ActionEvent ae) {
 // TODO Auto-generated method stub
 try {
 int level = Integer.parseInt(tfLevel.getText());
 if (level > 1) {
 tfLevel.setText("" + (level - 1));

 }

 } catch (NumberFormatException e) {
 // TODO: handle exception
 requestFocus();
 }

 }
 });

 /*
 * 主要用于解決Jframe窗口大小變化時,里面的組件的位置也會自適應的移動。
 */
 addComponentListener(new ComponentAdapter() {
 public void componentResized(ComponentEvent ce) {
 plTipBlock.fanning();
 }
 });

4、創(chuàng)建方塊

public class ErsBox implements Cloneable {

 private boolean isColor;
 private Dimension size = new Dimension(); // Dimension類封裝單個對象中組件的寬度和高度(精確到整數(shù))

 /*
 * 方格類構造函數(shù) isColor是不是用前景色為此方格著色,true前景色,false背景色
 */
 public ErsBox(boolean isColor) {
 // TODO Auto-generated constructor stub
 this.isColor = isColor;
 }

 /*
 * 設置方格的顏色 true前景色,false背景色
 */
 public void setColor(boolean isColor) {
 // TODO Auto-generated method stub
 this.isColor = isColor;

 }

 /*
 * 得到此方格的尺寸
 */
 public Dimension getSize() {
 return size;
 }

 /**
 * 設置方格的尺寸,
 *
 * @param size Dimension ,方格的尺寸
 */
 public void setSize(Dimension size) {
 this.size = size;
 }

 /*
 * 覆蓋object的object clone(),實現(xiàn)克隆
 */
 public Object clone() {
 Object cloned = null;
 try {
 cloned = super.clone();
 } catch (Exception ex) {
 // TODO: handle exception
 ex.printStackTrace();
 }
 return cloned;

 }

 /**
 * 此方格是不是用前景色表現(xiàn)
 *
 * @return boolean ,true用前景色表現(xiàn),false 用背景色表現(xiàn)
 */
 public boolean isColorBox() {
 // TODO Auto-generated method stub
 return isColor;
 }

}

5、實現(xiàn)對方塊操作

public class ErsBlock extends Thread {

 // 一個塊占得4行
 public static final int BOXES_ROWS = 4;

 // 一個塊占4列
 public static final int BOXES_COLS = 4;

 /*
 * 讓升級變化平滑的因子,避免最后幾級之間的速度相差近一倍
 */
 public final static int LEVEL_FLATNESS_GENE = 3;

 // 相近的兩級之間,塊每下落一行的時間差別為多少(毫秒)
 public final static int BETWEEN_LEVELS_DEGRESS_TIME = 50;

 // 方塊的樣式數(shù)目為7
 public final static int BLOCK_KIND_NUMBER = 7;

 // 每一個樣式的方塊反轉狀態(tài)種類為4
 public final static int BLOCK_STASTUS_NUMBER = 4;

 /**
 * 分別對應7中模型的28中狀態(tài)
 */
 public final static int[][] STYLES = { // 共28種狀態(tài)
 { 0x0f00, 0x4444, 0x0f00, 0x4444 }, // 長條型的四種狀態(tài)
 { 0x04e0, 0x0464, 0x00e4, 0x04c4 }, // T型的四種狀態(tài)
 { 0x4620, 0x6c00, 0x4620, 0x6c00 }, // 反Z型的四種狀態(tài)
 { 0x2640, 0xc600, 0x2640, 0xc600 }, // Z型的四種狀態(tài)
 { 0x6220, 0x1700, 0x2230, 0x0740 }, // 7型的四種狀態(tài)
 { 0x6440, 0x0e20, 0x44c0, 0x8e00 }, // 反7型的四種狀態(tài)
 { 0x0660, 0x0660, 0x0660, 0x0660 }, // 方塊的四種狀態(tài)
 };

 private GameCanvas canvas;
 private ErsBox[][] boxes = new ErsBox[BOXES_ROWS][BOXES_COLS];
 private int style, y, x, level;
 private boolean pausing = false, moving = true;

 /*
 * 構造一個函數(shù),產(chǎn)生一個特定的塊 style為塊的樣式,對應STYLES中的某一個 y起始位置,左上角在canvas中的坐標行
 * x起始位置,左上角在canvas中的坐標列 level游戲等級控制下降速度 canvas面板
 */
 public ErsBlock(int style, int y, int x, int level, GameCanvas canvas) {
 this.style = style;
 this.y = y;
 this.x = x;
 this.level = level;
 this.canvas = canvas;

 int key = 0x8000;
 for (int i = 0; i < boxes.length; i++) {
 for (int j = 0; j < boxes[i].length; j++) {
 boolean isColor = ((style & key) != 0);
 boxes[i][j] = new ErsBox(isColor);
 key >>= 1;
 }
 }
 display();
 }

 /*
 * 線程類的run()函數(shù)覆蓋,下落塊,直到塊不能再下落
 */
 @Override
 public void run() {
 while (moving) {
 try {
 sleep(BETWEEN_LEVELS_DEGRESS_TIME * (RussiaBlocksGame.MAX_LEVEL - level + LEVEL_FLATNESS_GENE));
 } catch (InterruptedException ie) {
 ie.printStackTrace();
 }
 // 后邊的moving是表示在等待的100毫秒間,moving沒有被改變
 if (!pausing) {
 moving = (moveTo(y + 1, x) && moving);
 }
 }
 }

 /*
 * 塊左移一格
 */
 public void moveLeft() {
 // TODO Auto-generated method stub
 moveTo(y, x - 1);
 }

 /*
 * 塊右移一格
 */
 public void moveRight() {
 // TODO Auto-generated method stub
 moveTo(y, x + 1);
 }

 /**
 * 塊下移一格
 */
 public void moveDown() {
 // TODO Auto-generated method stub
 moveTo(y + 1, x);
 }

 /*
 * 塊變形
 */
 public void turnNext() {
 for (int i = 0; i < BLOCK_KIND_NUMBER; i++) {
 for (int j = 0; j < BLOCK_STASTUS_NUMBER; j++) {
 if (STYLES[i][j] == style) {
 int newStyle = STYLES[i][(j + 1) % BLOCK_STASTUS_NUMBER];
 turnTo(newStyle);
 return;
 }
 }
 }
 }

 public void startMove() {
 // TODO Auto-generated method stub
 pausing = false;
 moving = true;

 }

 /*
 * 暫定塊的下落,對應暫停游戲
 */
 public void pauseMove() {
 // TODO Auto-generated method stub
 pausing = true;
 // moving = false;
 }

 /*
 * 繼續(xù)塊的下落,對應游戲的繼續(xù)
 */
 public void resumeMove() {
 // TODO Auto-generated method stub
 pausing = false;
 moving = true;

 }

 /*
 * 停止塊的下落,對應游戲的停止
 */
 public void stopMove() {
 // TODO Auto-generated method stub
 pausing = false;
 moving = false;
 }

 /*
 * 將當前塊從畫布的對應位置移除,要等到下次重畫畫布時才能反映出來
 */
 private void erase() {
 for (int i = 0; i < boxes.length; i++) {
 for (int j = 0; j < boxes[i].length; j++) {
 if (boxes[i][j].isColorBox()) {
 ErsBox box = canvas.getBox(i + y, j + x);
 if (box == null) {
 continue;
 }
 box.setColor(false);
 }
 }
 }
 }

 /*
 * 讓當前塊放置在畫布的對應位置上,要等到下次重畫畫布時,才能看見
 */
 private void display() {
 for (int i = 0; i < boxes.length; i++) {
 for (int j = 0; j < boxes[i].length; j++) {
 if (boxes[i][j].isColorBox()) {
 ErsBox box = canvas.getBox(i + y, j + x);
 if (box == null) {
 continue;
 }
 box.setColor(true);
 }
 }

 }

 }

 /**
 * 當前塊能否移動到newRow/newCol 所指定的位置
 *
 * @param newRow int,目的地所在行
 * @param newCol int,目的地所在列
 * @return boolean,true-能移動,false-不能移動
 */
 public boolean isMoveAble(int newRow, int newCol) {
 erase();
 for (int i = 0; i < boxes.length; i++) {
 for (int j = 0; j < boxes[i].length; j++) {
 if (boxes[i][j].isColorBox()) {
 ErsBox box = canvas.getBox(i + newRow, j + newCol);
 if (box == null || (box.isColorBox())) {
 display();
 return false;
 }
 }
 }
 }
 display();
 return true;
 }

 /*
 * 將當前塊移動到newRow/newCol所指定位置 newRow 目的所在行 newCol 目的所在列 boolean, true 能移動,false
 * 不能移動
 */
 private synchronized boolean moveTo(int newRow, int newCol) {
 if (!isMoveAble(newRow, newCol) || !moving) {
 return false;
 }

 erase();
 y = newRow;
 x = newCol;

 display();
 canvas.repaint();

 return true;
 }

 /*
 * 當前塊能否變成newStyle所指定的樣式,主要考慮 邊界,以及被其他塊擋住不能移動的情況 newStyle,希望改變的樣式 boolean true
 * 能改變,false不能改變
 */
 private boolean isTurnAble(int newStyle) {
 int key = 0x80000;
 erase();
 for (int i = 0; i < boxes.length; i++) {
 for (int j = 0; j < boxes[i].length; j++) {
 if ((newStyle & key) != 0) {
 ErsBox box = canvas.getBox(i + y, j + x);
 if (box == null || (box.isColorBox())) {
 display();
 return false;
 }
 }
 key >>= 1;
 }
 }
 display();
 return true;
 }

 /*
 * 將當前塊變成newStyle所指定的塊樣式 newStyle ,希望改變的樣式,對應STYLES中的某一個 true 改變成功,false改變失敗
 */
 private boolean turnTo(int newStyle) {
 // TODO Auto-generated method stub
 if (!isTurnAble(newStyle) || !moving) {
 return false;
 }

 erase();
 int key = 0x8000;
 for (int i = 0; i < boxes.length; i++) {
 for (int j = 0; j < boxes[i].length; j++) {
 boolean isColor = ((newStyle & key) != 0);
 boxes[i][j].setColor(isColor);
 key >>= 1;
 }
 }
 style = newStyle;

 display();
 canvas.repaint();

 return true;
 }

}

6、游戲主類,實現(xiàn)游戲控制

public RussiaBlocksGame(String title) {
 super(title); // 設置標題
 setSize(500, 600); // 設置窗口大小
 setLocationRelativeTo(null); // 設置窗口居中

 creatMenu();
 Container container = getContentPane(); // 創(chuàng)建菜單欄
 container.setLayout(new BorderLayout(6, 0)); // 設置窗口的布局管理器
 canvas = new GameCanvas(20, 15); // 新建游戲畫布
 ctrlPanel = new ControlPanel(this); // 新建控制面板
 container.add(canvas, BorderLayout.CENTER); // 左邊加上畫布
 container.add(ctrlPanel, BorderLayout.EAST); // 右邊加上控制面板

 // 注冊窗口事件。當點擊關閉按鈕時,結束游戲,系統(tǒng)退出。
 addWindowListener(new WindowAdapter() {
 @Override
 public void windowClosing(WindowEvent we) {
 stopGame();
 System.exit(0);
 }
 });

 // 根據(jù)窗口大小,自動調節(jié)方格的尺寸
 addComponentListener(new ComponentAdapter() {
 @Override
 public void componentResized(ComponentEvent ce) {
 canvas.adjust();
 }
 });

 setVisible(true);
 canvas.adjust();
 }

 /**
 * 讓游戲復位
 */
 public void reset() { // 畫布復位,控制面板復位
 ctrlPanel.setPlayButtonEnable(true);
 ctrlPanel.setPauseButtonEnable(false);
 ctrlPanel.setPauseButtonLabel(true);
 ctrlPanel.setStopButtonEnable(false);
 ctrlPanel.setTurnLevelDownButtonEnable(true);
 ctrlPanel.setTurnLevelUpButtonEnable(true);
 miPlay.setEnabled(true);
 miPause.setEnabled(false);
 miResume.setEnabled(false);
 miStop.setEnabled(false);
 ctrlPanel.reset();
 canvas.reset();
 }

 /**
 * 判斷游戲是否還在進行
 *
 * @return boolean,true -還在運行,false-已經(jīng)停止
 */
 public boolean isPlaying() {
 return playing;
 }

 /**
 * 得到當前活動的塊
 *
 * @return ErsBlock,當前活動塊的引用
 */
 public ErsBlock getCurBlock() {
 return block;
 }

 /**
 * 得到當前畫布
 *
 * @return GameCanvas,當前畫布的引用
 */
 public GameCanvas getCanvas() {
 return canvas;
 }

 /**
 * 開始游戲
 */
 public void playGame() {
 play();
 ctrlPanel.setPlayButtonEnable(false);
 ctrlPanel.setPauseButtonEnable(true);
 ctrlPanel.setPauseButtonLabel(true);
 ctrlPanel.setStopButtonEnable(true);
 ctrlPanel.setTurnLevelDownButtonEnable(false);
 ctrlPanel.setTurnLevelUpButtonEnable(false);
 miStop.setEnabled(true);
 miTurnHarder.setEnabled(false);
 miTurnEasier.setEnabled(false);
 ctrlPanel.requestFocus(); // 設置焦點
 }

 /**
 * 游戲暫停
 */
 public void pauseGame() {
 if (block != null) {
 block.pauseMove();
 }
 ctrlPanel.setPlayButtonEnable(false);
 ctrlPanel.setPauseButtonLabel(false);
 ctrlPanel.setStopButtonEnable(true);
 miPlay.setEnabled(false);
 miPause.setEnabled(false);
 miResume.setEnabled(true);
 miStop.setEnabled(true);
 }

 /**
 * 讓暫停中的游戲繼續(xù)
 */
 public void resumeGame() {
 if (block != null) {
 block.resumeMove();
 }
 ctrlPanel.setPlayButtonEnable(false);
 ctrlPanel.setPauseButtonEnable(true);
 ctrlPanel.setPauseButtonLabel(true);
 miPause.setEnabled(true);
 miResume.setEnabled(false);
 ctrlPanel.requestFocus();
 }

 /**
 * 用戶停止游戲
 */
 public void stopGame() {
 playing = false;
 if (block != null) {
 block.stopMove();
 }
 ctrlPanel.setPlayButtonEnable(true);
 ctrlPanel.setPauseButtonEnable(false);
 ctrlPanel.setPauseButtonLabel(true);
 ctrlPanel.setStopButtonEnable(false);
 ctrlPanel.setTurnLevelDownButtonEnable(true);
 ctrlPanel.setTurnLevelUpButtonEnable(true);
 miPlay.setEnabled(true);
 miPause.setEnabled(false);
 miResume.setEnabled(false);
 miStop.setEnabled(false);
 miTurnHarder.setEnabled(true);
 miTurnEasier.setEnabled(true);
 reset();// 重置畫布和控制面板
 }

 /**
 * 得到游戲者設置的難度
 *
 * @return int ,游戲難度1-MAX_LEVEL
 */
 public int getLevel() {
 return ctrlPanel.getLevel();
 }

 /**
 * 用戶設置游戲難度
 *
 * @param level int ,游戲難度1-MAX_LEVEL
 */
 public void setLevel(int level) {
 if (level < 11 && level > 0) {
 ctrlPanel.setLevel(level);
 }
 }

 /**
 * 得到游戲積分
 *
 * @return int,積分
 */
 public int getScore() {
 if (canvas != null) {
 return canvas.getScore();
 }
 return 0;
 }

 /**
 * 得到自上次升級以來的游戲積分,升級以后,此積分清零
 *
 * @return int,積分
 */
 public int getScoreForLevelUpdate() {
 if (canvas != null) {
 return canvas.getScoreForLevelUpdate();
 }
 return 0;
 }

 /**
 * 當積分累積到一定數(shù)值時,升一次級
 *
 * @return Boolean,true-update succeed,false-update fail
 */
 public boolean levelUpdate() {
 int curLevel = getLevel();
 if (curLevel < MAX_LEVEL) {
 setLevel(curLevel + 1);
 canvas.resetScoreForLevelUpdate();
 return true;
 }
 return false;
 }

 /**
 * 游戲開始
 */
 private void play() {
 reset();
 playing = true;
 Thread thread = new Thread(new Game());// 啟動游戲線程
 thread.start();
 }

 /**
 * 報告游戲結束了
 */
 private void reportGameOver() {
 new gameOverDialog(this, "俄羅斯方塊", "游戲結束,您的得分為" + canvas.getScore());
 }

 /**
 * 一輪游戲過程,實現(xiàn)了Runnable接口 一輪游戲是一個大循環(huán),在這個循環(huán)中,每隔100毫秒, 檢查游戲中的當前塊是否已經(jīng)到底了,如果沒有,
 * 就繼續(xù)等待。如果到底了,就看有沒有全填滿的行, 如果有就刪除它,并為游戲者加分,同時隨機產(chǎn)生一個新的當前塊并讓它自動落下。
 * 當新產(chǎn)生一個塊時,先檢查畫布最頂上的一行是否已經(jīng)被占了,如果是,可以判斷Game Over 了。
 */
 private class Game implements Runnable {
 @Override
 public void run() {
 int col = (int) (Math.random() * (canvas.getCols() - 3));
 int style = ErsBlock.STYLES[(int) (Math.random() * 7)][(int) (Math.random() * 4)];

 while (playing) {
 if (block != null) { // 第一次循環(huán)時,block為空
 if (block.isAlive()) {
 try {
 Thread.currentThread();
 Thread.sleep(500);
 } catch (InterruptedException ie) {
 ie.printStackTrace();
 }
 continue;
 }
 }

 checkFullLine(); // 檢查是否有全填滿的行

 if (isGameOver()) {
 reportGameOver();
 miPlay.setEnabled(true);
 miPause.setEnabled(false);
 miResume.setEnabled(false);
 miStop.setEnabled(false);
 ctrlPanel.setPlayButtonEnable(true);
 ctrlPanel.setPauseButtonLabel(false);
 ctrlPanel.setStopButtonEnable(false);
 return;
 }

 block = new ErsBlock(style, -1, col, getLevel(), canvas);
 block.start();

 col = (int) (Math.random() * (canvas.getCols() - 3));
 style = ErsBlock.STYLES[(int) (Math.random() * 7)][(int) (Math.random() * 4)];

 ctrlPanel.setTipStyle(style);
 }
 }

 // 檢查畫布中是否有全填滿的行,如果有就刪之
 public void checkFullLine() {
 for (int i = 0; i < canvas.getRows(); i++) {
 int row = -1;
 boolean fullLineColorBox = true;
 for (int j = 0; j < canvas.getCols(); j++) {
 if (!canvas.getBox(i, j).isColorBox()) {
 fullLineColorBox = false;
 break;
 }
 }
 if (fullLineColorBox) {
 row = i--;
 canvas.removeLine(row);
 }
 }
 }

 // 根據(jù)最頂行是否被占,判斷游戲是否已經(jīng)結束了
 // @return boolean ,true-游戲結束了,false-游戲未結束
 private boolean isGameOver() {
 for (int i = 0; i < canvas.getCols(); i++) {
 ErsBox box = canvas.getBox(0, i);
 if (box.isColorBox()) {
 return true;
 }
 }
 return false;
 }
 }

 /**
 * 定義GameOver對話框。
 */
 @SuppressWarnings("serial")
 private class gameOverDialog extends JDialog implements ActionListener {

 private JButton againButton, exitButton;
 private Border border = new EtchedBorder(EtchedBorder.RAISED, Color.white, new Color(148, 145, 140));

 public gameOverDialog(JFrame parent, String title, String message) {
 super(parent, title, true);
 if (parent != null) {
 setSize(240, 120);
 this.setLocationRelativeTo(parent);
 JPanel messagePanel = new JPanel();
 messagePanel.add(new JLabel(message));
 messagePanel.setBorder(border);
 Container container = this.getContentPane();
 container.setLayout(new GridLayout(2, 0, 0, 10));
 container.add(messagePanel);
 JPanel choosePanel = new JPanel();
 choosePanel.setLayout(new GridLayout(0, 2, 4, 0));
 container.add(choosePanel);
 againButton = new JButton("再玩一局");
 exitButton = new JButton("退出游戲");
 choosePanel.add(new JPanel().add(againButton));
 choosePanel.add(new JPanel().add(exitButton));
 choosePanel.setBorder(border);
 }
 againButton.addActionListener(this);
 exitButton.addActionListener(this);
 this.setVisible(true);
 }

 @Override
 public void actionPerformed(ActionEvent e) {
 if (e.getSource() == againButton) {
 this.setVisible(false);
 reset();
 } else if (e.getSource() == exitButton) {
 stopGame();
 System.exit(0);

 }
}

以上是“java如何實現(xiàn)俄羅斯方塊游戲”這篇文章的所有內容,感謝各位的閱讀!希望分享的內容對大家有幫助,更多相關知識,歡迎關注億速云行業(yè)資訊頻道!

向AI問一下細節(jié)

免責聲明:本站發(fā)布的內容(圖片、視頻和文字)以原創(chuàng)、轉載和分享為主,文章觀點不代表本網(wǎng)站立場,如果涉及侵權請聯(lián)系站長郵箱:is@yisu.com進行舉報,并提供相關證據(jù),一經(jīng)查實,將立刻刪除涉嫌侵權內容。

AI