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
|
package tim.prune.load.xml;
import java.util.ArrayList;
import org.xml.sax.Attributes;
import org.xml.sax.SAXException;
import tim.prune.data.Field;
/**
* Class for handling specifics of parsing Kml files
*/
public class KmlHandler extends XmlHandler
{
private boolean _insidePlacemark = false;
private boolean _insideName = false;
private boolean _insideCoordinates = false;
private String _name = null;
private StringBuffer _coordinates = null;
private ArrayList<String[]> _pointList = new ArrayList<String[]>();
/**
* Receive the start of a tag
* @see org.xml.sax.ContentHandler#startElement(java.lang.String, java.lang.String, java.lang.String, org.xml.sax.Attributes)
*/
public void startElement(String uri, String localName, String qName,
Attributes attributes) throws SAXException
{
String tagName = localName;
if (tagName == null || tagName.equals("")) {tagName = qName;}
if (tagName.equalsIgnoreCase("Placemark")) _insidePlacemark = true;
else if (tagName.equalsIgnoreCase("coordinates")) {_insideCoordinates = true; _coordinates = null;}
else if (tagName.equalsIgnoreCase("name")) {_insideName = true; _name = null;}
super.startElement(uri, localName, qName, attributes);
}
/**
* Process end tag
* @see org.xml.sax.ContentHandler#endElement(java.lang.String, java.lang.String, java.lang.String)
*/
public void endElement(String uri, String localName, String qName)
throws SAXException
{
String tagName = localName;
if (tagName == null || tagName.equals("")) {tagName = qName;}
if (tagName.equalsIgnoreCase("Placemark"))
{
processPlacemark();
_insidePlacemark = false;
}
else if (tagName.equalsIgnoreCase("coordinates")) _insideCoordinates = false;
else if (tagName.equalsIgnoreCase("name")) _insideName = false;
super.endElement(uri, localName, qName);
}
/**
* Process character text (inside tags or between them)
* @see org.xml.sax.ContentHandler#characters(char[], int, int)
*/
public void characters(char[] ch, int start, int length)
throws SAXException
{
if (_insidePlacemark && (_insideName || _insideCoordinates))
{
String value = new String(ch, start, length);
if (_insideName) {_name = value;}
else if (_insideCoordinates)
{
if (_coordinates == null)
{
_coordinates = new StringBuffer();
}
_coordinates.append(value);
}
}
super.characters(ch, start, length);
}
/**
* Process a placemark entry, either a single waypoint or a whole track
*/
private void processPlacemark()
{
if (_coordinates == null) return;
String allCoords = _coordinates.toString().trim();
String[] coordArray = allCoords.split("[ \n]");
int numPoints = coordArray.length;
if (numPoints == 1)
{
// Add single waypoint to list
_pointList.add(makeStringArray(allCoords, _name));
}
else if (numPoints > 1)
{
// Add each of the unnamed track points to list
boolean firstPoint = true;
for (int p=0; p<numPoints; p++)
{
if (coordArray[p] != null && coordArray[p].trim().length()>3)
{
String[] pointArray = makeStringArray(coordArray[p], null);
if (firstPoint) {pointArray[4] = "1";} // start of segment flag
firstPoint = false;
_pointList.add(pointArray);
}
}
}
}
/**
* Construct the String array for the given coordinates and name
* @param inCoordinates coordinate string in Kml format
* @param inName name of waypoint, or null if track point
* @return String array for point
*/
private static String[] makeStringArray(String inCoordinates, String inName)
{
String[] result = new String[5];
String[] values = inCoordinates.split(",");
if (values.length == 3) {System.arraycopy(values, 0, result, 0, 3);}
result[3] = inName;
return result;
}
/**
* @see tim.prune.load.xml.XmlHandler#getFieldArray()
*/
public Field[] getFieldArray()
{
final Field[] fields = {Field.LONGITUDE, Field.LATITUDE, Field.ALTITUDE, Field.WAYPT_NAME, Field.NEW_SEGMENT};
return fields;
}
/**
* Return the parsed information as a 2d array
* @see tim.prune.load.xml.XmlHandler#getDataArray()
*/
public String[][] getDataArray()
{
int numPoints = _pointList.size();
// construct data array
String[][] result = new String[numPoints][];
for (int i=0; i<numPoints; i++)
{
result[i] = _pointList.get(i);
}
return result;
}
}
|