/*
* Copyright (C) 2011-2014 GeoForge Project
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public License
* as published by the Free Software Foundation; either version 2
* of the License, 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 Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
*/
package org.geoforge.gfrplgimportshapesgeojson4gfr.lang.thread;
import gov.nasa.worldwind.formats.geojson.*;
import gov.nasa.worldwind.geom.Position;
import java.awt.geom.Point2D;
import java.util.*;
import java.util.logging.Logger;
import javax.swing.JLabel;
import org.geoforge.gfrplgimportshapesgeojson4gfr.io.GfrPlgImporterDataGeojson;
import org.geoforge.guillc.optionpane.GfrOptionPaneAbs;
import org.geoforge.guillc.progressbar.GfrProgressBar;
import org.geoforge.io.util.eventobject.GfrEventObjectDoneWriteObjects;
import org.geoforge.lang.util.eventobject.GfrEventObjectAbs;
import org.geoforge.lang.handler.IGfrHandlerEventListenerThreadJobProgress;
import org.geoforge.lang.thread.GfrPgsThrAbs;
import org.geoforge.lang.util.GfrResBundleLang;
import org.geoforge.java.util.logging.filehandler.FileHandlerLogger;
import org.geoforge.java.lang.string.GfrUtlString;
import org.geoforge.mdldatecl.*;
import org.geoforge.wrpbasprssynecl.*;
/**
*
* @author bantchao@gmail.com
*/
public class GfrPgsThrImpShpsGeojson extends GfrPgsThrAbs
{
// ----
// begin: instantiate logger for this class
final private static Logger _LOGGER_ = Logger.getLogger(GfrPgsThrImpShpsGeojson.class.getName());
static
{
GfrPgsThrImpShpsGeojson._LOGGER_.addHandler(FileHandlerLogger.s_getInstance());
}
// end: instantiate logger for this class
// ----
private Set<String> _setCreatedIdsSct_ = null;
private Set<String> _setCreatedIdsPnt_ = null;
private Set<String> _setCreatedIdsPth_ = null;
private Set<String> _setCreatedIdsAre_ = null;
private Set<String> _setCreatedIdsSpn_ = null;
private GfrProgressBar _pbr_ = null;
private JLabel _lbl_ = null;
private boolean _blnDoneJob = false;
public boolean isDoneJob() { return this._blnDoneJob; }
public Set<String> getCreatedIdsSector() { return this._setCreatedIdsSct_; }
public Set<String> getCreatedIdsPoint() { return this._setCreatedIdsPnt_; }
public Set<String> getCreatedIdsPath() { return this._setCreatedIdsPth_; }
public Set<String> getCreatedIdsArea() { return this._setCreatedIdsAre_; }
public Set<String> getCreatedIdsPointset() { return this._setCreatedIdsSpn_; }
// ---
private ArrayList<String> _lstNameSct_ = null;
private ArrayList<String> _lstNamePnt_ = null;
private ArrayList<String> _lstNamePth_ = null;
private ArrayList<String> _lstNameAre_ = null;
private ArrayList<String> _lstNameSpn_ = null;
private ArrayList<ArrayList<Point2D.Double>> _lstGeometrySct_ = null;
private ArrayList<Point2D.Double> _lstGeometryPnt_ = null;
private ArrayList<ArrayList<Point2D.Double>> _lstGeometryPth_ = null;
private ArrayList<ArrayList<Point2D.Double>> _lstGeometryAre_ = null;
private ArrayList<ArrayList<Point2D.Double>> _lstGeometrySpn_ = null;
private ArrayList<String> _lstNameExistingSct_ = null; // should be a set of strings
private ArrayList<String> _lstNameExistingPnt_ = null; // should be a set of strings
private ArrayList<String> _lstNameExistingPth_ = null; // should be a set of strings
private ArrayList<String> _lstNameExistingAre_ = null; // should be a set of strings
private ArrayList<String> _lstNameExistingSpn_ = null; // should be a set of strings
private String _strPathOrUrl_ = null;
// ---
public GfrPgsThrImpShpsGeojson(
IGfrHandlerEventListenerThreadJobProgress lst,
GfrProgressBar pbr,
JLabel lbl,
String strPathOrUrl)
{
super(lst);
this._pbr_ = pbr;
this._lbl_ = lbl;
this._strPathOrUrl_ = strPathOrUrl;
this._setCreatedIdsSct_ = new HashSet<String>();
this._setCreatedIdsPnt_ = new HashSet<String>();
this._setCreatedIdsPth_ = new HashSet<String>();
this._setCreatedIdsAre_ = new HashSet<String>();
this._setCreatedIdsSpn_ = new HashSet<String>();
// ---
this._lstNameSct_ = new ArrayList<String>();
this._lstNamePnt_ = new ArrayList<String>();
this._lstNamePth_ = new ArrayList<String>();
this._lstNameAre_ = new ArrayList<String>();
this._lstNameSpn_ = new ArrayList<String>();
// ---
this._lstGeometrySct_ = new ArrayList<ArrayList<Point2D.Double>>();
this._lstGeometryPnt_ = new ArrayList<Point2D.Double>();
this._lstGeometryPth_ = new ArrayList<ArrayList<Point2D.Double>>();
this._lstGeometryAre_ = new ArrayList<ArrayList<Point2D.Double>>();
this._lstGeometrySpn_ = new ArrayList<ArrayList<Point2D.Double>>();
// ---
this._lstNameExistingSct_ = new ArrayList<String>();
this._lstNameExistingPnt_ = new ArrayList<String>();
this._lstNameExistingPth_ = new ArrayList<String>();
this._lstNameExistingAre_ = new ArrayList<String>();
this._lstNameExistingSpn_ = new ArrayList<String>();
// ---
super._thr.start();
}
// TODO: implement LifeCycle
public void destroy()
{
// ---
if(this._lstNameSct_ != null)
{
this._lstNameSct_.clear();
this._lstNameSct_ = null;
}
if(this._lstGeometrySct_ != null)
{
this._lstGeometrySct_.clear();
this._lstGeometrySct_ = null;
}
if(this._lstNameExistingSct_ != null)
{
this._lstNameExistingSct_.clear();
this._lstNameExistingSct_ = null;
}
// ---
if(this._lstNamePnt_ != null)
{
this._lstNamePnt_.clear();
this._lstNamePnt_ = null;
}
if(this._lstGeometryPnt_ != null)
{
this._lstGeometryPnt_.clear();
this._lstGeometryPnt_ = null;
}
if(this._lstNameExistingPnt_ != null)
{
this._lstNameExistingPnt_.clear();
this._lstNameExistingPnt_ = null;
}
// ---
if(this._lstNamePth_ != null)
{
this._lstNamePth_.clear();
this._lstNamePth_ = null;
}
if(this._lstGeometryPth_ != null)
{
this._lstGeometryPth_.clear();
this._lstGeometryPth_ = null;
}
if(this._lstNameExistingPth_ != null)
{
this._lstNameExistingPth_.clear();
this._lstNameExistingPth_ = null;
}
// ---
if(this._lstNameAre_ != null)
{
this._lstNameAre_.clear();
this._lstNameAre_ = null;
}
if(this._lstGeometryAre_ != null)
{
this._lstGeometryAre_.clear();
this._lstGeometryAre_ = null;
}
if(this._lstNameExistingAre_ != null)
{
this._lstNameExistingAre_.clear();
this._lstNameExistingAre_ = null;
}
// ---
if(this._lstNameSpn_ != null)
{
this._lstNameSpn_.clear();
this._lstNameSpn_ = null;
}
if(this._lstGeometrySpn_ != null)
{
this._lstGeometrySpn_.clear();
this._lstGeometrySpn_ = null;
}
if(this._lstNameExistingSpn_ != null)
{
this._lstNameExistingSpn_.clear();
this._lstNameExistingSpn_ = null;
}
}
@Override
protected void _doJob()
{
this._lbl_.setText("Processing ...");
this._pbr_.setIndeterminate(true);
try
{
_doJob_();
}
catch (Exception exc)
{
exc.printStackTrace();
String str = exc.getMessage();
if (str == null)
str = "Uncaught exception";
GfrPgsThrImpShpsGeojson._LOGGER_.severe(str);
if (str.length() > 3000)
{
str = str.substring(0, 3000);
str = "First 3000 chars error messages: \n" + str;
}
super._strError = str;
this._blnDoneJob = true;
//super._pbrItems_.setIndeterminate(false);
GfrOptionPaneAbs.s_showDialogWarning(
null, str);
try
{
_fireEvent();
}
catch (Exception exc2)
{
exc2.printStackTrace();
}
}
}
@Override
protected void _actionCancelled()
{
System.out.println("TODO: GfrPgsThrImpShpsGeojson._actionCancelled()");
}
private void _doJob_() throws Exception
{
GfrPlgImporterDataGeojson loader = new GfrPlgImporterDataGeojson(this._strPathOrUrl_)
{
@Override
protected void _addPoint(GeoJSONPoint geom)
{
try
{
_addPoint_(geom);
}
catch (Exception exc)
{
exc.printStackTrace();
}
}
@Override
protected void _addPath(GeoJSONLineString geom)
{
try
{
_addPath_(geom);
}
catch (Exception exc)
{
exc.printStackTrace();
}
}
@Override
protected void _addSector(GeoJSONBox geom)
{
try
{
_addSector_(geom);
}
catch (Exception exc)
{
exc.printStackTrace();
}
}
@Override
protected void _addArea(GeoJSONPolygon geom)
{
try
{
_addArea_(geom);
}
catch (Exception exc)
{
exc.printStackTrace();
}
}
@Override
protected void _addPointsSet(GeoJSONMultiPoint geom)
{
try
{
_addPointset_(geom);
}
catch (Exception exc)
{
exc.printStackTrace();
}
}
/*
* not yet notion of pathSet
* iterating, and creating paths
*/
@Override
protected void _addPathsSet(GeoJSONMultiLineString geom)
{
try
{
_addPaths_(geom);
}
catch (Exception exc)
{
exc.printStackTrace();
}
}
@Override
protected void _addAreasSet_(GeoJSONMultiPolygon geom)
{
try
{
_addAreas_(geom);
}
catch (Exception exc)
{
exc.printStackTrace();
}
}
};
this._lbl_.setText("Parsing document");
loader.doJob();
_saveObjects_();
// ending
this._blnDoneJob = true;
_fireEvent();
}
@Override
protected synchronized void _fireEvent() throws Exception
{
if (super._blnCanceled)
return;
GfrEventObjectAbs event = new GfrEventObjectDoneWriteObjects(this, super._strError);
Iterator itr = super._listeners.iterator();
while (itr.hasNext())
{
if (super._blnCanceled)
return;
((IGfrHandlerEventListenerThreadJobProgress) itr.next()).handleEventThreadJobDone(event);
}
}
// ---
private void _saveObjects_() throws Exception
{
int intTotalItems = this._lstNameExistingSct_.size();
// ---
intTotalItems += this._lstNameExistingPnt_.size();
intTotalItems += this._lstNameExistingPth_.size();
intTotalItems += this._lstNameExistingAre_.size();
intTotalItems += this._lstNameExistingSpn_.size();
if (intTotalItems < 1)
{
// TODO: dialog, no objects to save
System.err.println("TODO: dialog, intTotalItems < 1");
return;
}
this._pbr_.setIndeterminate(false);
int intCountItems = 0;
_savePoints_(intTotalItems, intCountItems);
intCountItems += this._lstNameSct_.size();
_saveSectors_(intTotalItems, intCountItems);
intCountItems += this._lstNamePnt_.size();
_savePaths_(intTotalItems, intCountItems);
intCountItems += this._lstNamePth_.size();
_saveAreas_(intTotalItems, intCountItems);
intCountItems += this._lstNameAre_.size();
_savePointsets_(intTotalItems, intCountItems);
}
private void _savePointsets_(int intTotalItems, int intCountItems) throws Exception
{
if (this._lstNameSpn_.isEmpty())
return;
for (int i=0; i<this._lstNameSpn_.size(); i++)
{
int intPercentItems = intCountItems * 100 / intTotalItems;
this._lbl_.setText("Saving pointsets, " + intPercentItems + "% done");
this._pbr_.setValue(intPercentItems);
intCountItems++;
if (super._blnCanceled)
{
this._blnDoneJob = true;
return;
}
String strIdCur = GfrMdlDatSetTlosEclSpn.getInstance().newObject(
this._lstNameSpn_.get(i),
null, //strsDescription
null, //strsUrl
this._lstGeometrySpn_.get(i));
this._setCreatedIdsSpn_.add(strIdCur);
if (super._blnCanceled)
{
this._blnDoneJob = true;
return;
}
}
}
private void _saveAreas_(int intTotalItems, int intCountItems) throws Exception
{
if (this._lstNameAre_.isEmpty())
return;
for (int i=0; i<this._lstNameAre_.size(); i++)
{
int intPercentItems = intCountItems * 100 / intTotalItems;
this._lbl_.setText("Saving areas, " + intPercentItems + "% done");
this._pbr_.setValue(intPercentItems);
intCountItems++;
if (super._blnCanceled)
{
this._blnDoneJob = true;
return;
}
String strIdCur = GfrMdlDatSetTlosEclAre.getInstance().newObject(
this._lstNameAre_.get(i),
null, //strsDescription
null, //strsUrl
this._lstGeometryAre_.get(i));
this._setCreatedIdsAre_.add(strIdCur);
if (super._blnCanceled)
{
this._blnDoneJob = true;
return;
}
}
}
private void _savePaths_(int intTotalItems, int intCountItems) throws Exception
{
if (this._lstNamePth_.isEmpty())
return;
for (int i=0; i<this._lstNamePth_.size(); i++)
{
int intPercentItems = intCountItems * 100 / intTotalItems;
this._lbl_.setText("Saving paths, " + intPercentItems + "% done");
this._pbr_.setValue(intPercentItems);
intCountItems++;
if (super._blnCanceled)
{
this._blnDoneJob = true;
return;
}
String strIdCur = GfrMdlDatSetTlosEclPth.getInstance().newObject(
this._lstNamePth_.get(i),
null, //strsDescription
null, //strsUrl
this._lstGeometryPth_.get(i));
this._setCreatedIdsPth_.add(strIdCur);
if (super._blnCanceled)
{
this._blnDoneJob = true;
return;
}
}
}
private void _saveSectors_(int intTotalItems, int intCountItems) throws Exception
{
if (this._lstNameSct_.isEmpty())
return;
for (int i=0; i<this._lstNameSct_.size(); i++)
{
int intPercentItems = intCountItems * 100 / intTotalItems;
this._lbl_.setText("Saving sectors, " + intPercentItems + "% done");
this._pbr_.setValue(intPercentItems);
intCountItems++;
if (super._blnCanceled)
{
this._blnDoneJob = true;
return;
}
String strIdCur = GfrMdlDatSetTlosEclSct.getInstance().newObject(
this._lstNameSct_.get(i),
null, //strsDescription
null, //strsUrl
this._lstGeometrySct_.get(i));
this._setCreatedIdsSct_.add(strIdCur);
if (super._blnCanceled)
{
this._blnDoneJob = true;
return;
}
}
}
private void _savePoints_(int intTotalItems, int intCountItems) throws Exception
{
if (this._lstNamePnt_.isEmpty())
return;
for (int i=0; i<this._lstNamePnt_.size(); i++)
{
int intPercentItems = intCountItems * 100 / intTotalItems;
this._lbl_.setText("Saving points, " + intPercentItems + "% done");
this._pbr_.setValue(intPercentItems);
intCountItems++;
if (super._blnCanceled)
{
this._blnDoneJob = true;
return;
}
String strIdCur = GfrMdlDatSetTlosEclPnt.getInstance().newObject(
this._lstNamePnt_.get(i),
null, //strsDescription
null, //strsUrl
this._lstGeometryPnt_.get(i));
this._setCreatedIdsPnt_.add(strIdCur);
if (super._blnCanceled)
{
this._blnDoneJob = true;
return;
}
}
}
private void _addPaths_(GeoJSONMultiLineString geom) throws Exception
{
for (int i = 0; i < geom.getLineStringCount(); i++)
{
_addPath_(geom.getCoordinates(i));
}
}
private void _addPath_(GeoJSONLineString geom) throws Exception
{
_addPath_(geom.getCoordinates());
}
private void _addPoint_(GeoJSONPoint geom) throws Exception
{
Position pos = geom.getPosition();
Point2D.Double dblGeometry = new Point2D.Double();
dblGeometry.y = pos.latitude.degrees;
dblGeometry.x = pos.longitude.degrees;
if (this._lstNameExistingPnt_.isEmpty()) // first run
{
String[] strsNameExistingInDb = GfrWrpBasTopSynEclPnts.getInstance().getSortedNamesTlo();
this._lstNameExistingPnt_.addAll(Arrays.asList(strsNameExistingInDb));
}
String[] strsNameExisting = new String[this._lstNameExistingPnt_.size()];
for (int i=0; i<this._lstNameExistingPnt_.size(); i++)
strsNameExisting[i] = this._lstNameExistingPnt_.get(i);
String strValue = GfrUtlString.s_createUniqueNameByNumber(
strsNameExisting,
"point");
this._lstNameExistingPnt_.add(strValue);
this._lstNamePnt_.add(strValue);
this._lstGeometryPnt_.add(dblGeometry);
}
private void _addSector_(GeoJSONBox geom) throws Exception
{
GeoJSONPositionArray arrPositions = geom.getCoordinates();
ArrayList<Point2D.Double> altValue = new ArrayList<Point2D.Double>();
if (arrPositions.length() != 2)
{
String strWarning = "arrPositions.length() != 2, arrPositions.length()=" + arrPositions.length();
GfrPgsThrImpShpsGeojson._LOGGER_.warning(strWarning);
throw new Exception(strWarning);
}
for (Position posCur: arrPositions)
{
Point2D.Double dblGeometry = new Point2D.Double();
dblGeometry.y = posCur.latitude.degrees;
dblGeometry.x = posCur.longitude.degrees;
altValue.add(dblGeometry);
}
if (this._lstNameExistingSct_.isEmpty()) // first run
{
String[] strsNameExistingInDb = GfrWrpBasTopSynEclScts.getInstance().getSortedNamesTlo();
this._lstNameExistingSct_.addAll(Arrays.asList(strsNameExistingInDb));
}
String[] strsNameExisting = new String[this._lstNameExistingSct_.size()];
for (int i=0; i<this._lstNameExistingSct_.size(); i++)
strsNameExisting[i] = this._lstNameExistingSct_.get(i);
String strValue = GfrUtlString.s_createUniqueNameByNumber(
strsNameExisting,
"sector");
this._lstNameExistingSct_.add(strValue);
this._lstNameSct_.add(strValue);
this._lstGeometrySct_.add(altValue);
}
private void _addPath_(GeoJSONPositionArray arrPositions) throws Exception
{
ArrayList<Point2D.Double> altValueLine = new ArrayList<Point2D.Double>();
for (Position posCur: arrPositions)
{
Point2D.Double dblGeometry = new Point2D.Double();
dblGeometry.y = posCur.latitude.degrees;
dblGeometry.x = posCur.longitude.degrees;
altValueLine.add(dblGeometry);
}
if (this._lstNameExistingPth_.isEmpty()) // first run
{
String[] strsNameExistingInDb = GfrWrpBasTopSynEclPths.getInstance().getSortedNamesTlo();
this._lstNameExistingPth_.addAll(Arrays.asList(strsNameExistingInDb));
}
String[] strsNameExisting = new String[this._lstNameExistingPth_.size()];
for (int i=0; i<this._lstNameExistingPth_.size(); i++)
strsNameExisting[i] = this._lstNameExistingPth_.get(i);
String strValue = GfrUtlString.s_createUniqueNameByNumber(
strsNameExisting,
GfrResBundleLang.s_getInstance().getValue("word.path").toLowerCase());
this._lstNameExistingPth_.add(strValue);
this._lstNamePth_.add(strValue);
this._lstGeometryPth_.add(altValueLine);
}
private void _addAreas_(GeoJSONMultiPolygon geom) throws Exception
{
for (int i = 0; i < geom.getPolygonCount(); i++)
{
_addArea_(geom.getExteriorRing(i));
}
}
/*
* LIMITATION: just keeping exterior ring
* TODO: check for last point
*/
private void _addArea_(GeoJSONPolygon geom) throws Exception
{
_addArea_(geom.getExteriorRing());
}
private void _addArea_(GeoJSONPositionArray arrPositions) throws Exception
{
ArrayList<Point2D.Double> altValueLine = new ArrayList<Point2D.Double>();
// excluding last point (same as first point)
for (int i=0; i<arrPositions.length()-1; i++)
{
Point2D.Double dblGeometry = new Point2D.Double();
dblGeometry.y = arrPositions.getPosition(i).latitude.degrees;
dblGeometry.x = arrPositions.getPosition(i).longitude.degrees;
altValueLine.add(dblGeometry);
}
if (this._lstNameExistingAre_.isEmpty()) // first run
{
String[] strsNameExistingInDb = GfrWrpBasTopSynEclAres.getInstance().getSortedNamesTlo();
this._lstNameExistingAre_.addAll(Arrays.asList(strsNameExistingInDb));
}
String[] strsNameExisting = new String[this._lstNameExistingAre_.size()];
for (int i=0; i<this._lstNameExistingAre_.size(); i++)
strsNameExisting[i] = this._lstNameExistingAre_.get(i);
String strValue = GfrUtlString.s_createUniqueNameByNumber(
strsNameExisting,
GfrResBundleLang.s_getInstance().getValue("word.area").toLowerCase());
this._lstNameExistingAre_.add(strValue);
this._lstNameAre_.add(strValue);
this._lstGeometryAre_.add(altValueLine);
}
private void _addPointset_(GeoJSONMultiPoint geom) throws Exception
{
ArrayList<Point2D.Double> altPoint2d = new ArrayList<Point2D.Double>();
GeoJSONPositionArray arrPositions = geom.getCoordinates();
for (int i=0; i<arrPositions.length(); i++)
{
Point2D.Double dblGeometry = new Point2D.Double();
dblGeometry.y = arrPositions.getPosition(i).latitude.degrees;
dblGeometry.x = arrPositions.getPosition(i).longitude.degrees;
altPoint2d.add(dblGeometry);
}
if (this._lstNameExistingSpn_.isEmpty()) // first run
{
String[] strsNameExistingInDb = GfrWrpBasTopSynEclSpns.getInstance().getSortedNamesTlo();
this._lstNameExistingSpn_.addAll(Arrays.asList(strsNameExistingInDb));
}
String[] strsNameExisting = new String[this._lstNameExistingSpn_.size()];
for (int i=0; i<this._lstNameExistingSpn_.size(); i++)
strsNameExisting[i] = this._lstNameExistingSpn_.get(i);
String strValue = GfrUtlString.s_createUniqueNameByNumber(
strsNameExisting,
GfrResBundleLang.s_getInstance().getValue("word.pointset").toLowerCase());
this._lstNameExistingSpn_.add(strValue);
this._lstNameSpn_.add(strValue);
this._lstGeometrySpn_.add(altPoint2d);
}
}