package view.panels; import model.Line; import presenter.Presenter; import view.MainFrame; import view.custom.ButtonGroupAtLeastTwo; import view.custom.ColorColumnRenderer; import javax.swing.*; import javax.swing.border.TitledBorder; import javax.swing.filechooser.FileNameExtensionFilter; import javax.swing.filechooser.FileSystemView; import javax.swing.table.DefaultTableModel; import javax.swing.table.JTableHeader; import javax.swing.table.TableColumn; import java.awt.*; import java.io.File; import java.util.ArrayList; import java.util.Arrays; import java.util.LinkedList; /** * Created by * Armin Wolf * on 02.08.17. */ public class EvaluationPanel extends JPanel { private final MainFrame view; private JTable table; private JTableHeader header; private JButton start; private JButton latexExport; private JButton clearTable; private JButton exportData; private JRadioButton evalTypeOne; //1: Alg - N: Data private JRadioButton evalTypeTwo; //N: Alg - 1: Data private ButtonGroup radiobuttonGroup; private ButtonGroup checkboxGroup; private ButtonGroupAtLeastTwo checkboxAtLeastOne; private JCheckBox lms; //1: Alg - N: Data private JCheckBox rm; //N: Alg - 1: Data private JCheckBox ts; //1: Alg - N: Data private JPanel comp; private JPanel algorithmPanel; private JPanel leftSidePanel; private JPanel datasetCount; private JComboBox datasetCountChoice; private JComboBox datasetType; private JLabel datasetCountLabel; private JSplitPane splitPane; private DefaultTableModel model; private int currentRowOfTypes; private JPanel buttonPanel; private PlotPanel plotPanel; private String[] selections = {"Approximationsgüte", "Least Median of Squares", "Repeated-Median", "Theil-Sen"}; public EvaluationPanel(MainFrame view) { super(); this.view = view; this.setLayout(new BorderLayout()); this.currentRowOfTypes = 0; init(); addListener(); addComponents(); } private void init() { datasetCountLabel = new JLabel("Größe des Datensatzes"); Integer[] choice = {50, 100, 200, 500, 1000, 1500}; datasetCountChoice = new JComboBox(choice); String[] datatypes = {"Punktwolke", "Gerade", "Kreis und Gerade"}; datasetType = new JComboBox<>(datatypes); start = new JButton("Start"); latexExport = new JButton("LaTex Export"); clearTable = new JButton("Löschen"); exportData = new JButton("Datenexport"); latexExport.setEnabled(false); clearTable.setEnabled(false); exportData.setEnabled(false); evalTypeOne = new JRadioButton("Algorithmus evaluieren"); evalTypeTwo = new JRadioButton("Algorithmen vergleichen"); lms = new JCheckBox("Least Median of Squares"); rm = new JCheckBox("Repeated Median"); ts = new JCheckBox("Theil-Sen"); radiobuttonGroup = new ButtonGroup(); checkboxGroup = new ButtonGroup(); checkboxAtLeastOne = new ButtonGroupAtLeastTwo(); buttonPanel = new JPanel(new FlowLayout()); leftSidePanel = new JPanel(new BorderLayout()); comp = new JPanel(new GridLayout(0, 1)); plotPanel = new PlotPanel(); model = new DefaultTableModel() { @Override public boolean isCellEditable(int row, int column) { //all cells false return false; } }; table = new JTable(model); UIManager.put("TableHeader.font", new Font("SansSerif", Font.BOLD, 14)); UIManager.put("TableHeader.foreground", Color.WHITE); header = table.getTableHeader(); header.setBackground(Color.GRAY); splitPane = new JSplitPane(); algorithmPanel = new JPanel(new FlowLayout(FlowLayout.LEFT)); datasetCount = new JPanel(new FlowLayout(FlowLayout.LEFT)); } private void addComponents() { evalTypeOne.setSelected(true); lms.setSelected(true); checkboxGroup.add(lms); checkboxGroup.add(rm); checkboxGroup.add(ts); radiobuttonGroup.add(evalTypeOne); radiobuttonGroup.add(evalTypeTwo); buttonPanel.add(start); buttonPanel.add(clearTable); buttonPanel.add(exportData); buttonPanel.add(latexExport); algorithmPanel.add(lms); algorithmPanel.add(rm); algorithmPanel.add(ts); datasetCount.add(datasetCountLabel); datasetCount.add(datasetCountChoice); datasetCount.add(datasetType); comp.add(evalTypeOne); comp.add(evalTypeTwo); comp.add(algorithmPanel); comp.add(datasetCount); comp.setBorder(new TitledBorder("Konfiguration")); //Tabelle model.setColumnIdentifiers(selections); table.setDragEnabled(true); JScrollPane scrollPane = new JScrollPane(table); scrollPane.setWheelScrollingEnabled(true); scrollPane.setBorder(new TitledBorder("Ergebnisse")); //Plot plotPanel.createPlot(new LinkedList<>()); plotPanel.setBorder(new TitledBorder("Plot")); leftSidePanel.add(comp, BorderLayout.NORTH); leftSidePanel.add(scrollPane, BorderLayout.CENTER); //Splitpane splitPane.setOrientation(JSplitPane.HORIZONTAL_SPLIT); splitPane.setResizeWeight(.5d); splitPane.setContinuousLayout(true); splitPane.setLeftComponent(leftSidePanel); splitPane.setRightComponent(plotPanel); this.add(splitPane, BorderLayout.CENTER); this.add(buttonPanel, BorderLayout.SOUTH); TableColumn tm = table.getColumnModel().getColumn(0); tm.setCellRenderer(new ColorColumnRenderer(Color.lightGray, Color.blue)); } private void addListener() { start.addActionListener(e -> { int type; int alg; int n; if (radiobuttonGroup.isSelected(evalTypeOne.getModel())) { type = 0; } else { type = 1; } alg = checkSelection(); n = (Integer) datasetCountChoice.getSelectedItem(); String datatyp = (String) datasetType.getSelectedItem(); ((Presenter) view.getPresenter()).startEvaluation(type, n, alg, datatyp); clearTable.setEnabled(true); latexExport.setEnabled(true); exportData.setEnabled(true); }); evalTypeOne.addActionListener(e -> { checkboxAtLeastOne.remove(lms); checkboxAtLeastOne.remove(rm); checkboxAtLeastOne.remove(ts); lms.setSelected(true); checkboxGroup.add(lms); checkboxGroup.add(rm); checkboxGroup.add(ts); }); evalTypeTwo.addActionListener(e -> { checkboxGroup.remove(lms); checkboxGroup.remove(rm); checkboxGroup.remove(ts); checkboxAtLeastOne.addAll(lms, rm, ts); lms.setSelected(true); rm.setSelected(true); }); latexExport.addActionListener(e -> { SwingUtilities.invokeLater(() -> { File file = null; JFileChooser chooser = new JFileChooser(FileSystemView.getFileSystemView().getHomeDirectory()); chooser.setPreferredSize(new Dimension(800, 700)); chooser.setFileFilter(new FileNameExtensionFilter("LaTeX-Datei", "tex", "text")); chooser.setMultiSelectionEnabled(false); chooser.setFileSelectionMode(JFileChooser.FILES_ONLY); if (chooser.showSaveDialog(this) == JFileChooser.APPROVE_OPTION) { //System.out.println ("Datei "+chooser.getSelectedFile()+ " ausgewählt."); file = chooser.getSelectedFile(); String filename = file.getAbsolutePath().contains(".tex") ? file.getAbsolutePath() : file.getAbsolutePath().concat(".tex"); File withExtension = new File(filename); final File input = withExtension; ((Presenter) view.getPresenter()).startResultExport(model, input); } }); }); clearTable.addActionListener(e -> { SwingUtilities.invokeLater(() -> { int n = model.getDataVector().size(); for (int i = 0; i < n; i++) { model.removeRow(0); currentRowOfTypes--; } this.revalidate(); latexExport.setEnabled(false); clearTable.setEnabled(false); exportData.setEnabled(false); }); }); exportData.addActionListener(e -> { SwingUtilities.invokeLater(() -> { JOptionPane.showMessageDialog(this, "Boooooooooooooooooooooooooooooooooooooooooooooooooooooo! :)"); }); }); } public void addColumn(Object[] data, int col, boolean b) { if (b) { addBlankRows(data.length); } for (int i = 0; i < data.length; i++) { int row = currentRowOfTypes - data.length + i; model.setValueAt(data[i], row, col); } this.repaint(); this.revalidate(); } public void addRow(Object[] data) { addBlankRows(1); for (int i = 0; i < 4; i++) { model.setValueAt(data[i], currentRowOfTypes, i); } currentRowOfTypes++; this.repaint(); this.revalidate(); } public void drawLines(ArrayList alg) { Paint[] color = {Color.ORANGE, Color.RED, Color.MAGENTA}; String[] name = {"LMS", "RM", "TS"}; for (Double[] o : alg) { int i = o[0].intValue(); Double m = o[1]; Double b = o[2]; plotPanel.addLineToPlot(m, b, color[i], name[i]); } } public void drawLines(Object[] results, int alg) { String[] castedResults = Arrays.copyOf(results, results.length, String[].class); Paint[] color = {Color.ORANGE, Color.RED, Color.MAGENTA}; String[] name = {"LMS", "RM", "TS"}; String[] nName = {"Brute-force LMS", "Brute-force RM", "Brute-force TS"}; Double m = Double.parseDouble(castedResults[0]); Double b = Double.parseDouble(castedResults[1]); plotPanel.addLineToPlot(m, b, color[alg], name[alg]); Double nM = Double.parseDouble(castedResults[2]); Double nB = Double.parseDouble(castedResults[3]); plotPanel.addLineToPlot(nM, nB, Color.BLACK, nName[alg]); } public void setDualPoints(LinkedList points) { plotPanel = new PlotPanel(); plotPanel.setBorder(new TitledBorder("Plot")); splitPane.setRightComponent(plotPanel); plotPanel.createPlot(points); plotPanel.repaint(); plotPanel.revalidate(); } private void addBlankRows(int n) { for (int i = 0; i < n; i++) { String[] tmp = {"", "", "", "",}; model.addRow(tmp); } } public void setCurrentRow(int val) { this.currentRowOfTypes += val; } private int checkSelection() { if (lms.isSelected() && rm.isSelected() && ts.isSelected()) { return 6; } else if (!lms.isSelected() && rm.isSelected() && ts.isSelected()) { return 5; } else if (lms.isSelected() && !rm.isSelected() && ts.isSelected()) { return 4; } else if (lms.isSelected() && rm.isSelected() && !ts.isSelected()) { return 3; } else if (!lms.isSelected() && !rm.isSelected() && ts.isSelected()) { return 2; } else if (!lms.isSelected() && rm.isSelected() && !ts.isSelected()) { return 1; } else if (lms.isSelected() && !rm.isSelected() && !ts.isSelected()) { return 0; } else { throw new IllegalStateException("Mindestens ein Algortihmus muss selektiert werden"); } } }