View Javadoc
1   ////////////////////////////////////////////////////////////////////////////////
2   // checkstyle: Checks Java source code for adherence to a set of rules.
3   // Copyright (C) 2001-2017 the original author or authors.
4   //
5   // This library is free software; you can redistribute it and/or
6   // modify it under the terms of the GNU Lesser General Public
7   // License as published by the Free Software Foundation; either
8   // version 2.1 of the License, or (at your option) any later version.
9   //
10  // This library is distributed in the hope that it will be useful,
11  // but WITHOUT ANY WARRANTY; without even the implied warranty of
12  // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13  // Lesser General Public License for more details.
14  //
15  // You should have received a copy of the GNU Lesser General Public
16  // License along with this library; if not, write to the Free Software
17  // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
18  ////////////////////////////////////////////////////////////////////////////////
19  
20  package com.puppycrawl.tools.checkstyle.gui;
21  
22  import java.awt.BorderLayout;
23  import java.awt.GridLayout;
24  import java.awt.event.ActionEvent;
25  import java.awt.event.KeyEvent;
26  import java.io.File;
27  
28  import javax.swing.AbstractAction;
29  import javax.swing.BorderFactory;
30  import javax.swing.JButton;
31  import javax.swing.JComboBox;
32  import javax.swing.JFileChooser;
33  import javax.swing.JFrame;
34  import javax.swing.JLabel;
35  import javax.swing.JOptionPane;
36  import javax.swing.JPanel;
37  import javax.swing.JScrollPane;
38  import javax.swing.JSplitPane;
39  import javax.swing.JTextArea;
40  import javax.swing.SwingConstants;
41  import javax.swing.filechooser.FileFilter;
42  
43  import com.puppycrawl.tools.checkstyle.api.CheckstyleException;
44  import com.puppycrawl.tools.checkstyle.gui.MainFrameModel.ParseMode;
45  
46  /**
47   * Displays information about a parse tree.
48   * The user can change the file that is parsed and displayed
49   * using a JFileChooser.
50   *
51   * @author Lars K├╝hne
52   * @author Vladislav Lisetskiy
53   * @noinspection MagicNumber
54   */
55  public class MainFrame extends JFrame {
56  
57      private static final long serialVersionUID = 7970053543351871890L;
58  
59      /** Checkstyle frame model. */
60      private final transient MainFrameModel model = new MainFrameModel();
61      /** Reload action. */
62      private final ReloadAction reloadAction = new ReloadAction();
63      /** Code text area. */
64      private JTextArea textArea;
65      /** Tree table. */
66      private TreeTable treeTable;
67  
68      /** Create a new MainFrame. */
69      public MainFrame() {
70          createContent();
71      }
72  
73      /** Create content of this MainFrame. */
74      private void createContent() {
75          setLayout(new BorderLayout());
76  
77          textArea = new JTextArea(20, 15);
78          textArea.setEditable(false);
79          final JScrollPane textAreaScrollPane = new JScrollPane(textArea);
80  
81          treeTable = new TreeTable(model.getParseTreeTableModel());
82          treeTable.setEditor(textArea);
83          treeTable.setLinePositionMap(model.getLinesToPosition());
84          final JScrollPane treeTableScrollPane = new JScrollPane(treeTable);
85  
86          final JSplitPane splitPane = new JSplitPane(JSplitPane.VERTICAL_SPLIT, treeTableScrollPane,
87              textAreaScrollPane);
88          add(splitPane, BorderLayout.CENTER);
89          splitPane.setResizeWeight(0.7);
90  
91          add(createButtonsPanel(), BorderLayout.PAGE_END);
92  
93          pack();
94      }
95  
96      /**
97       * Create buttons panel.
98       * @return buttons panel.
99       */
100     private JPanel createButtonsPanel() {
101         final JButton openFileButton = new JButton(new FileSelectionAction());
102         openFileButton.setMnemonic(KeyEvent.VK_S);
103         openFileButton.setText("Open File");
104 
105         reloadAction.setEnabled(false);
106         final JButton reloadFileButton = new JButton(reloadAction);
107         reloadFileButton.setMnemonic(KeyEvent.VK_R);
108         reloadFileButton.setText("Reload File");
109 
110         final JComboBox<ParseMode> modesCombobox = new JComboBox<>(ParseMode.values());
111         modesCombobox.setSelectedIndex(0);
112         modesCombobox.addActionListener(e -> {
113             model.setParseMode((ParseMode) modesCombobox.getSelectedItem());
114             reloadAction.actionPerformed(null);
115         });
116 
117         final JLabel modesLabel = new JLabel("Modes:", SwingConstants.RIGHT);
118         final int leftIndentation = 10;
119         modesLabel.setBorder(BorderFactory.createEmptyBorder(0, leftIndentation, 0, 0));
120 
121         final JPanel buttonPanel = new JPanel();
122         buttonPanel.setLayout(new GridLayout(1, 2));
123         buttonPanel.add(openFileButton);
124         buttonPanel.add(reloadFileButton);
125 
126         final JPanel modesPanel = new JPanel();
127         modesPanel.add(modesLabel);
128         modesPanel.add(modesCombobox);
129 
130         final JPanel mainPanel = new JPanel();
131         mainPanel.setLayout(new BorderLayout());
132         mainPanel.add(buttonPanel);
133         mainPanel.add(modesPanel, BorderLayout.LINE_END);
134 
135         return mainPanel;
136     }
137 
138     /**
139      * Open file and load it.
140      * @param sourceFile the file to open.
141      */
142     public void openFile(File sourceFile) {
143         try {
144             model.openFile(sourceFile);
145             setTitle(model.getTitle());
146             reloadAction.setEnabled(model.isReloadActionEnabled());
147             textArea.setText(model.getText());
148             treeTable.setLinePositionMap(model.getLinesToPosition());
149         }
150         catch (final CheckstyleException ex) {
151             JOptionPane.showMessageDialog(this, ex.getMessage());
152         }
153     }
154 
155     /**
156      * Handler for file selection action events.
157      */
158     private class FileSelectionAction extends AbstractAction {
159         private static final long serialVersionUID = 1762396148873280589L;
160 
161         @Override
162         public void actionPerformed(ActionEvent event) {
163             final JFileChooser fileChooser = new JFileChooser(model.getLastDirectory());
164             final FileFilter filter = new JavaFileFilter();
165             fileChooser.setFileFilter(filter);
166 
167             final int returnCode = fileChooser.showOpenDialog(MainFrame.this);
168             if (returnCode == JFileChooser.APPROVE_OPTION) {
169                 final File file = fileChooser.getSelectedFile();
170                 openFile(file);
171             }
172         }
173     }
174 
175     /**
176      * Handler for reload action events.
177      */
178     private class ReloadAction extends AbstractAction {
179         private static final long serialVersionUID = -890320994114628011L;
180 
181         @Override
182         public void actionPerformed(ActionEvent event) {
183             openFile(model.getCurrentFile());
184         }
185     }
186 
187     /**
188      * Filter for Java files.
189      */
190     private static class JavaFileFilter extends FileFilter {
191         @Override
192         public boolean accept(File file) {
193             return MainFrameModel.shouldAcceptFile(file);
194         }
195 
196         @Override
197         public String getDescription() {
198             return "Java Source File";
199         }
200     }
201 }