com.freedomotic.jfrontend.extras.GraphPanel.java Source code

Java tutorial

Introduction

Here is the source code for com.freedomotic.jfrontend.extras.GraphPanel.java

Source

/**
 *
 * Copyright (c) 2009-2013 Freedomotic team http://freedomotic.com
 *
 * This file is part of Freedomotic
 *
 * This Program is free software; you can redistribute it and/or modify it under
 * the terms of the GNU General Public License as published by the Free Software
 * Foundation; either version 2, or (at your option) any later version.
 *
 * This Program 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. See the GNU General Public License for more
 * details.
 *
 * You should have received a copy of the GNU General Public License along with
 * Freedomotic; see the file COPYING. If not, see
 * <http://www.gnu.org/licenses/>.
 */
package com.freedomotic.jfrontend.extras;

import com.freedomotic.api.EventTemplate;
import com.freedomotic.api.Plugin;
import com.freedomotic.app.Freedomotic;
import com.freedomotic.model.charting.UsageData;
import com.freedomotic.model.charting.UsageDataFrame;
import com.freedomotic.objects.DataBehaviorLogic;
import com.freedomotic.objects.EnvObjectLogic;
import com.freedomotic.reactions.Command;
import com.freedomotic.reactions.CommandPersistence;
import java.awt.Color;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.swing.table.AbstractTableModel;
import org.jfree.chart.ChartFactory;
import org.jfree.chart.ChartPanel;
import org.jfree.chart.JFreeChart;
import org.jfree.chart.axis.DateAxis;
import org.jfree.chart.axis.DateTickUnit;
import org.jfree.chart.axis.DateTickUnitType;
import org.jfree.chart.plot.XYPlot;
import org.jfree.chart.renderer.xy.XYItemRenderer;
import org.jfree.chart.renderer.xy.XYLineAndShapeRenderer;
import org.jfree.chart.renderer.xy.XYStepRenderer;
import org.jfree.data.time.Millisecond;
import org.jfree.data.time.TimeSeries;
import org.jfree.data.time.TimeSeriesCollection;
import org.jfree.data.xy.XYDataset;
import org.jfree.ui.RectangleInsets;

/**
 *
 * @author Matteo Mazzoni <matteo@bestmazzo.it>
 */
public class GraphPanel extends javax.swing.JFrame {

    private UsageDataFrame points = new UsageDataFrame();
    private EnvObjectLogic obj;
    private TimeSeries series;
    private JFreeChart chart;
    private String title;
    private Plugin master;

    /**
     * Creates new form GraphWindow
     * @param obj
     */
    public GraphPanel(Plugin master, EnvObjectLogic obj) {
        this.master = master;
        this.obj = obj;
        this.title = obj.getPojo().getPhisicalAddress();
        initComponents();

        this.setTitle(title);
        reDraw();

    }

    /**
     *
     */
    public final void reDraw() {
        //  String JSON = obj.getBehavior("data").getValueAsString();
        DataBehaviorLogic dbl = (DataBehaviorLogic) obj.getBehavior("data");
        if (dbl.isChanged()) {
            this.points.setData(dbl.getData());
            createChart(this.points, title);
            jRawDatatxt.setText(dbl.getValueAsString());
            dataTable.setModel(new FreedomoticTableModel());
            setVisible(true);
        }

    }

    /**
     * Creates a chart.
     *
     * @param dataset a dataset.
     *
     * @return A chart.
     */
    /**
     * This method is called from within the constructor to initialize the form.
     * WARNING: Do NOT modify this code. The content of this method is always
     * regenerated by the Form Editor.
     */
    @SuppressWarnings("unchecked")
    // <editor-fold defaultstate="collapsed" desc="Generated Code">//GEN-BEGIN:initComponents
    private void initComponents() {

        jTabbedPane1 = new javax.swing.JTabbedPane();
        graphPanel = new javax.swing.JPanel();
        tabDataPanel = new javax.swing.JScrollPane();
        dataTable = new javax.swing.JTable();
        rawDataPanel = new javax.swing.JScrollPane();
        jRawDatatxt = new javax.swing.JTextArea();
        jPanel1 = new javax.swing.JPanel();
        jLabel1 = new javax.swing.JLabel();
        jLabel2 = new javax.swing.JLabel();
        jButton1 = new javax.swing.JButton();
        jSpinnerStartDate = new javax.swing.JSpinner();
        jSpinnerStopDate = new javax.swing.JSpinner();
        jButton2 = new javax.swing.JButton();
        jComboGranularity = new javax.swing.JComboBox();
        jLabel3 = new javax.swing.JLabel();

        graphPanel.setLayout(new java.awt.BorderLayout());
        jTabbedPane1.addTab("Graph", graphPanel);

        dataTable.setModel(new javax.swing.table.DefaultTableModel(new Object[][] {

        }, new String[] {

        }));
        tabDataPanel.setViewportView(dataTable);

        jTabbedPane1.addTab("TableData", tabDataPanel);

        jRawDatatxt.setColumns(20);
        jRawDatatxt.setRows(5);
        rawDataPanel.setViewportView(jRawDatatxt);

        jTabbedPane1.addTab("RawData", rawDataPanel);

        jLabel1.setText("Start Date");

        jLabel2.setText("End Date");

        jButton1.setText("Apply filters");
        jButton1.addActionListener(new java.awt.event.ActionListener() {
            public void actionPerformed(java.awt.event.ActionEvent evt) {
                jButton1ActionPerformed(evt);
            }
        });

        jSpinnerStartDate.setModel(
                new javax.swing.SpinnerDateModel(new java.util.Date(), null, null, java.util.Calendar.SECOND));

        jSpinnerStopDate.setModel(
                new javax.swing.SpinnerDateModel(new java.util.Date(), null, null, java.util.Calendar.SECOND));

        jButton2.setText("Redraw");
        jButton2.addActionListener(new java.awt.event.ActionListener() {
            public void actionPerformed(java.awt.event.ActionEvent evt) {
                jButton2ActionPerformed(evt);
            }
        });

        jComboGranularity.setModel(new javax.swing.DefaultComboBoxModel(
                new String[] { "Year", "Month", "Day", "Hour", "Minute", "Second" }));
        jComboGranularity.setSelectedIndex(3);

        jLabel3.setText("Granularity");

        javax.swing.GroupLayout jPanel1Layout = new javax.swing.GroupLayout(jPanel1);
        jPanel1.setLayout(jPanel1Layout);
        jPanel1Layout.setHorizontalGroup(jPanel1Layout
                .createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
                .addGroup(javax.swing.GroupLayout.Alignment.TRAILING, jPanel1Layout.createSequentialGroup()
                        .addContainerGap(javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
                        .addComponent(jButton2).addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
                        .addComponent(jButton1).addContainerGap())
                .addGroup(jPanel1Layout.createSequentialGroup().addContainerGap().addGroup(jPanel1Layout
                        .createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
                        .addGroup(jPanel1Layout
                                .createParallelGroup(javax.swing.GroupLayout.Alignment.TRAILING, false)
                                .addComponent(jLabel2, javax.swing.GroupLayout.DEFAULT_SIZE,
                                        javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
                                .addComponent(jLabel1, javax.swing.GroupLayout.DEFAULT_SIZE, 130, Short.MAX_VALUE))
                        .addComponent(jLabel3)).addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
                        .addGroup(
                                jPanel1Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING, false)
                                        .addComponent(jSpinnerStartDate).addComponent(jSpinnerStopDate)
                                        .addComponent(jComboGranularity, 0, javax.swing.GroupLayout.DEFAULT_SIZE,
                                                Short.MAX_VALUE))
                        .addContainerGap(336, Short.MAX_VALUE)));
        jPanel1Layout.setVerticalGroup(jPanel1Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
                .addGroup(jPanel1Layout.createSequentialGroup().addGap(17, 17, 17)
                        .addGroup(jPanel1Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
                                .addComponent(jLabel1).addComponent(jSpinnerStartDate,
                                        javax.swing.GroupLayout.PREFERRED_SIZE,
                                        javax.swing.GroupLayout.DEFAULT_SIZE,
                                        javax.swing.GroupLayout.PREFERRED_SIZE))
                        .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
                        .addGroup(jPanel1Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
                                .addComponent(jLabel2).addComponent(jSpinnerStopDate,
                                        javax.swing.GroupLayout.PREFERRED_SIZE,
                                        javax.swing.GroupLayout.DEFAULT_SIZE,
                                        javax.swing.GroupLayout.PREFERRED_SIZE))
                        .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
                        .addGroup(jPanel1Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
                                .addComponent(jComboGranularity, javax.swing.GroupLayout.PREFERRED_SIZE,
                                        javax.swing.GroupLayout.DEFAULT_SIZE,
                                        javax.swing.GroupLayout.PREFERRED_SIZE)
                                .addComponent(jLabel3))
                        .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED, 193, Short.MAX_VALUE)
                        .addGroup(jPanel1Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
                                .addComponent(jButton1).addComponent(jButton2))
                        .addContainerGap()));

        jTabbedPane1.addTab("Filters", jPanel1);

        javax.swing.GroupLayout layout = new javax.swing.GroupLayout(getContentPane());
        getContentPane().setLayout(layout);
        layout.setHorizontalGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING).addGroup(
                layout.createSequentialGroup().addContainerGap().addComponent(jTabbedPane1).addContainerGap()));
        layout.setVerticalGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
                .addGroup(layout.createSequentialGroup().addContainerGap()
                        .addComponent(jTabbedPane1, javax.swing.GroupLayout.DEFAULT_SIZE, 376, Short.MAX_VALUE)
                        .addContainerGap()));

        pack();
    }// </editor-fold>//GEN-END:initComponents

    private void jButton1ActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_jButton1ActionPerformed
        Command c = CommandPersistence.getCommand("Ask data from the harvester");
        Command d;
        if (c != null) {
            try {
                d = c.clone();

                d.setProperty("startDate", Long.toString(((Date) jSpinnerStartDate.getValue()).getTime()));
                d.setProperty("stopDate", Long.toString(((Date) jSpinnerStopDate.getValue()).getTime()));
                d.setProperty("QueryAddress", obj.getPojo().getPhisicalAddress());
                Freedomotic.sendCommand(d);

            } catch (CloneNotSupportedException ex) {
                Logger.getLogger(GraphPanel.class.getName()).log(Level.SEVERE, null, ex);
            }
        }

    }//GEN-LAST:event_jButton1ActionPerformed

    private void jButton2ActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_jButton2ActionPerformed
        // TODO add your handling code here:
        reDraw();
    }//GEN-LAST:event_jButton2ActionPerformed
     // Variables declaration - do not modify//GEN-BEGIN:variables

    private javax.swing.JTable dataTable;
    private javax.swing.JPanel graphPanel;
    private javax.swing.JButton jButton1;
    private javax.swing.JButton jButton2;
    private javax.swing.JComboBox jComboGranularity;
    private javax.swing.JLabel jLabel1;
    private javax.swing.JLabel jLabel2;
    private javax.swing.JLabel jLabel3;
    private javax.swing.JPanel jPanel1;
    private javax.swing.JTextArea jRawDatatxt;
    private javax.swing.JSpinner jSpinnerStartDate;
    private javax.swing.JSpinner jSpinnerStopDate;
    private javax.swing.JTabbedPane jTabbedPane1;
    private javax.swing.JScrollPane rawDataPanel;
    private javax.swing.JScrollPane tabDataPanel;
    // End of variables declaration//GEN-END:variables

    private void createChart(UsageDataFrame points, String title) {
        series = new TimeSeries(title);

        for (UsageData d : points.getData()) {
            Date resultdate = d.getDateTime();
            Millisecond ms_read = new Millisecond(resultdate);
            int poweredValue = -1;
            if (d.getObjBehavior().equalsIgnoreCase("powered")) {
                poweredValue = d.getObjValue().equalsIgnoreCase("true") ? 1 : 0;
            } else if (d.getObjBehavior().equalsIgnoreCase("brigthness")) {
                try {
                    poweredValue = Integer.parseInt(d.getObjValue());
                } catch (NumberFormatException ex) {
                    poweredValue = -1;
                }
            }
            series.addOrUpdate(ms_read, poweredValue);
        }

        XYDataset xyDataset = new TimeSeriesCollection(series);

        chart = ChartFactory.createTimeSeriesChart("Chart", "TIME", "VALUE", xyDataset, true, // legend
                true, // tooltips
                false // urls
        );
        chart.setAntiAlias(true);
        // Set plot styles
        XYPlot plot = (XYPlot) chart.getPlot();
        plot.setBackgroundPaint(Color.lightGray);
        plot.setDomainGridlinePaint(Color.white);
        plot.setRangeGridlinePaint(Color.white);
        plot.setAxisOffset(new RectangleInsets(2.0, 2.0, 2.0, 2.0));
        // Set series line styles
        plot.setRenderer(new XYStepRenderer());

        XYItemRenderer r = plot.getRenderer();
        if (r instanceof XYLineAndShapeRenderer) {
            XYLineAndShapeRenderer renderer = (XYLineAndShapeRenderer) r;
            renderer.setShapesVisible(true);
            renderer.setShapesFilled(true);
        }

        // Set date axis style
        DateAxis axis = (DateAxis) plot.getDomainAxis();

        String formatString = "MM-dd HH";
        DateTickUnitType dtut = DateTickUnitType.HOUR;

        if (jComboGranularity.getSelectedItem().equals("Year")) {
            formatString = "yyyy";
            dtut = DateTickUnitType.YEAR;
        } else if (jComboGranularity.getSelectedItem().equals("Month")) {
            axis.setDateFormatOverride(new SimpleDateFormat("yyyy-MM"));
            dtut = DateTickUnitType.MONTH;
        } else if (jComboGranularity.getSelectedItem().equals("Day")) {
            axis.setDateFormatOverride(new SimpleDateFormat("MM-dd"));
            dtut = DateTickUnitType.DAY;
        } else if (jComboGranularity.getSelectedItem().equals("Minute")) {
            formatString = "MM-dd HH:mm";
            dtut = DateTickUnitType.MINUTE;
        } else if (jComboGranularity.getSelectedItem().equals("Second")) {
            formatString = "HH:mm:SS";
            dtut = DateTickUnitType.SECOND;
        }

        DateFormat formatter = new SimpleDateFormat(formatString);
        DateTickUnit unit = new DateTickUnit(dtut, 1, formatter);
        axis.setTickUnit(unit);

        ChartPanel chartPanel = new ChartPanel(chart);
        chartPanel.setPreferredSize(new java.awt.Dimension(800, 500));
        graphPanel.removeAll();
        graphPanel.add(chartPanel);

    }

    /**
     *
     * @param ev
     */
    public void addDataFromEvent(EventTemplate ev) {
        Date d = new Date(ev.getCreation());
        Millisecond ms_read = new Millisecond(d);
        int valut = ev.getProperty("object.behavior.powered").equalsIgnoreCase("true") ? 1 : 0;
        series.addOrUpdate(ms_read, valut);
        chart.fireChartChanged();

    }

    /**
     *
     */
    public class FreedomoticTableModel extends AbstractTableModel {

        /**
         *
         * @return
         */
        @Override
        public int getRowCount() {
            return points.getData().size();
        }

        /**
         *
         * @return
         */
        @Override
        public int getColumnCount() {
            return 6;
        }

        /**
         *
         * @param rowIndex
         * @param columnIndex
         * @return
         */
        @Override
        public Object getValueAt(int rowIndex, int columnIndex) {
            UsageData item = points.getData().get(rowIndex);
            switch (columnIndex) {
            case 0:
                return item.getDateTime();
            case 1:
                return item.getObjName();
            case 2:
                return item.getObjProtocol();
            case 3:
                return item.getObjAddress();
            case 4:
                return item.getObjBehavior();
            case 5:
                return item.getObjValue();
            }
            return null;
        }

        /**
         *
         * @param columnIndex
         * @return
         */
        @Override
        public Class<?> getColumnClass(int columnIndex) {
            if (columnIndex == 0) {
                return Date.class;
            } else {
                return String.class;
            }
        }

        private final String[] columnNames = { "Datetime", "Name", "Protocol", "Address", "Behavior", "Value" };

        /**
         *
         * @param column
         * @return
         */
        @Override
        public String getColumnName(int column) {
            return columnNames[column];
        }
    }
}