Example usage for org.jfree.data.time TimeSeriesCollection addSeries

List of usage examples for org.jfree.data.time TimeSeriesCollection addSeries

Introduction

In this page you can find the example usage for org.jfree.data.time TimeSeriesCollection addSeries.

Prototype

public void addSeries(TimeSeries series) 

Source Link

Document

Adds a series to the collection and sends a DatasetChangeEvent to all registered listeners.

Usage

From source file:ecg.ecgshow.ECGShowUI.java

private void createPressureData(long timeZone) {
    PressureData = new JPanel();
    PressuredateAxises = new DateAxis[1];
    SystolicPressureSeries = new TimeSeries[2];
    DiastolicPressureSeries = new TimeSeries[2];

    TimeSeriesCollection timeseriescollection = new TimeSeriesCollection();
    SystolicPressureSeries[0] = new TimeSeries("");
    SystolicPressureSeries[0].setMaximumItemAge(timeZone);
    SystolicPressureSeries[0].setMaximumItemCount(500);
    SystolicPressureSeries[1] = new TimeSeries("");
    SystolicPressureSeries[1].setMaximumItemAge(timeZone);
    SystolicPressureSeries[1].setMaximumItemCount(2);
    timeseriescollection.addSeries(SystolicPressureSeries[0]);
    timeseriescollection.addSeries(SystolicPressureSeries[1]);

    PressuredateAxises[0] = new DateAxis("");
    PressuredateAxises[0].setTickLabelFont(new Font("SansSerif", 0, (int) (HEIGHT * 0.016)));
    PressuredateAxises[0].setLabelFont(new Font("SansSerif", 0, (int) (HEIGHT * 0.018)));
    PressuredateAxises[0].setTickLabelsVisible(true);
    PressuredateAxises[0].setVisible(false);

    DiastolicPressureSeries[0] = new TimeSeries("");
    DiastolicPressureSeries[0].setMaximumItemAge(timeZone);
    DiastolicPressureSeries[0].setMaximumItemCount(500);
    DiastolicPressureSeries[1] = new TimeSeries("");
    DiastolicPressureSeries[1].setMaximumItemAge(timeZone);
    DiastolicPressureSeries[1].setMaximumItemCount(2);
    timeseriescollection.addSeries(DiastolicPressureSeries[0]);
    timeseriescollection.addSeries(DiastolicPressureSeries[1]);

    NumberAxis numberaxis = new NumberAxis("Pressure");
    numberaxis.setTickLabelFont(new Font("SansSerif", 0, (int) (HEIGHT * 0.016)));
    numberaxis.setLabelFont(new Font("SansSerif", 0, (int) (HEIGHT * 0.018)));
    numberaxis.setStandardTickUnits(NumberAxis.createIntegerTickUnits());
    numberaxis.setVisible(false);/*  w  w w  .  ja va2 s .  c  o m*/
    numberaxis.setLowerBound(0D);
    numberaxis.setUpperBound(200D);

    XYLineAndShapeRenderer xylineandshaperenderer = new XYLineAndShapeRenderer(true, false);
    xylineandshaperenderer.setSeriesPaint(0, Color.GREEN); //
    xylineandshaperenderer.setSeriesStroke(0, new BasicStroke(2)); //
    xylineandshaperenderer.setSeriesPaint(1, Color.LIGHT_GRAY); //
    xylineandshaperenderer.setSeriesStroke(1, new BasicStroke(5));

    xylineandshaperenderer.setSeriesPaint(2, Color.ORANGE); //
    xylineandshaperenderer.setSeriesStroke(2, new BasicStroke(2)); //
    xylineandshaperenderer.setSeriesPaint(3, Color.LIGHT_GRAY); //
    xylineandshaperenderer.setSeriesStroke(3, new BasicStroke(5));

    //XYPlot xyplot = new XYPlot(timeseriescollection, PressuredateAxises[0], numberaxis, xylineandshaperenderer);
    XYPlot xyplot = new XYPlot(timeseriescollection, dateAxises[0], numberaxis, xylineandshaperenderer);

    xyplot.setBackgroundPaint(Color.LIGHT_GRAY);
    xyplot.setDomainGridlinePaint(Color.LIGHT_GRAY);
    xyplot.setRangeGridlinePaint(Color.LIGHT_GRAY);
    xyplot.setAxisOffset(new RectangleInsets(5D, 5D, 5D, 5D));
    xyplot.setBackgroundPaint(Color.BLACK);

    JFreeChart jfreechart = new JFreeChart(xyplot);
    jfreechart.setBackgroundPaint(new Color(237, 237, 237));//?
    jfreechart.getLegend().setVisible(false);

    ChartPanel chartpanel = new ChartPanel(jfreechart, (int) (WIDTH * 0.155), (int) (HEIGHT * 0.18), 0, 0,
            Integer.MAX_VALUE, Integer.MAX_VALUE, true, true, false, true, false, false);

    chartpanel.setBorder(BorderFactory.createCompoundBorder(BorderFactory.createEmptyBorder(0, 0, 0, 0) //??0
            , BorderFactory.createEmptyBorder() //????
    ));
    chartpanel.setMouseZoomable(false);
    PressureData.add(chartpanel);

}

From source file:edu.unibonn.plotting.TimeSeriesPlotter_Sensors.java

private XYDataset createDataset(ArrayList<Sensor> sensors) {
    final TimeSeriesCollection dataset = new TimeSeriesCollection();

    for (int i = 0; i < sensors.size(); i++) {
        Sensor current_sensor = sensors.get(i);

        final TimeSeries s1 = new TimeSeries("Sensor " + i, Hour.class);

        for (int j = 0; j < current_sensor.getDimensions(); j++) {
            LocalDateTime current_record_time = current_sensor.getInitial_record_time().plusHours(j);
            s1.add(new Hour(current_record_time.getHour(), current_record_time.getDayOfMonth(),
                    current_record_time.getMonthValue(), current_record_time.getYear()),
                    current_sensor.getMeasurement(j));
        }/*from  w w w  .  j  a v a2s . c  o m*/

        dataset.addSeries(s1);
    }

    dataset.setDomainIsPointsInTime(true);

    return dataset;
}

From source file:com.geminimobile.chart.GeminiChartUtil.java

public void createReport(OutputStream out, List<ChartSeries> chartData, String strTitle,
        String strDomainAxisLabel) {

    strDomainAxisLabel = "Time Interval: " + strDomainAxisLabel;
    String strYAxisLabel;/*from   w  w w.ja v a  2  s.c  om*/
    //String strCategoryType = " ";
    strYAxisLabel = "Count";
    //SimpleDateFormat sdf = new SimpleDateFormat("MMMM-dd hh:mm a");

    //build a dataset as needed by JFreeChart
    //      note: strCategoryType is for a chart with multiple categories.
    //      i.e. idisplay multiple bars for each time interval.
    //

    TimeSeriesCollection dataSet = new TimeSeriesCollection();

    // For each series of data, create a TimeSeries
    for (int i = 0; i < chartData.size(); i++) {
        ChartSeries chartSeries = chartData.get(i);

        TimeSeries timeSeries = new TimeSeries(chartSeries.getName(), Millisecond.class);
        List<ChartValueByTime> data = chartSeries.getData();

        //int cumulValue = 0;
        for (int j = 0; j < data.size(); j++) {
            ChartValueByTime chartVal = data.get(j);

            Millisecond ms = new Millisecond(new Date(chartVal.getTime()));

            // *NOT* Store the cumulative value . So maintain a running total.                
            //cumulValue += chartVal.getValue();
            //timeSeries.add(ms, cumulValue);
            timeSeries.add(ms, chartVal.getValue());
        }
        dataSet.addSeries(timeSeries);
    }

    JFreeChart lineChart = ChartFactory.createTimeSeriesChart(strTitle, // chart title
            strDomainAxisLabel, // domain axis label
            strYAxisLabel, // range axis label
            dataSet, // data
            true, // legend
            false, // tooltips
            false // urls
    );

    try {
        ChartUtilities.writeChartAsPNG(out, lineChart, 800, 400);
    } catch (IOException e) {
        e.printStackTrace();
    }

}

From source file:edu.fullerton.timeseriesapp.TimeSeriesApp.java

public ArrayList<Integer> makePlot(ArrayList<ChanDataBuffer> dbufs, boolean compact) throws WebUtilException {
    int imageId;// w w  w .ja  v  a 2  s  .c om
    try {
        PluginSupport psupport = new PluginSupport();
        String gtitle = psupport.getTitle(dbufs, compact);
        String xAxisLabel = "";
        XYSeriesCollection xyds = new XYSeriesCollection();
        TimeSeriesCollection mtds = new TimeSeriesCollection();

        compact = dbufs.size() > 2 ? false : compact;
        for (ChanDataBuffer dbuf : dbufs) {
            int npts = dbuf.getDataLength();
            int sum = 1;
            if (npts > 2000) {
                sum = npts / 2000;
            }
            String legend = psupport.getLegend(dbuf, compact);
            if (timeAxis.equalsIgnoreCase("utc")) {
                TimeSeries ts = psupport.getTimeSeries(dbuf, legend, sum);
                xAxisLabel = "Time (UTC)";
                mtds.addSeries(ts);
            } else {
                boolean isDt = timeAxis.equalsIgnoreCase("dt");
                XYSeries xys = psupport.addXySeries(dbuf, legend, isDt, sum);
                xAxisLabel = psupport.getxAxisLabel();
                xyds.addSeries(xys);
            }
        }
        Double minx, miny, maxx, maxy;
        Double[] rng = new Double[4];

        if (timeAxis.equalsIgnoreCase("utc")) {
            PluginSupport.getRangeLimits(mtds, rng);
        } else {
            int skip = 0;
            PluginSupport.getRangeLimits(xyds, rng, skip);
        }
        minx = rng[0];
        miny = rng[1];
        maxx = rng[2];
        maxy = rng[3];

        int exp;
        if (timeAxis.equalsIgnoreCase("utc")) {
            exp = PluginSupport.scaleRange(mtds, miny, maxy);
        } else {
            exp = PluginSupport.scaleRange(xyds, miny, maxy);
        }

        ChartPanel cpnl;
        DefaultXYDataset ds = new DefaultXYDataset();
        JFreeChart chart;
        if (timeAxis.equalsIgnoreCase("utc")) {
            chart = ChartFactory.createTimeSeriesChart(gtitle, "Time (UTC)", "Counts", ds, true, true, false);
        } else {
            chart = ChartFactory.createXYLineChart(gtitle, xAxisLabel, "Counts", ds, PlotOrientation.VERTICAL,
                    true, false, false);
        }
        chart.setBackgroundPaint(Color.WHITE);
        chart.setAntiAlias(true);

        XYPlot plot = (XYPlot) chart.getPlot();
        plot.setBackgroundPaint(Color.white);
        plot.setRangeGridlinePaint(Color.LIGHT_GRAY);
        plot.setDomainGridlinePaint(Color.LIGHT_GRAY);

        NumberAxis rangeAxis = new NumberAxis("Counts");
        ScaledAxisNumberFormat sanf = new ScaledAxisNumberFormat();
        sanf.setExp(exp);
        NumberTickUnit tickUnit;
        double plotRange;
        if (maxy != 0 && Math.abs(maxy - miny) < Math.abs(maxy) * 1e-30) {
            // this garbage is to get jFreeChart to always put labels on the Y axis
            double dt = Math.abs(miny) / 10;
            double scaledMin = (miny - dt) * Math.pow(10., exp);
            double scaledMax = (maxy + dt) * Math.pow(10., exp);
            rangeAxis.setRange(scaledMin, scaledMax);
            plotRange = scaledMax - scaledMin;
            rangeAxis.setAutoRange(false);
        } else {
            sanf.setMinMax(miny, maxy);
            plotRange = maxy - miny;
            rangeAxis.setAutoRange(true);
        }
        tickUnit = rangeAxis.getTickUnit();
        double tickSize = tickUnit.getSize();
        int nticks = (int) ((plotRange) / tickSize);
        if (nticks > yTicks) {
            double newTickSize = plotRange / yTicks;
            rangeAxis.setTickUnit(new NumberTickUnit(newTickSize));
        }
        rangeAxis.setNumberFormatOverride(sanf);
        rangeAxis.setAutoRangeIncludesZero(false);
        plot.setRangeAxis(rangeAxis);

        if (timeAxis.equalsIgnoreCase("utc")) {
            plot.setDataset(0, mtds);

        } else {
            plot.setDataset(0, xyds);
        }

        // Set the line thickness
        XYLineAndShapeRenderer r = (XYLineAndShapeRenderer) plot.getRenderer();
        BasicStroke str = new BasicStroke(lineThickness);
        int n = plot.getSeriesCount();
        for (int i = 0; i < n; i++) {
            r.setSeriesStroke(i, str);
        }

        if (compact) {
            chart.removeLegend();
        }
        cpnl = new ChartPanel(chart);
        if (outFilename.isEmpty()) {
            imageId = psupport.saveImageAsPNG(cpnl);
        } else {
            imageId = 0;
            psupport.saveImageAsPdfFile(chart, outFilename);
        }

    } catch (SQLException | NoSuchAlgorithmException | IOException ex) {
        throw new WebUtilException(ex);
    }
    ArrayList<Integer> ret = new ArrayList<>();
    ret.add(imageId);
    return ret;
}

From source file:edu.unibonn.kmeans.mapreduce.plotting.TimeSeriesPlotter_KMeans.java

private XYDataset createDataset_centroids(ArrayList<Cluster_KMeans> clusters, LocalDateTime from) {
    final TimeSeriesCollection dataset = new TimeSeriesCollection();

    for (int i = 0; i < clusters.size(); i++) {
        Cluster_KMeans current_cluster = clusters.get(i);
        double[] center_of_mass = current_cluster.getCenter_of_mass();

        final TimeSeries s1 = new TimeSeries("Cluster_" + current_cluster.getCluster_id(), Hour.class);

        for (int j = 0; j < 24; j++) {
            s1.add(new Hour(j, from.getDayOfMonth(), from.getMonthValue(), from.getYear()), center_of_mass[j]);
        }/*from  w  w  w.ja  va2 s.c  o m*/

        dataset.addSeries(s1);
    }

    dataset.setDomainIsPointsInTime(true);

    return dataset;
}

From source file:com.android.ddmuilib.log.event.DisplayGraph.java

/**
* Updates the chart with the {@link EventContainer} by adding the values/occurrences defined
* by the {@link ValueDisplayDescriptor} and {@link OccurrenceDisplayDescriptor} objects from
* the two lists.//from w w w  . ja  v a 2  s  . c  o  m
* <p/>This method is only called when at least one of the descriptor list is non empty.
* @param event
* @param logParser
* @param valueDescriptors
* @param occurrenceDescriptors
*/
private void updateChart(EventContainer event, EventLogParser logParser,
        ArrayList<ValueDisplayDescriptor> valueDescriptors,
        ArrayList<OccurrenceDisplayDescriptor> occurrenceDescriptors) {
    Map<Integer, String> tagMap = logParser.getTagMap();

    Millisecond millisecondTime = null;
    long msec = -1;

    // If the event container is a cpu container (tag == 2721), and there is no descriptor
    // for the total CPU load, then we do accumulate all the values.
    boolean accumulateValues = false;
    double accumulatedValue = 0;

    if (event.mTag == 2721) {
        accumulateValues = true;
        for (ValueDisplayDescriptor descriptor : valueDescriptors) {
            accumulateValues &= (descriptor.valueIndex != 0);
        }
    }

    for (ValueDisplayDescriptor descriptor : valueDescriptors) {
        try {
            // get the hashmap for this descriptor
            HashMap<Integer, TimeSeries> map = mValueDescriptorSeriesMap.get(descriptor);

            // if it's not there yet, we create it.
            if (map == null) {
                map = new HashMap<Integer, TimeSeries>();
                mValueDescriptorSeriesMap.put(descriptor, map);
            }

            // get the TimeSeries for this pid
            TimeSeries timeSeries = map.get(event.pid);

            // if it doesn't exist yet, we create it
            if (timeSeries == null) {
                // get the series name
                String seriesFullName = null;
                String seriesLabel = getSeriesLabel(event, descriptor);

                switch (mValueDescriptorCheck) {
                case EVENT_CHECK_SAME_TAG:
                    seriesFullName = String.format("%1$s / %2$s", seriesLabel, descriptor.valueName);
                    break;
                case EVENT_CHECK_SAME_VALUE:
                    seriesFullName = String.format("%1$s", seriesLabel);
                    break;
                default:
                    seriesFullName = String.format("%1$s / %2$s: %3$s", seriesLabel,
                            tagMap.get(descriptor.eventTag), descriptor.valueName);
                    break;
                }

                // get the data set for this ValueType
                TimeSeriesCollection dataset = getValueDataset(
                        logParser.getEventInfoMap().get(event.mTag)[descriptor.valueIndex].getValueType(),
                        accumulateValues);

                // create the series
                timeSeries = new TimeSeries(seriesFullName, Millisecond.class);
                if (mMaximumChartItemAge != -1) {
                    timeSeries.setMaximumItemAge(mMaximumChartItemAge * 1000);
                }

                dataset.addSeries(timeSeries);

                // add it to the map.
                map.put(event.pid, timeSeries);
            }

            // update the timeSeries.

            // get the value from the event
            double value = event.getValueAsDouble(descriptor.valueIndex);

            // accumulate the values if needed.
            if (accumulateValues) {
                accumulatedValue += value;
                value = accumulatedValue;
            }

            // get the time
            if (millisecondTime == null) {
                msec = (long) event.sec * 1000L + (event.nsec / 1000000L);
                millisecondTime = new Millisecond(new Date(msec));
            }

            // add the value to the time series
            timeSeries.addOrUpdate(millisecondTime, value);
        } catch (InvalidTypeException e) {
            // just ignore this descriptor if there's a type mismatch
        }
    }

    for (OccurrenceDisplayDescriptor descriptor : occurrenceDescriptors) {
        try {
            // get the hashmap for this descriptor
            HashMap<Integer, TimeSeries> map = mOcurrenceDescriptorSeriesMap.get(descriptor);

            // if it's not there yet, we create it.
            if (map == null) {
                map = new HashMap<Integer, TimeSeries>();
                mOcurrenceDescriptorSeriesMap.put(descriptor, map);
            }

            // get the TimeSeries for this pid
            TimeSeries timeSeries = map.get(event.pid);

            // if it doesn't exist yet, we create it.
            if (timeSeries == null) {
                String seriesLabel = getSeriesLabel(event, descriptor);

                String seriesFullName = String.format("[%1$s:%2$s]", tagMap.get(descriptor.eventTag),
                        seriesLabel);

                timeSeries = new TimeSeries(seriesFullName, Millisecond.class);
                if (mMaximumChartItemAge != -1) {
                    timeSeries.setMaximumItemAge(mMaximumChartItemAge);
                }

                getOccurrenceDataSet().addSeries(timeSeries);

                map.put(event.pid, timeSeries);
            }

            // update the series

            // get the time
            if (millisecondTime == null) {
                msec = (long) event.sec * 1000L + (event.nsec / 1000000L);
                millisecondTime = new Millisecond(new Date(msec));
            }

            // add the value to the time series
            timeSeries.addOrUpdate(millisecondTime, 0); // the value is unused
        } catch (InvalidTypeException e) {
            // just ignore this descriptor if there's a type mismatch
        }
    }

    // go through all the series and remove old values.
    if (msec != -1 && mMaximumChartItemAge != -1) {
        Collection<HashMap<Integer, TimeSeries>> pidMapValues = mValueDescriptorSeriesMap.values();

        for (HashMap<Integer, TimeSeries> pidMapValue : pidMapValues) {
            Collection<TimeSeries> seriesCollection = pidMapValue.values();

            for (TimeSeries timeSeries : seriesCollection) {
                timeSeries.removeAgedItems(msec, true);
            }
        }

        pidMapValues = mOcurrenceDescriptorSeriesMap.values();
        for (HashMap<Integer, TimeSeries> pidMapValue : pidMapValues) {
            Collection<TimeSeries> seriesCollection = pidMapValue.values();

            for (TimeSeries timeSeries : seriesCollection) {
                timeSeries.removeAgedItems(msec, true);
            }
        }
    }
}

From source file:view.App.java

private XYDataset createDataset(SpreadObject obj) throws ParseException {
    TimeSeriesCollection dataset = new TimeSeriesCollection();
    TimeSeries series = new TimeSeries(
            obj.getBaseStock().getTicker() + " : " + obj.getSecondStock().getTicker());

    List<SpreadData> data = obj.getData();
    for (SpreadData item : data) {
        String date = item.getDate();
        DateFormat df = new SimpleDateFormat("yyyy-MM-dd");
        Date dateRes = df.parse(date);
        Day d = new Day(dateRes);
        RegularTimePeriod regTime = d.next();
        series.add(regTime, item.getSpreadValue().doubleValue());
    }//from   w ww .  jav a  2s. c om

    dataset.addSeries(series);
    return dataset;
}

From source file:com.bdb.weather.display.summary.RainSummary.java

/**
 * Load the data into the plot.//from w ww.ja v  a  2  s  .c  om
 * 
 * @param list The summary data
 */
public void loadData(List<SummaryRecord> list) {
    dataTable.setItems(FXCollections.observableList(list));
    TimeSeriesCollection ds = new TimeSeriesCollection();
    TimeSeries etSeries = new TimeSeries(ET_ROW_KEY);
    TimeSeries rainSeries = new TimeSeries(RAIN_ROW_KEY);

    Depth totalRain = new Depth(0.0);
    Depth totalET = new Depth(0.0);

    //
    // Load each record
    //
    for (SummaryRecord rec : list) {
        Depth rain = rec.getTotalRainfall();

        RegularTimePeriod tp = RegularTimePeriod.createInstance(interval.getFreeChartClass(),
                TimeUtils.localDateTimeToDate(rec.getDate()), TimeZone.getDefault());

        if (rain != null) {
            rainSeries.add(tp, rain.get());
            totalRain = totalRain.add(rain);
        }

        Depth et = rec.getTotalET();
        if (et != null) {
            etSeries.add(tp, et.get());
            totalET = totalET.add(et);
        }
    }

    ds.addSeries(etSeries);
    ds.addSeries(rainSeries);
    rainPlot.setDataset(ds);
}

From source file:ca.myewb.frame.servlet.GraphServlet.java

private JFreeChart getDaily2Stats(Session s) {
    JFreeChart chart;//www  .  java2 s  .  c o m
    List<DailyStatsModel> stats = (new SafeHibList<DailyStatsModel>(
            s.createQuery("select ds from DailyStatsModel as ds where day<? and day>=? order by day desc")
                    .setDate(0, new Date()).setDate(1, GraphServlet.getStartDate()))).list();
    TimeSeriesCollection theData = new TimeSeriesCollection();

    TimeSeries signups = new TimeSeries("signups", Day.class);
    theData.addSeries(signups);

    TimeSeries mlSignups = new TimeSeries("Mailing list signups", Day.class);
    theData.addSeries(mlSignups);

    TimeSeries mlUpgrades = new TimeSeries("Mailing list upgrades", Day.class);
    theData.addSeries(mlUpgrades);

    TimeSeries deletions = new TimeSeries("Deletions", Day.class);
    theData.addSeries(deletions);

    for (DailyStatsModel ds : stats) {
        Day theDay = new Day(ds.getDay());
        signups.add(theDay, ds.getSignups());
        deletions.add(theDay, ds.getDeletions());
        mlSignups.add(theDay, ds.getMailinglistsignups());
        mlUpgrades.add(theDay, ds.getMailinglistupgrades());
    }

    chart = ChartFactory.createTimeSeriesChart("Account changes (14-day moving avg)", "Day", "Occurrences",
            MovingAverage.createMovingAverage(theData, "", 14, 0), true, true, true);

    XYPlot plot = (XYPlot) chart.getPlot();
    plot.getRangeAxis().setUpperBound(25);

    XYLineAndShapeRenderer renderer = (XYLineAndShapeRenderer) plot.getRenderer();
    renderer.setSeriesStroke(0, new BasicStroke(2.0f));
    renderer.setSeriesStroke(1, new BasicStroke(2.0f));
    renderer.setSeriesStroke(2, new BasicStroke(2.0f));
    renderer.setSeriesStroke(3, new BasicStroke(2.0f));
    return chart;
}

From source file:com.bdb.weather.display.summary.WindSummary.java

/**
 * Load the data into the plot./*from  w ww.jav  a  2s. c om*/
 * 
 * @param records The summary records
 */
public void loadData(List<SummaryRecord> records) {
    dataTable.setItems(FXCollections.observableList(records));
    TimeSeriesCollection sustainedDataset = new TimeSeriesCollection();
    TimeSeries avgSpeedSeries = new TimeSeries("Average Sustained");
    TimeSeries maxSpeedSeries = new TimeSeries("Maximum Sustained");
    TimeSeriesCollection gustDataset = new TimeSeriesCollection();
    TimeSeries windGustSeries = new TimeSeries("Maximum Gust");

    for (int i = 0; i < records.size(); i++) {
        RegularTimePeriod p = RegularTimePeriod.createInstance(interval.getFreeChartClass(),
                TimeUtils.localDateTimeToDate(records.get(i).getDate().atStartOfDay()), TimeZone.getDefault());
        maxSpeedSeries.add(p, records.get(i).getMaxWindSpeed().get());
        avgSpeedSeries.add(p, records.get(i).getAvgWindSpeed().get());
        Speed gust = records.get(i).getMaxWindGust();

        if (gust != null) {
            windGustSeries.add(p, gust.get());
        }
    }

    sustainedDataset.addSeries(avgSpeedSeries);
    sustainedDataset.addSeries(maxSpeedSeries);
    gustDataset.addSeries(windGustSeries);

    plot.setDataset(SUSTAINED_WIND_SERIES, sustainedDataset);
    plot.setDataset(GUST_SERIES, gustDataset);
}