package boggle.view; import mvc143.IBoggleView; import mvc143.IBoggleController; import boggle.controller.BoggleController; import boggle.model.BoggleModel; import java.util.List; import java.util.Iterator; import java.io.*; import javax.swing.JFrame; import javax.swing.JPanel; import javax.swing.JTextArea; import javax.swing.JOptionPane; import javax.swing.JFileChooser; import javax.swing.JScrollPane; import javax.swing.JButton; import javax.swing.JLabel; import javax.swing.BoxLayout; import java.awt.Color; import java.awt.Container; import java.awt.BorderLayout; import java.awt.FlowLayout; import java.awt.GridLayout; import java.awt.Dimension; import java.awt.Graphics; import java.awt.event.ActionListener; import java.awt.event.ActionEvent; /** * This is the visual aspect of the game of Boggle. */ public class BoggleView implements IBoggleView { public static final String author = "Kei & Vy"; public static final String description = "BoggleView provides visual aspects of the game."; private static final Color backgroundColor = new Color(255, 240, 180); private IBoggleController controller; private JFrame boggleFrame; private JPanel boardPanel; private ScorePanel scoreP; private TimePanel timeP; private StatusPanel statusP; // private HistoryList history; private JTextArea history; /** * Initializes the controller. * * @param controller which controls the process of the game. */ public BoggleView(IBoggleController controller) { this.controller = controller; boggleFrame = new JFrame("Boggle"); boggleFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); Container contents = boggleFrame.getContentPane(); contents.setBackground(backgroundColor); boardPanel = new JPanel(); boardPanel.setPreferredSize(new Dimension(300, 300)); contents.add(boardPanel, BorderLayout.CENTER); //boardPanel.add(but); //boardPanel.repaint(); JPanel northPanel = new JPanel(); northPanel.setLayout(new FlowLayout()); northPanel.add(new JLabel("Score: ")); scoreP = new ScorePanel(); scoreP.setPreferredSize(new Dimension(200, 20)); northPanel.add(scoreP); northPanel.add(new JLabel("Remaining time: ")); timeP = new TimePanel(); timeP.setPreferredSize(new Dimension(200, 20)); northPanel.add(timeP); contents.add(northPanel, BorderLayout.NORTH); // history = new HistoryList(); history = new JTextArea(); history.setPreferredSize(new Dimension(100, 200)); JScrollPane historyPane = new JScrollPane(history); contents.add(historyPane, BorderLayout.WEST); statusP = new StatusPanel(); contents.add(statusP, BorderLayout.SOUTH); JPanel eastPanel = new JPanel(); eastPanel.setLayout(new BoxLayout(eastPanel, BoxLayout.Y_AXIS)); eastPanel.add(new AboutButton()); eastPanel.add(new StartButton()); eastPanel.add(new EraseButton()); eastPanel.add(new SubmitButton()); eastPanel.add(new EndButton()); contents.add(eastPanel, BorderLayout.EAST); boggleFrame.pack(); boggleFrame.show(); } /** * shows the author and description of different modules */ public void showInfo() { JOptionPane.showMessageDialog(null, "Authors: " + author + "\n" + description + "\n" + BoggleController.description + "\n" + BoggleModel.description); } /** * This method will redisplay everything. This should only * be called from the Controller. The typical way redraw() should be implemented * (for a GUI) is for redraw to call repaint() on each of the main GUI components * which it has created. */ public void redraw() { timeP.repaint(); scoreP.repaint(); statusP.repaint(); // history.repaint(); } /** * Perform cleanup when the application is about to end. Should only * be called by the Controller. * (You don't neccessarily need to do anything, but it's an opportunity.) * */ public void terminateView() { } private class BoardButton extends JButton { private int row; private int col; public BoardButton(int ro, int co) { this.row = ro; this.col = co; int letter = BoggleView.this.controller.getLetterInBoard(ro, co); setText(String.valueOf((char) letter)); addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { BoggleView.this.controller.addToProposal(row, col); //System.out.println(row + " " + col); } }); } } private class EraseButton extends JButton { public EraseButton() { super("Erase"); setToolTipText("Erase last character from the proposed word before submission."); addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { BoggleView.this.controller.removeLetterFromProposal(); } }); } } private class SubmitButton extends JButton { public SubmitButton() { super("Submit"); setToolTipText("Submit word"); addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { if(controller.submitProposal() == 1){ BoggleView.this.controller.newProposal(); int i = controller.getWordsHistory().size() - 1; history.append((String) controller.getWordsHistory().get(i) + "\n"); } // history.repaint(); } }); } } private class StartButton extends JButton { public StartButton() { super("Start Game"); addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { boardPanel.removeAll(); Object[] boardOptions = {"Load board file", "Create random board"}; int result = JOptionPane.showOptionDialog(null, "Please choose your board option.", "Board Options", JOptionPane.YES_NO_OPTION, JOptionPane.PLAIN_MESSAGE, null, boardOptions, boardOptions[1]); if (result == JOptionPane.YES_OPTION) { BoggleView.this.controller.startGame(chooseBoardFile()); } else if (result == JOptionPane.NO_OPTION) { BoggleView.this.controller.startGame(); } // BoggleView.this.boardPanel.add(new JLabel("Hi")); int row = BoggleView.this.controller.getBoardRows(); int col = BoggleView.this.controller.getBoardCols(); boardPanel.setLayout(new GridLayout(row, col)); for (int i = 0 ; i < row; i++) { for (int j = 0; j < col; j++) { // BoggleView.this.boardPanel.add(new JLabel("Hi")); //System.out.println(row + " " + col); BoardButton boardButton = new BoardButton(i, j); BoggleView.this.boardPanel.add(boardButton); } } boggleFrame.validate(); //BoggleView.this.boardPanel.repaint(); } public String chooseBoardFile() { try { String boardName = null; JFileChooser boardChooser = new JFileChooser(); boardChooser.setDialogTitle("Choose a board file"); int result = boardChooser.showOpenDialog(null); if (result == JFileChooser.APPROVE_OPTION) { //a file was selected File board = boardChooser.getSelectedFile(); boardName = board.getAbsolutePath(); } else if (result == JFileChooser.CANCEL_OPTION) { //No file was selected BoggleView.this.controller.startGame(); } else { //Error occurs chooseBoardFile(); } return boardName; } catch (Exception e) { chooseBoardFile(); return null; } } }); } } private class EndButton extends JButton { public EndButton() { super("End Game"); addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { BoggleView.this.controller.endGame(); } }); } } private class AboutButton extends JButton { public AboutButton() { super("About"); setToolTipText("Show authors and description of the modules of this game."); addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { BoggleView.this.showInfo(); } }); } } private class ScorePanel extends JPanel { public void paintComponent(Graphics g) { super.paintComponent(g); String score = String.valueOf(BoggleView.this.controller.getScore()); //System.out.println(score); g.setColor(Color.BLACK); g.drawString(score, 10, 10); } } private class StatusPanel extends JPanel { public void paintComponent(Graphics g) { super.paintComponent(g); g.setColor(Color.BLACK); g.drawString(BoggleView.this.controller.getStatus(), 10, 10); } } private class TimePanel extends JPanel { public void paintComponent(Graphics g) { super.paintComponent(g); long timeMilliSec = BoggleView.this.controller.getMillisRemaining(); String minute = String.valueOf(timeMilliSec/60000); String second = String.valueOf((timeMilliSec % 60000) / 1000); for (int i = 0; i < 10; i++) { if (((timeMilliSec % 60000) / 1000) == i) { second = "0" + second; } } g.setColor(Color.BLACK); g.drawString(minute + ":" + second, 10, 10); } } // private class HistoryList extends JTextArea { // public void paintComponent(Graphics g) { // super.paintComponent(g); // List history = BoggleView.this.controller.getWordsHistory(); // //System.out.println(history.size()); // Iterator iter = history.iterator(); // g.setColor(Color.BLACK); // int y = 10 ; // while (iter.hasNext()) { // g.drawString((String) iter.next() + "\n", 10, y); // // iter.next(); su // y += 20; // } // } // } }