Java tutorial
/* * Maui, Maltcms User Interface. * Copyright (C) 2008-2014, The authors of Maui. All rights reserved. * * Project website: http://maltcms.sf.net * * Maui may be used under the terms of either the * * GNU Lesser General Public License (LGPL) * http://www.gnu.org/licenses/lgpl.html * * or the * * Eclipse Public License (EPL) * http://www.eclipse.org/org/documents/epl-v10.php * * As a user/recipient of Maui, you may choose which license to receive the code * under. Certain files or entire directories may not be covered by this * dual license, but are subject to licenses compatible to both LGPL and EPL. * License exceptions are explicitly declared in all relevant files or in a * LICENSE file in the relevant directories. * * Maui is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS * FOR A PARTICULAR PURPOSE. Please consult the relevant license documentation * for details. */ package maltcms.ui.fileHandles.csv; import cross.datastructures.tuple.Tuple2D; import cross.datastructures.tools.EvalTools; import maltcms.io.csv.ColorRampReader; import maltcms.tools.ImageTools; import java.util.ArrayList; import java.util.Collections; import java.util.Comparator; import java.util.List; import java.util.logging.Level; import java.util.logging.Logger; import javax.swing.table.DefaultTableModel; import maltcms.ui.charts.GradientPaintScale; import maltcms.ui.fileHandles.serialized.JFCTopComponent; import org.jfree.chart.JFreeChart; import org.jfree.chart.axis.NumberAxis; import org.jfree.chart.axis.SymbolAxis; import org.jfree.chart.labels.XYToolTipGenerator; import org.jfree.chart.plot.XYPlot; import org.jfree.chart.renderer.xy.XYBlockRenderer; import org.jfree.chart.renderer.xy.XYLineAndShapeRenderer; import org.jfree.chart.title.PaintScaleLegend; import org.jfree.data.xy.DefaultXYZDataset; import org.jfree.data.xy.XYDataset; import org.jfree.data.xy.XYSeries; import org.jfree.data.xy.XYSeriesCollection; import org.jfree.data.xy.XYZDataset; import org.jfree.ui.RectangleEdge; import org.netbeans.api.progress.ProgressHandle; import org.netbeans.api.progress.ProgressHandleFactory; import org.openide.filesystems.FileObject; import org.openide.util.Exceptions; import org.openide.util.RequestProcessor; import org.openide.util.Task; import ucar.ma2.ArrayDouble; /** * * @author nilshoffmann */ public class CSV2JFCLoader implements Runnable { private FileObject is = null; private ProgressHandle ph = null; private JFCTopComponent jtc = null; private String title = ""; private enum CHART { MATRIX, PEAKS, ALIGNMENT, XY; } private CHART mode = CHART.XY; /** * * @param m * @param jtc */ public void load(CSVDataObject m, JFCTopComponent jtc) { Logger.getLogger(getClass().getName()).info("Load"); this.ph = ProgressHandleFactory.createHandle("Loading file " + m.getPrimaryFile().getName()); this.is = m.getPrimaryFile(); this.title = m.getPrimaryFile().getName(); if (this.title.equals("pairwise_distances")) { this.mode = CHART.MATRIX; } this.jtc = jtc; jtc.setDisplayName(this.title); Task task = new Task(this); RequestProcessor.getDefault().post(task); } @Override public void run() { CSV2TableLoader tl = new CSV2TableLoader(this.ph, this.is); DefaultTableModel dtm; try { dtm = tl.call(); if (this.mode == CHART.XY) { XYSeriesCollection cd = new XYSeriesCollection(); for (int j = 0; j < dtm.getColumnCount(); j++) { XYSeries xys = new XYSeries(dtm.getColumnName(j)); for (int i = 0; i < dtm.getRowCount(); i++) { Object o = dtm.getValueAt(i, j); try { double d = Double.parseDouble(o.toString()); xys.add(i, d); Logger.getLogger(getClass().getName()).log(Level.INFO, "Adding {0} {1} {2}", new Object[] { i, d, dtm.getColumnName(j) }); } catch (Exception e) { } } cd.addSeries(xys); } XYLineAndShapeRenderer d = new XYLineAndShapeRenderer(true, false); XYPlot xyp = new XYPlot(cd, new NumberAxis("category"), new NumberAxis("value"), d); JFreeChart jfc = new JFreeChart(this.title, xyp); jtc.setChart(jfc); Logger.getLogger(getClass().getName()).info("creating chart done"); } else if (this.mode == CHART.MATRIX) { DefaultXYZDataset cd = new DefaultXYZDataset(); Logger.getLogger(getClass().getName()).log(Level.INFO, "Name of column 0: {0}", dtm.getColumnName(0)); if (dtm.getColumnName(0).isEmpty()) { Logger.getLogger(getClass().getName()).info("Removing column 0"); dtm = removeColumn(dtm, 0); } if (dtm.getColumnName(dtm.getColumnCount() - 1).equalsIgnoreCase("filename")) { dtm = removeColumn(dtm, dtm.getColumnCount() - 1); } StringBuilder sb = new StringBuilder(); for (int i = 0; i < dtm.getRowCount(); i++) { for (int j = 0; j < dtm.getColumnCount(); j++) { sb.append(dtm.getValueAt(i, j) + " "); } sb.append("\n"); } Logger.getLogger(getClass().getName()).log(Level.INFO, "Table before sorting: {0}", sb.toString()); // dtm = sort(dtm); StringBuilder sb2 = new StringBuilder(); for (int i = 0; i < dtm.getRowCount(); i++) { for (int j = 0; j < dtm.getColumnCount(); j++) { sb2.append(dtm.getValueAt(i, j) + " "); } sb2.append("\n"); } Logger.getLogger(getClass().getName()).log(Level.INFO, "Table after sorting: {0}", sb2.toString()); int rows = dtm.getRowCount(); int columns = dtm.getColumnCount(); Logger.getLogger(getClass().getName()).log(Level.INFO, "Storing {0} * {1} elements, {2} total!", new Object[] { columns, rows, rows * columns }); double[][] data = new double[3][(columns * rows)]; ArrayDouble.D1 dt = new ArrayDouble.D1((columns) * rows); double min = Double.POSITIVE_INFINITY; double max = Double.NEGATIVE_INFINITY; EvalTools.eqI(rows, columns, this); int k = 0; for (int i = 0; i < dtm.getRowCount(); i++) { for (int j = 0; j < dtm.getColumnCount(); j++) { Object o = dtm.getValueAt(i, j); try { double d = Double.parseDouble(o.toString()); if (d < min) { min = d; } if (d > max) { max = d; } data[0][k] = (double) i; data[1][k] = (double) j; data[2][k] = d; dt.set(k, d); k++; //System.out.println("Adding "+i+" "+d+" "+dtm.getColumnName(j)); } catch (Exception e) { } } //cd.addSeries(xys); } cd.addSeries(this.title, data); XYBlockRenderer xyb = new XYBlockRenderer(); GradientPaintScale ps = new GradientPaintScale(ImageTools.createSampleTable(256), min, max, ImageTools .rampToColorArray(new ColorRampReader().readColorRamp("res/colorRamps/bcgyr.csv"))); xyb.setPaintScale(ps); final String[] colnames = new String[dtm.getColumnCount()]; for (int i = 0; i < colnames.length; i++) { colnames[i] = dtm.getColumnName(i); } NumberAxis na1 = new SymbolAxis("category", colnames); na1.setVerticalTickLabels(false); NumberAxis na2 = new SymbolAxis("category", colnames); na1.setVerticalTickLabels(true); XYPlot xyp = new XYPlot(cd, na1, na2, xyb); xyb.setSeriesToolTipGenerator(0, new XYToolTipGenerator() { @Override public String generateToolTip(XYDataset xyd, int i, int i1) { return "[" + colnames[xyd.getX(i, i1).intValue()] + ":" + colnames[xyd.getY(i, i1).intValue()] + "] = " + ((XYZDataset) xyd).getZValue(i, i1) + ""; } }); JFreeChart jfc = new JFreeChart(this.title, xyp); NumberAxis values = new NumberAxis("value"); values.setAutoRange(false); values.setRangeWithMargins(min, max); PaintScaleLegend psl = new PaintScaleLegend(ps, values); psl.setBackgroundPaint(jfc.getBackgroundPaint()); jfc.addSubtitle(psl); psl.setStripWidth(50); psl.setPadding(20, 20, 20, 20); psl.setHeight(200); psl.setPosition(RectangleEdge.RIGHT); jtc.setChart(jfc); } } catch (Exception ex) { Exceptions.printStackTrace(ex); } ph.finish(); } private DefaultTableModel sort(DefaultTableModel dtm) { DefaultTableModel tmp = dtm; for (int i = 0; i < tmp.getRowCount(); i++) { int[] permutation = getRanksDescending(tmp, i); //System.out.println("Cost of permutation: " + getPermutationCost(permutation) + " on column " + i); //System.out.println("Permutation: "+Arrays.toString(permutation)); tmp = sortByRows(tmp, permutation); tmp = sortByColumns(tmp, permutation); } return tmp; } private int[] getMinCostPermutation(DefaultTableModel dtm, int from) { int minPermCost = Integer.MAX_VALUE; int[] minPerm = null; for (int i = 0; i < dtm.getRowCount(); i++) { int[] permutation = getRanksDescending(dtm, i); int pc = getPermutationCost(permutation); //System.out.println("Permutation: "+Arrays.toString(permutation)); //exclude trivial case of identity permutation if (pc < minPermCost && pc > 0 && i >= from) { //System.out.println("Cost of permutation: "+pc+ " on column "+i); minPermCost = pc; minPerm = permutation; } } return minPerm; } private int getPermutationCost(int[] permutation) { int s = 0; for (int i = 0; i < permutation.length; i++) { s += (Math.abs(i - permutation[i])); } return s; } private int[] getRanksDescending(DefaultTableModel dtm, int column) { int rows = dtm.getRowCount(); int[] ranks = new int[rows]; List<Tuple2D<Double, Integer>> valueToIndex = new ArrayList<>(); for (int i = 0; i < rows; i++) { Object o = dtm.getValueAt(i, column); if (o instanceof Double) { Double d = (Double) o; valueToIndex.add(new Tuple2D<>(d, i)); } else if (o instanceof String) { Double d = Double.parseDouble((String) o); valueToIndex.add(new Tuple2D<>(d, i)); } } Collections.sort(valueToIndex, new Comparator<Tuple2D<Double, Integer>>() { @Override public int compare(Tuple2D<Double, Integer> t, Tuple2D<Double, Integer> t1) { return t.getFirst().compareTo(t1.getFirst()); } }); for (int i = 0; i < ranks.length; i++) { ranks[i] = valueToIndex.get(i).getSecond(); } return ranks; } private DefaultTableModel sortByRows(DefaultTableModel dtm, int[] permutation) { Object[][] modelByRows = new Object[dtm.getRowCount()][dtm.getColumnCount()]; for (int i = 0; i < dtm.getRowCount(); i++) { modelByRows[i] = new Object[dtm.getColumnCount()]; for (int j = 0; j < dtm.getColumnCount(); j++) { Object o = dtm.getValueAt(permutation[i], j); //if(o instanceof Double) { modelByRows[i][j] = o; //} } } Object[] names = new Object[dtm.getRowCount()]; for (int i = 0; i < dtm.getRowCount(); i++) { names[i] = dtm.getColumnName(permutation[i]); } Logger.getLogger(getClass().getName()).log(Level.INFO, "Table model has {0} rows and {1} columns with {2} labels", new Object[] { modelByRows.length, modelByRows[0].length, names.length }); return new DefaultTableModel(modelByRows, names); } private DefaultTableModel sortByColumns(DefaultTableModel dtm, int[] permutation) { Object[][] modelByRows = new Object[dtm.getRowCount()][dtm.getColumnCount()]; for (int i = 0; i < dtm.getRowCount(); i++) { modelByRows[i] = new Object[dtm.getColumnCount()]; for (int j = 0; j < dtm.getColumnCount(); j++) { Object o = dtm.getValueAt(i, permutation[j]); //if(o instanceof Double) { modelByRows[i][j] = o; //} } } Object[] names = new Object[dtm.getRowCount()]; for (int i = 0; i < dtm.getRowCount(); i++) { names[i] = dtm.getColumnName(permutation[i]); } Logger.getLogger(getClass().getName()).log(Level.INFO, "Table model has {0} rows and {1} columns with {2} labels", new Object[] { modelByRows.length, modelByRows[0].length, names.length }); return new DefaultTableModel(modelByRows, names); } private DefaultTableModel removeColumn(DefaultTableModel dtm, int column) { Object[][] data = new Object[dtm.getRowCount()][dtm.getColumnCount() - 1]; Object[] names = new Object[dtm.getColumnCount() - 1]; int cnt = 0; for (int j = 0; j < dtm.getColumnCount(); j++) { if (j != column) { names[cnt++] = dtm.getColumnName(j); } } for (int i = 0; i < dtm.getRowCount(); i++) { cnt = 0; for (int j = 0; j < dtm.getColumnCount(); j++) { if (j != column) { data[i][cnt++] = dtm.getValueAt(i, j); } } } Logger.getLogger(getClass().getName()).log(Level.INFO, "Table model has {0} rows and {1} columns with {2} labels", new Object[] { data.length, data[0].length, names.length }); return new DefaultTableModel(data, names); } }