Aventuras con JavaFX 1.3 y NetBean 6.9
Bueno, después de una larga espera Oracle nos trae JavaFX 1.3. El entorno de ejecución promete muchas mejoras, lo único es que el entorno de desarrollo es NetBeans 6.9 BETA.
Si, beta. Tiene una lista de problemas (entre esos la depuración de programas). Sin embargo, si escribo mis ‘unit tests’ debería estar más o menos bien, ¿no es así?
Lo primero que intenté hacer es convertir el método ‘main’ de una de mis clases en Java (no JavaFX) a Junit:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 | /* * Helper class used to parse and process CVS data comming from an InputStream * License: GPL * @author josevnz at kodegeek dot com */ package com.kodegeek.blog.javafx.workout.app; import java.io.BufferedReader; import java.io.File; import java.io.FileInputStream; import java.io.InputStream; import java.io.InputStreamReader; import java.text.SimpleDateFormat; import java.util.ArrayList; import java.util.Date; import java.util.List; import java.util.regex.Pattern; /** * * @author josevnz */ final public class CsvDataParser { private List <list <Object>>data; private static final Pattern splitPattern = Pattern.compile(",\\s*"); private SimpleDateFormat format; private Pattern skipNonNumberPatter = Pattern.compile("^\\D+"); /** * Expected default number of data observations */ public static final int DEFAULT_DAY_COUNT = 365; /** * Expected default number of series to display on the same chart */ public static final int DEFAULT_SERIES = 50; /** * Constructor * @param numSeries expected number of series on the stream */ public CsvDataParser(int numSeries) { /* * Ddata is a list of lists where: * data(0): List of dates * data(n): Values of each series. * data is a rectangular array, every value matches a date */ data = new ArrayList</list><list <Object>>(); List<object> dates = new ArrayList</object><object>(); data.add(0, dates); for (int i = 1; i < numSeries; i++) { List<Object> values = new ArrayList</object><object>(); data.add(i, values); } format = new SimpleDateFormat("MM/dd/yy"); } /** * Parse a given input stream for data. Not thread safe. It is assumed than * the number of tokens on the stream is constant and there * are no data holes. The caller is responsible from closing the stream * @param io The data source * @throws Exception If there is a problem reading the stream */ public void parse(InputStream io) throws Exception { BufferedReader lineRdr = new BufferedReader(new InputStreamReader(io)); String line = null; try { while ((line = lineRdr.readLine()) != null) { if (skipNonNumberPatter.matcher(line).find()) { continue; } String[] tokens = splitPattern.split(line, -1); int numSeries = tokens.length; if (numSeries ==0 || tokens[0] == null) { return; } if (numSeries != data.size()) { String error = String.format( "Number of expected tokens is %s, got %s", data.size(), numSeries); throw new Exception(error); } // Store dates as numbers, let the caller do any conversions List</object><object> dates = (List</object><object>) data.get(0); dates.add(format.parse(tokens[0]).getTime()); // Get the values for each series now (rest of the tokens) for (int i = 1; i < numSeries; i++) { List<Object> values = (List</object><object>) data.get(i); values.add(Float.parseFloat(tokens[i])); } } } catch (Exception exp) { throw exp; } } /** * Get the collected data as a List of Lists. First element of the returned * list contains the dates as Epoch long dates, after that the series * @return Array of dates as epoch long */ public Long [] getDates() { return data.get(0).toArray(new Long[0]); } /** * Get the values as a list of * @param index Valid ranges go from 1 to n * @return Array of float series values */ public Float [] getSeriesValues(int index) { if (index < 1 || index > data.size()) { throw new IllegalArgumentException( String.format("Invalid series index %d", index)); } return data.get(index).toArray(new Float[0]); } /** * Unit test, show how the parser works on a CSV file. THIS SHOULD BE A * JUNIT TEST INSTEAD!!! * Program expects the property. * @param args List of files to parse. Each one like: numTokens:fullpathFile * @throws Exception If there are any problems */ public static void main(final String [] tokens) throws Exception { for (String token: tokens) { String [] parts = token.split(":", -1); InputStream in = null; try { int nTokens = Integer.parseInt(parts[0]); File f = new File(parts[1]); if (f.canRead() && f.isFile()) { in = new FileInputStream(f); CsvDataParser instance = new CsvDataParser(nTokens); instance.parse(in); in.close(); Long [] dates = instance.getDates(); Float [] values = instance.getSeriesValues(1); for (int i = 0; i < dates.length; i++) { System.out.println( String.format("%s -> %s", new Date(dates[i]), values[i])); } } } catch (NumberFormatException nfe) { System.err.println( String.format( "Invalid expected token value: '%s'", parts[0])); } catch (Exception exp) { throw exp; } finally { if (in != null) { in.close(); } } } } } </object></list> |
Sin embargo la interfaz gráfica me abofetea con este error: No tests root folder was found
Que fastidio. No soy un experto en NetBeans (me defiendo mucho más con Eclipse), así que en vez de estar echando código ando resolviendo estos problemas. ¡Que perdida de tiempo!
Me pregunto si Oracle piensa competir en serio con Adobe Flash si su editor principal aún tiene este tipo de problemas.
Amanecerá y veremos, por los momentos ando tratando de resolver el asunto yo mismo, al mismo tiempo pedí ayuda en los foros oficiales. Una vez resuelto, podré correr Junit para JavaFX como lo indica este excelente blog.
Comentarios recientes