com.itgp.gwtviz.client.ui.runtime.RuntimeDataV1.java Source code

Java tutorial

Introduction

Here is the source code for com.itgp.gwtviz.client.ui.runtime.RuntimeDataV1.java

Source

/*
 * The MIT License
 *
 * Copyright 2015 InsiTech LLC.   gwtvis@insitechinc.com
 *
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 * of this software and associated documentation files (the "Software"), to deal
 * in the Software without restriction, including without limitation the rights
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 * copies of the Software, and to permit persons to whom the Software is
 * furnished to do so, subject to the following conditions:
 *
 * The above copyright notice and this permission notice shall be included in
 * all copies or substantial portions of the Software.
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 * THE SOFTWARE.
 */

package com.itgp.gwtviz.client.ui.runtime;

import static com.itgp.gwtviz.client.ui.runtime.ColMeta.create;
import static com.itgp.gwtviz.client.ui.runtime.event.NotificationEvent.createDoneEvent;

import com.google.gwt.core.client.JavaScriptObject;
import com.google.gwt.json.client.*;
import com.itgp.gwtviz.client.charts.nv.*;
import com.itgp.gwtviz.client.comm.ServerComm;
import com.itgp.gwtviz.client.ui.runtime.ColMeta.TYPE;
import com.itgp.gwtviz.client.ui.runtime.event.*;
import com.itgp.gwtviz.client.ui.runtime.event.progressBar.ProgressBarNotificationEvent;
import com.itgp.gwtviz.shared.gconfig.*;
import com.itgp.gwtviz.shared.model.*;
import java.util.*;

/**
 * <p>
 *
 * @author Warp
 */
public class RuntimeDataV1 {
    public String configText;
    public GraphConfigImpl_1 config;
    public String fileName;
    public long fileID;
    public boolean designTime = false;

    public boolean sortOnYAxis = false;
    public GraphConfigUtility.YAxisSort sortOnYAxisDirection = GraphConfigUtility.YAxisSort.NoSort;

    String dataArray;
    AbstractChartXYV1 chartXY;
    PieChartV1 pieChart;
    ScatterChartV1 scatterChart;
    MatrixScatterChartV1 matrixScatterChart;

    ChartV1 chartToDisplay;

    String rawJSONData;

    //  JavaScriptObject        matrixScatterData;

    //--------------------
    private List<Item> columnDescriptors;
    public DataModelV1 dataModel = new DataModelV1();

    //--------------------
    public FilterCompleteListenerGroup filterListeners = new FilterCompleteListenerGroup();
    protected ProgressReportListenerGroup progressReporting = new ProgressReportListenerGroup();
    protected ErrorReportListenerGroup errorReporting = new ErrorReportListenerGroup();

    //--------------------

    public boolean useNative = true;

    //--------------------
    private int nextRowIndex = -1; // used in recursive entry
    private int numberOfRows = -1; // used in recursive entry
    private int numberOfColumns = -1; // used in recursive entry

    //TODO: Rename to RuntimeDataV1
    public RuntimeDataV1() {
    }

    public void setColumnDescriptors(List<Item> columnDescriptors) {
        this.columnDescriptors = columnDescriptors;
        int n = columnDescriptors.size();
        ColMeta[] colArray = new ColMeta[n];

        for (int i = 0; i < n; i++) {
            Item item = columnDescriptors.get(i);
            ColMeta cm = create(i, item.getValue()); // position and column name
            cm.positionAtDesignTime = ItemUtil.getIndexInCompleteDataSet(cm.name);
            cm.run = this;
            colArray[i] = cm;
        }

        this.dataModel.setColMetaArray(colArray);

    }

    public List<Item> getColumnDescriptors() {
        return this.columnDescriptors;
    }

    //-------------------------------------------------------------------------------------------------------------------

    public void setRawJSONData(String jsonData) {
        this.rawJSONData = jsonData;
    }

    protected JSONArray parsedJSONData;
    public static final int getData = 0;
    public static final int parseJava = 1;
    public static final int makeModelUsingJava = 2;

    public static final int parseNative = 11;
    public static final int makeModelUsingNative = 12;
    public int next;

    public boolean loopSetData() {
        switch (next) {
        case getData:
            sendProgress("Parsing data received. One moment please...");

            if (useNative) {
                next = parseNative;
            } else {
                next = parseJava;
            }

            return true; // continue

        case parseJava:
            parsedJSONData = (JSONArray) JSONParser.parseStrict(rawJSONData); // all strings
            dataModel.setDesignDataJava(parsedJSONData);
            initColumnTypeFromJava(parsedJSONData);

            //---- now initialize makeDataModel params
            this.nextRowIndex = 0; // initialize the index
            this.numberOfRows = parsedJSONData.size();
            this.numberOfColumns = this.dataModel.getColMetaArray().length;
            this.dataModel.setData(new Object[numberOfRows][numberOfColumns]);
            next = makeModelUsingJava;

            return true; // continue

        case makeModelUsingJava:

            // break up makeDataModelFromJava(parsedJSONData);
            boolean keepLoopGoing = makeDataModelFromJava();
            next = (keepLoopGoing ? makeModelUsingJava : getData); // reset

            return keepLoopGoing;

        case parseNative:

            JavaScriptObject nativeJSData = nativeParse(rawJSONData);
            dataModel.setDesignDataNative(nativeJSData);
            initColumnTypeFromNative();

            //---- now initialize makeDataModel params
            this.nextRowIndex = 0; // initialize the index
            this.numberOfRows = nativeLength(nativeJSData);
            this.numberOfColumns = this.dataModel.getColMetaArray().length;
            this.dataModel.setData(new Object[numberOfRows][numberOfColumns]);
            next = makeModelUsingNative;

            return true;

        case makeModelUsingNative:

            //TODO implement notifications
            boolean keepLoopGoing2 = createDataModelFromNative();
            next = (keepLoopGoing2 ? makeModelUsingNative : getData); // reset

            return keepLoopGoing2;

        default:
            sendError("Case " + next + " not implemented.");

            return false;

        }

    }

    protected void initColumnTypeFromNative() {

        JavaScriptObject nativeJSData = dataModel.getDesignDataNative();
        sendProgress("Initializing the column information based on the data received...");
        int numberOfRows = nativeLength(nativeJSData);
        int numberOfColumns = this.dataModel.getColMetaArray().length;

        for (int colModelIndex = 0; colModelIndex < numberOfColumns; colModelIndex++) {

            int testDataRows = 0;
            ColMeta colMeta = this.dataModel.getColMetaArray()[colModelIndex];
            int colPos = colMeta.getColPos();
            for (int rowIndex = 0; rowIndex < numberOfRows; rowIndex++) {

                JavaScriptObject row = getArray(nativeJSData, rowIndex);
                String val = get(row, colPos);
                if (val != null && val.length() > 0) {
                    testDataRows += 1;

                    if ((colMeta.getType() == TYPE.STRING)) {
                        break; // get out, no need to do more - a string cannot become a number again
                    } else {

                        // test for numeric in the first 3 rows if it's not already pegged as string
                        try {
                            double d = Double.parseDouble(val);
                            colMeta.setType(TYPE.NUMBER);
                        } catch (Exception ex) {
                            colMeta.setType(TYPE.STRING);
                        }

                    }

                    if (testDataRows >= 3) {
                        break; // get out of the for loop - we have enough data points
                    }
                } // if (val != null && val.length() > 0)
            } // for i
        } // for j
    }

    protected boolean createDataModelFromNative() {

        JavaScriptObject nativeJSData = dataModel.getDesignDataNative();

        while (this.nextRowIndex < numberOfRows) {

            JavaScriptObject row = getArray(nativeJSData, this.nextRowIndex);

            for (int colModelIndex = 0; colModelIndex < numberOfColumns; colModelIndex++) {
                ColMeta colMeta = this.dataModel.getColMetaArray()[colModelIndex];
                int colPos = colMeta.getColPos();

                Object x = null;
                if (colMeta.type == TYPE.NUMBER) {
                    x = getDouble(row, colPos);
                } else {
                    x = get(row, colPos);
                }

                this.dataModel.getData()[this.nextRowIndex][colModelIndex] = x;

            } // for j (columns)

            this.nextRowIndex++;

            if (this.nextRowIndex % 10 == 0) {

                // every 10 rows
                sendProgress("Processed " + this.nextRowIndex + " of " + this.numberOfRows + " rows.",
                        this.numberOfRows, this.nextRowIndex, "dataLoopPhase");

                return true; //stay in the loop
            }
        } // while nextRowIndex

        sendProgress("All " + numberOfRows + " data rows have been processed.");

        return false; // loop done
    }

    protected void obsolete_createDataModelFromNative() {

        ///!!! DO NOT USE YET- VERY UNSTABLE  AT THIS TIME8777
        JavaScriptObject nativeJSData = dataModel.getDesignDataNative();
        int numberOfRows = nativeLength(nativeJSData);
        int numberOfColumns = this.dataModel.getColMetaArray().length;
        this.dataModel.setData(new Object[numberOfRows][numberOfColumns]);

        for (int colModelIndex = 0; colModelIndex < numberOfColumns; colModelIndex++) {
            ColMeta colMeta = this.dataModel.getColMetaArray()[colModelIndex];
            int colPos = colMeta.getColPos();

            for (int i = 0; i < numberOfRows; i++) {
                if (i % 10 == 0) {

                    // progress every 10 records
                    sendProgress("Converting data to proper format. Working on column " + (colModelIndex + 1)
                            + " of " + numberOfColumns + ". " + i + " of " + numberOfRows
                            + " rows processed so far...");
                }

                JavaScriptObject row = getArray(nativeJSData, i);

                Object x = null;
                if (colMeta.type == TYPE.NUMBER) {
                    x = getDouble(row, colPos);
                } else {
                    x = get(row, colPos);
                }

                this.dataModel.getData()[i][colModelIndex] = x;
            } // for i ( rows)
        } // for j (columns)

        sendProgress("Data conversion complete.");
    }

    public static native String get(JavaScriptObject jsArray, int index) /*-{
                                                                         var v = jsArray[index];
                                                                         return v;
                                                                         }-*/
    ;

    public static native double getDouble(JavaScriptObject jsArray, int index) /*-{
                                                                               var v = jsArray[index];
                                                                                   
                                                                               var retVal = $wnd.parseFloat(v);
                                                                               if ( $wnd.isNaN( retVal) ){
                                                                               retVal = 0;
                                                                               }
                                                                               return retVal;
                                                                               }-*/
    ;

    public static native JavaScriptObject getArray(JavaScriptObject jsArray, int index) /*-{
                                                                                        var v = jsArray[index];
                                                                                        return v;
                                                                                        }-*/
    ;

    public static native JavaScriptObject nativeParse(String input) /*-{
                                                                    var v = $wnd.itgp.fromString(input);
                                                                    return v;
                                                                    }-*/
    ;

    public static native int nativeLength(JavaScriptObject jsArray) /*-{
                                                                    var v = jsArray.length;
                                                                    return v;
                                                                    }-*/
    ;

    //-------------------------------------------------------------------------------------------------------------------

    protected void initColumnTypeFromJava(JSONArray parsedJSONData) {

        int numberOfRows = parsedJSONData.size();
        int numberOfColumns = this.dataModel.getColMetaArray().length;

        for (int colModelIndex = 0; colModelIndex < numberOfColumns; colModelIndex++) {

            int testDataRows = 0;
            ColMeta colMeta = this.dataModel.getColMetaArray()[colModelIndex];
            int colPos = colMeta.getColPos();
            for (int rowIndex = 0; rowIndex < numberOfRows; rowIndex++) {
                JSONValue cell = ((JSONArray) parsedJSONData.get(rowIndex)).get(colPos);

                JSONString cellAsString = cell.isString();
                if (cellAsString == null) {
                    ServerComm.alert("row " + rowIndex + " col " + colPos + " : [" + cell.toString()
                            + "] is not a String! This circumstance contradicts the design parameters given!");

                    return;
                }

                String val = cellAsString.stringValue();

                if (val != null && val.length() > 0) {
                    testDataRows += 1;

                    if ((colMeta.getType() == TYPE.STRING)) {
                        break; // get out, no need to do more - a string cannot become a number again
                    } else {

                        // test for numeric in the first 3 rows if it's not already pegged as string
                        try {
                            double d = Double.parseDouble(val);
                            colMeta.setType(TYPE.NUMBER);
                        } catch (Exception ex) {
                            colMeta.setType(TYPE.STRING);
                        }

                    }

                    if (testDataRows >= 3) {
                        break; // get out of the for loop - we have enough data points
                    }
                } // if (val != null && val.length() > 0) 
            } // for i
        } // for j
    }

    protected boolean makeDataModelFromJava() {

        JSONArray parsedJSONData = dataModel.getDesignDataJava();
        while (this.nextRowIndex < numberOfRows) {
            JSONArray row = (JSONArray) parsedJSONData.get(this.nextRowIndex);

            for (int colModelIndex = 0; colModelIndex < this.numberOfColumns; colModelIndex++) {
                ColMeta colMeta = this.dataModel.getColMetaArray()[colModelIndex];
                int colPos = colMeta.getColPos();

                JSONString cell = (JSONString) row.get(colPos); // everything is a string
                String value = cell.stringValue();
                Object modelValue = null; // can only be String or Double
                if (colMeta.type == TYPE.NUMBER) {
                    try {
                        modelValue = Double.parseDouble(value); // Double instance
                    } catch (Exception ex) {
                        modelValue = Double.valueOf(0); // 0 but as Double
                    }
                } else {
                    modelValue = value; // direct string
                }

                this.dataModel.getData()[this.nextRowIndex][colModelIndex] = modelValue;
            } // for j (columns)

            this.nextRowIndex++;

            if (this.nextRowIndex % 10 == 0) {

                // every 10 rows
                sendProgress("Processed " + this.nextRowIndex + " of " + this.numberOfRows + " rows.");

                return true;
            }

        } // while (nextRowIndex)

        sendProgress("All " + numberOfRows + " data rows have been processed.");

        return false;
    }

    //
    //  protected void obsolete_makeDataModelFromJava(JSONArray parsedJSONData) {
    //      int numberOfRows    = parsedJSONData.size();
    //      int numberOfColumns = this.dataModel.getColMetaArray().length;
    //      this.dataModel.setRawJSONData(new Object[numberOfRows][numberOfColumns]);
    //
    //      for (int colModelIndex = 0; colModelIndex < numberOfColumns; colModelIndex++) {
    //          ColMeta colMeta = this.dataModel.getColMetaArray()[colModelIndex];
    //          int     colPos  = colMeta.getColPos();
    //
    //          for (int i = 0; i < numberOfRows; i++) {
    //              JSONArray  row        = (JSONArray) parsedJSONData.get(i);
    //
    //              JSONString cell       = (JSONString) row.get(colPos);    // everything is a string
    //              String     value      = cell.stringValue();
    //              Object     modelValue = null;                            // can only be String or Double
    //              if (colMeta.type == TYPE.NUMBER) {
    //                  try {
    //                      modelValue = Double.parseDouble(value);          // Double instance
    //                  } catch (Exception ex) {
    //                      modelValue = Double.valueOf(0);                  // 0 but as Double
    //                  }
    //              } else {
    //                  modelValue = value;                                  // direct string
    //              }
    //
    //              this.dataModel.getData()[i][colModelIndex] = modelValue;
    //          }                                                            // for i ( rows)
    //      }                                                                // for j (columns)
    //  }

    //----------------------------------------------------------------

    public void sendProgressInit() {
        NotificationEvent evt = NotificationEvent.createInitEvent();
        progressReporting.fireEvent(evt);
    }

    public void sendProgress(String progressReport) {
        if (progressReport != null) {
            NotificationEvent evt = new NotificationEvent(progressReport);
            progressReporting.fireEvent(evt);
        }
    }

    public void sendProgress(String progressReport, String phase) {
        if (progressReport != null) {
            NotificationEvent evt = new NotificationEvent(progressReport, phase);
            progressReporting.fireEvent(evt);
        }
    }

    public void sendProgress(String progressReport, int max, int current, String phase) {
        if (progressReport != null) {
            ProgressBarNotificationEvent evt = new ProgressBarNotificationEvent(progressReport, max, current,
                    phase);
            progressReporting.fireEvent(evt);
        }
    }

    public void sendProgressDone() {
        progressReporting.fireEvent(createDoneEvent());
    }

    public void sendError(String errorReport) {
        if (errorReport != null) {
            NotificationEvent evt = new NotificationEvent(errorReport);
            errorReporting.fireEvent(evt);
        }
    }

    public FilterCompleteListenerGroup getFilterListeners() {
        return filterListeners;
    }

    public void addFilterCompleteListener(FilterCompleteListener listener) {
        filterListeners.add(listener);
    }

}