Java大作业——手把手教你写俄罗斯方块
目录
俄罗斯方块方块体的设计:
控制主逻辑块:
可视化界面:
封面设计:
游戏底盘:
游戏主界面:
文末附源码链接
俄罗斯方块:
由小方块组成的不同形状的板块陆续从屏幕上方落下来,玩家通过调整板块的位置和方向,使它们在屏幕底部拼出完整的一条或几条。这些完整的横条会随即消失,给新落下来的板块腾出空间,与此同时,玩家得到分数奖励。没有被消除掉的方块不断堆积起来,一旦堆到屏幕顶端,玩家便告输,游戏结束。
笔者相信很多小伙伴都玩过或听说过这个小游戏,今天笔者就带大家走一遍编写流程(写的时间有点久远了,可能有些地方有疏忽,欢迎批评指正)。
俄罗斯方块方块体的设计:
//Blocks.javapublic class Blocks { int[][] t={ {1,1,1,0,0,1,0,0,0,0,0,0,0,0,0,0}, {1,0,0,0,1,1,0,0,1,0,0,0,0,0,0,0}, {0,1,0,0,1,1,1,0,0,0,0,0,0,0,0,0}, {0,1,0,0,1,1,0,0,0,1,0,0,0,0,0,0}, }; int[][] l={ { 1, 1, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },{ 1, 1, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },{ 1, 1, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },{ 1, 1, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 } }; int[][] m={ { 1, 0, 0, 0, 1, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0 },{ 1, 1, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },{ 1, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0 },{ 0, 0, 1, 0, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0 } }; int[][] i={ { 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0 },{ 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0 },{ 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0 },{ 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 1, 0, 0 } }; }
控制主逻辑块:
//Controller.javaimport java.util.Random;import java.util.logging.Level;import java.util.logging.Logger;import javax.swing.JOptionPane;public class Controller extends Thread{ GamePanel gp; int i; int hua; int fen=0; int[][] blocks; Random r=new Random(); int status=r.nextInt(4);int po; //int[] block; public Controller(GamePanel gp){ this.gp=gp; gp.status=r.nextInt(4); status=r.nextInt(4); hua=r.nextInt(4);if(hua==1) blocks =new Blocks().t; else if (hua==2) blocks =new Blocks().l; else if(hua==3) blocks =new Blocks().m; else blocks =new Blocks().i; gp.block=blocks[status]; start(); } public boolean isOverStep(int x,int y,int [] block){ boolean flag=false; for(int i=0;i<4;i++) for(int j=0;j<4;j++){ if(block[4*i+j]==1 && ((x+j*20)180 || (y+i*20)>=400 || gp.fixBlocks[y/20+i][x/20+j]==1) ){ flag=true; } } return flag; } public void theBlockFinish(){ for(int i=0;i<4;i++) for(int j=0;j=0;i--){ m=0; for(int j=0;j<=9;j++){ m=m+gp.fixBlocks[i][j]; } if(m==10){ for(int s=0;s0;k--){ gp.fixBlocks[k][s]=gp.fixBlocks[k-1][s]; } } gp.fen=gp.fen+1; } } up();} public void up(){if(!isOverStep(gp.x-20, gp.y+20, gp.block)){ if (hua==1) gp.block=new Blocks().t[status]; else if (hua==2) gp.block=new Blocks().l[status]; else if(hua==3) gp.block=new Blocks().m[status]; else gp.block=new Blocks().i[status];gp.repaint();status++;if (status==blocks.length) status=0;} } public void left(){ if(!isOverStep(gp.x-20, gp.y, gp.block)){ gp.x-=20; gp.repaint(); } } public void right(){if(!isOverStep(gp.x+20, gp.y, gp.block)){gp.x+=20;gp.repaint();}} public void down(){if(!isOverStep(gp.x, gp.y+20, gp.block)){gp.y+=20;gp.repaint();}else {theBlockFinish();} } public int cedown(){if(!isOverStep(gp.x, gp.y+20, gp.block)){gp.y+=20;gp.repaint();return 1;}else {theBlockFinish();return 0;} } public void gameover(){ JOptionPane.showMessageDialog(null, "GAME OVER"); } public void run(){ while(!isOverStep(gp.x, gp.y+20, gp.block)){ try { {gp.y+=20; gp.repaint(); } sleep(1000); } catch (InterruptedException ex) { Logger.getLogger(Controller.class.getName()).log(Level.SEVERE, null, ex); } } }}
可视化界面:
封面设计:
//FenMian.javapublic class FenMian extends javax.swing.JPanel {int panduan=0; / * Creates new form FenMian */ public FenMian() { initComponents(); } / * This method is called from within the constructor to initialize the form. * WARNING: Do NOT modify this code. The content of this method is always * regenerated by the Form Editor. */ @SuppressWarnings("unchecked") // private void initComponents() { jButton1 = new javax.swing.JButton(); setBackground(new java.awt.Color(255, 102, 102)); jButton1.setText("jButton1"); jButton1.addMouseListener(new java.awt.event.MouseAdapter() { public void mouseClicked(java.awt.event.MouseEvent evt) { jButton1MouseClicked(evt); } }); javax.swing.GroupLayout layout = new javax.swing.GroupLayout(this); this.setLayout(layout); layout.setHorizontalGroup( layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) .addGroup(javax.swing.GroupLayout.Alignment.TRAILING, layout.createSequentialGroup() .addContainerGap(161, Short.MAX_VALUE) .addComponent(jButton1) .addGap(142, 142, 142)) ); layout.setVerticalGroup( layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) .addGroup(layout.createSequentialGroup() .addGap(89, 89, 89) .addComponent(jButton1) .addContainerGap(184, Short.MAX_VALUE)) ); }// private void jButton1MouseClicked(java.awt.event.MouseEvent evt) { panduan=1; jButton1.setVisible(false); // TODO add your handling code here: } // Variables declaration - do not modify private javax.swing.JButton jButton1; // End of variables declaration }
游戏底盘:
//GamePanel.javaimport java.awt.Color;import java.awt.Graphics;public class GamePanel extends javax.swing.JPanel { MainFrame main; int panduan=0; int status; int x=40,y=0; int i; int flag=1; int jia=0; int fen=0; int[] block; int[][] fixBlocks=new int[20][10]; / * Creates new form GamePanel */ public GamePanel() { initComponents(); } public void drawBlock(Graphics g){for(int i=0;i<4;i++){ for(int j=0;j<4;j++){ if(block[i*4+j]==1) g.fill3DRect(x+j*20,y+i*20, 20, 20,true); } } } public void drawFixBlocks(Graphics g){ for(int i=0;i<20;i++){ for(int j=0;j<10;j++){ if(fixBlocks[i][j]==1) g.fill3DRect(j*20,i*20, 20, 20,true); } } } public void paintComponent(Graphics g){ super.paintComponent(g); g.setColor(Color.BLUE); drawBlock(g); g.setColor(Color.GRAY); drawFixBlocks(g); String ma=String.valueOf(fen*10);g.drawString("score=" + ma, 125, 10); //g.fill3DRect(x, y, 20, 20,true); } / * This method is called from within the constructor to initialize the form. * WARNING: Do NOT modify this code. The content of this method is always * regenerated by the Form Editor. */ @SuppressWarnings("unchecked") // private void initComponents() { setBackground(new java.awt.Color(255, 255, 204)); setBorder(javax.swing.BorderFactory.createBevelBorder(javax.swing.border.BevelBorder.LOWERED)); addKeyListener(new java.awt.event.KeyAdapter() { public void keyPressed(java.awt.event.KeyEvent evt) { formKeyPressed(evt); } }); javax.swing.GroupLayout layout = new javax.swing.GroupLayout(this); this.setLayout(layout); layout.setHorizontalGroup( layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) .addGap(0, 396, Short.MAX_VALUE) ); layout.setVerticalGroup( layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) .addGap(0, 296, Short.MAX_VALUE) ); }// private void formKeyPressed(java.awt.event.KeyEvent evt) { // TODO add your handling code here: }// Variables declaration - do not modify // End of variables declaration / * @param jLabel1 the jLabel1 to set */ }
游戏主界面:
//MainFrame.javapublic class MainFrame extends javax.swing.JFrame {Controller controller;int i;int jia=0;int panduan=0; String ma=String.valueOf(jia*10); / * Creates new form MainFrame */ public MainFrame() { initComponents(); FenMian fm=new FenMian(); GamePanel gp=new GamePanel();controller=new Controller(gp); gp.setSize(200, 400); gp.setLocation(50, 50); this.setSize(400, 600); this.getContentPane().add(gp); //将panel放入frame中 setTitle("yyf nb"); if(!controller.isOverStep(gp.x+20, gp.y+20, gp.block)) {gp.x=40;gp.y=0; controller=new Controller(gp);} } / * This method is called from within the constructor to initialize the form. * WARNING: Do NOT modify this code. The content of this method is always * regenerated by the Form Editor. */ @SuppressWarnings("unchecked") // private void initComponents() { jLabel2 = new javax.swing.JLabel(); jMenuBar1 = new javax.swing.JMenuBar(); jMenu1 = new javax.swing.JMenu(); jCheckBoxMenuItem1 = new javax.swing.JCheckBoxMenuItem(); jMenu2 = new javax.swing.JMenu(); setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); addKeyListener(new java.awt.event.KeyAdapter() { public void keyPressed(java.awt.event.KeyEvent evt) { formKeyPressed(evt); } }); jLabel2.setText("score"); jMenu1.setText("菜单"); jCheckBoxMenuItem1.setSelected(true); jCheckBoxMenuItem1.setText("开始"); jMenu1.add(jCheckBoxMenuItem1); jMenuBar1.add(jMenu1); jMenu2.setText("选项"); jMenuBar1.add(jMenu2); setJMenuBar(jMenuBar1); javax.swing.GroupLayout layout = new javax.swing.GroupLayout(getContentPane()); getContentPane().setLayout(layout); layout.setHorizontalGroup( layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) .addGroup(layout.createSequentialGroup() .addContainerGap(213, Short.MAX_VALUE) .addComponent(jLabel2) .addGap(147, 147, 147)) ); layout.setVerticalGroup( layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) .addGroup(layout.createSequentialGroup() .addGap(27, 27, 27) .addComponent(jLabel2) .addContainerGap(229, Short.MAX_VALUE)) ); pack(); }// private void formKeyPressed(java.awt.event.KeyEvent evt) { switch(evt.getKeyCode()){ case 37: controller.left();break; case 40: {controller.down();};break; case 39: controller.right();break; case 38: controller.up(); break; } // TODO add your handling code here: }/ * @param args the command line arguments */ public static void main(String args[]) { /* Set the Nimbus look and feel */ // /* If Nimbus (introduced in Java SE 6) is not available, stay with the default look and feel. * For details see http://download.oracle.com/javase/tutorial/uiswing/lookandfeel/plaf.html */ try { for (javax.swing.UIManager.LookAndFeelInfo info : javax.swing.UIManager.getInstalledLookAndFeels()) { if ("Nimbus".equals(info.getName())) { javax.swing.UIManager.setLookAndFeel(info.getClassName()); break; } } } catch (ClassNotFoundException ex) { java.util.logging.Logger.getLogger(MainFrame.class.getName()).log(java.util.logging.Level.SEVERE, null, ex); } catch (InstantiationException ex) { java.util.logging.Logger.getLogger(MainFrame.class.getName()).log(java.util.logging.Level.SEVERE, null, ex); } catch (IllegalAccessException ex) { java.util.logging.Logger.getLogger(MainFrame.class.getName()).log(java.util.logging.Level.SEVERE, null, ex); } catch (javax.swing.UnsupportedLookAndFeelException ex) { java.util.logging.Logger.getLogger(MainFrame.class.getName()).log(java.util.logging.Level.SEVERE, null, ex); } // /* Create and display the form */ java.awt.EventQueue.invokeLater(new Runnable() { public void run() { new MainFrame().setVisible(true); } }); } // Variables declaration - do not modify private javax.swing.JCheckBoxMenuItem jCheckBoxMenuItem1; private javax.swing.JLabel jLabel2; private javax.swing.JMenu jMenu1; private javax.swing.JMenu jMenu2; private javax.swing.JMenuBar jMenuBar1; // End of variables declaration / * @param jLabel1 the jLabel1 to set */ }
本期就到这里啦,欢迎大家留言讨论。
源码链接:俄罗斯方块源码,详情可看我博客-Java文档类资源-CSDN下载