001 package breakout; 002 003 import java.awt.*; 004 import java.awt.event.*; 005 import javax.swing.*; 006 import javax.swing.border.EtchedBorder; 007 008 /** Manages the user interface for Breakout. 009 * <BR><BR> 010 * BreakoutUI manages:<ul> 011 * <li>The message/instructions bar 012 * <li>The {@link breakout.BoardPanel} 013 * <li>The Load, Start, and Stop buttons, and their associated actions:<ol> 014 * <li>Loading a Board from a text file 015 * <li>Starting the game 016 * <li>Stopping(pausing) the game 017 * </ol> 018 * <li>Loading a Board from code 019 * </ul> 020 **/ 021 public class BreakoutUI extends JFrame implements ActionListener { 022 /** The padding used to get away from the system-added borders to a JFrame. **/ 023 public static final int PADDING = 2; 024 025 private BoardPanel bp; 026 private JLabel stat; 027 028 private World world; 029 030 /** Creates a new BreakoutUI and gives it a new BoardPanel with no Board. 031 **/ 032 public BreakoutUI() { 033 super("Breakout"); 034 this.setDefaultCloseOperation(EXIT_ON_CLOSE); 035 036 // initiate widgets 037 this.stat = new JLabel(" Click \"Load\" to begin."); 038 JButton loadb = new JButton("Load"), 039 startb = new JButton("Start"), 040 quitb = new JButton("Stop"); 041 startb.addActionListener(this); 042 loadb.addActionListener(this); 043 quitb.addActionListener(this); 044 045 //initiate top panel 046 JPanel top = new JPanel(); 047 top.setLayout(new BorderLayout()); 048 top.add(this.stat, BorderLayout.WEST); 049 Dimension topSize = new Dimension(BoardPanel.PREF_WIDTH, 050 top.getSize().height + 2*BreakoutUI.PADDING); 051 052 //initiate middle panel 053 this.bp = new BoardPanel(this); 054 055 //initiate bottom panel 056 JPanel bottom = new JPanel(); 057 BoxLayout bot = new BoxLayout(bottom, BoxLayout.X_AXIS); 058 bottom.setLayout(bot); 059 bottom.add(loadb); 060 bottom.add(startb); 061 bottom.add(Box.createHorizontalGlue()); 062 bottom.add(quitb); 063 064 //put middle and bottom panels together 065 JPanel allBottom = new JPanel(); 066 BoxLayout bot2 = new BoxLayout(allBottom, BoxLayout.Y_AXIS); 067 allBottom.setLayout(bot2); 068 allBottom.add(this.bp); 069 allBottom.add(bottom); 070 Dimension allBot = new Dimension(BoardPanel.PREF_WIDTH, 071 BoardPanel.PREF_HEIGHT+loadb.getPreferredSize().height); 072 allBottom.setSize(allBot.width,allBot.height); 073 allBottom.setMaximumSize(allBot); 074 allBottom.setMinimumSize(allBot); 075 076 //put middle-bottom and top panels together 077 JPanel all = new JPanel(); 078 BoxLayout allb = new BoxLayout(all, BoxLayout.Y_AXIS); 079 all.setLayout(allb); 080 all.add(top); 081 all.add(allBottom); 082 Dimension alld = new Dimension(top.getSize().height+allBottom.getSize().height, 083 BoardPanel.PREF_WIDTH); 084 all.setSize(alld); 085 all.setMaximumSize(alld); 086 all.setMinimumSize(alld); 087 088 //add "all" panel to the ContentPane of this JFrame 089 Container thisC = this.getContentPane(); 090 thisC.setLayout(new FlowLayout()); 091 thisC.add(all); 092 093 this.pack(); 094 this.show(); 095 } 096 097 /** Sets up a new World with the specified Board and this BreakoutUI. 098 * @param b The Board object to be loaded. 099 **/ 100 public void loadBoard(Board b) { 101 this.world = new World(b, this); 102 this.bp.repaint(); 103 this.stat.setText(" Press \"Start\" to play."); 104 } 105 /** Loads a new Board from a properly formatted text file. 106 **/ 107 public void loadBoard() { 108 Board b = new LoaderUI(this, ".").load(); 109 if(b != null) this.loadBoard(b); 110 } 111 112 /** Winning the game. 113 * Stops the World thread, and puts the appropriate message in the message box. 114 **/ 115 public void win() { 116 this.world.stop(); 117 this.stat.setText(" You won!"); 118 } 119 /** Losing the game. 120 * Stops the World thread, and puts the appropriate message in the message box. 121 **/ 122 public void lose() { 123 this.world.stop(); 124 this.stat.setText(" You lost."); 125 } 126 127 /** Gets the World used by this BreakoutUI. 128 * @return a label for the World object used by this BreakoutUI. 129 **/ 130 public World getWorld() { 131 return this.world; 132 } 133 /** Gets the BoardPanel used by this BreakoutUI. 134 * @return a label for the BoardPanel object used by this BreakoutUI. 135 **/ 136 public BoardPanel getBoardPanel() { 137 return this.bp; 138 } 139 140 /** Manages button presses. **/ 141 public void actionPerformed(ActionEvent ae) { 142 if(ae.getActionCommand().equals("Load")) { 143 this.loadBoard(); 144 } else if(ae.getActionCommand().equals("Start")) { 145 if(this.world != null) { 146 this.world.start(); 147 this.stat.setText(" "); 148 } else { 149 System.err.println("BreakoutUI Error: Load board before pressing \"Start\"."); 150 this.stat.setText(" Please press \"Load\" first."); 151 } 152 } else if(ae.getActionCommand().equals("Stop")) { 153 if(this.world != null) { 154 this.world.stop(); 155 } 156 } 157 } 158 }