Long story short, I'm developing an android app about collecting dynamic data and creating a KML file to show the characteristics of the driving with self-calibration of the sensors. I want to create a KML file using XMLserializer with the data obtained, this is the service that manages the process of creation of the file (it can run several times, that's why it doesn't close the file always):
File file = new File(sp.getString(getResources().getString(R.string.filesdir_key),"error"));
if (file.getPath().equals("error")) {
file = new File (Environment.getExternalStoragePublicDirectory("/smart-drive").toString()
+ "/SmaDri_" + sp.getString(getResources().getString(R.string.ruta_key),"00000000_0000"));
file.mkdirs();
}
finalFile = new File (file,"Final.kml");
if(!finalFile.exists()) {
try {
finalFile.createNewFile();
Log.d(TAG, "RefreshKML: creando " + finalFile.getPath());
} catch (IOException e) {
e.printStackTrace();
Log.d(TAG, "RefreshKML: fallo al crear " + finalFile.getName());
}
start = true;
}
try{
fileos = new FileOutputStream(finalFile,true);
} catch(FileNotFoundException e) {
e.printStackTrace();
Log.d(TAG,"RefreshKML: error abriendo "+finalFile.getName());
}
try {
serializer = Xml.newSerializer();
serializer.setOutput(fileos, "UTF-8");
if (start) {
kH.SerialStart(serializer, fileos, "Ruta "+sp.getString(getResources().getString(R.string.ruta_key),"00000000_0000"));
start = false;
}
int i=sp.getInt("poligonos",1);
for (s=0 ; s<PolyArray.size() ; s++){
polygon = PolyArray.get(s);
kH.SerialPlacePol(serializer, fileos,"Tramo "+i, polygon);
i++;
}
editor.putInt("poligonos",i);
editor.apply();
if (end) { //Solo cierra el archivo si se termina la recopilación de datos
kH.SerialEnd(serializer, fileos);
Log.d(TAG,"RefreshKML crea el cierre del KML");
end=false; //En caso de que no se completó esta opción
copyAllFiles();
mainDB.close();
DBHelper.close();
}
fileos.close();
} catch(IOException e) {
e.printStackTrace();
Log.d(TAG,"RefreshKML: error al escribir en serializer");
}
And these are the methods I use to create the header, body and close of the KML file:
public void SerialStart (XmlSerializer serializer, FileOutputStream fileos, String docName ) {
try{
serializer.startDocument(null, Boolean.valueOf(true));
serializer.setFeature("http://xmlpull.org/v1/doc/features.html#indent-output", true);
serializer.startTag(null, "kml");
serializer.attribute(null, "xmlns", "http://www.opengis.net/kml/2.2");
serializer.attribute(null,"xmlns:gx", "http://www.google.com/kml/ext/2.2"); //ALE, para intentar que se vea en Earth
serializer.attribute(null, "xmlns:kml", "http://www.opengis.net/kml/2.2");
serializer.attribute(null, "xmlns:atom", "http://www.w3.org/2005/Atom");
serializer.startTag(null, "Document");
serializer.startTag(null, "name");
serializer.text(docName);
serializer.endTag(null, "name");
serializer.startTag(null, "open");
serializer.text("1");
serializer.endTag(null, "open");
} catch(Exception e){
Log.d(TAG,"KMLHelper: Exception occured in SerialStart");
e.printStackTrace();
}
}
public void SerialPlacePol (XmlSerializer serializer, FileOutputStream fileos, String placeName, PolyKML poly ) {
try{
serializer.startTag(null, "Placemark");
// He añadido el tag fill porque parece que Google Earth la exige
serializer.startTag(null, "name");
serializer.text(placeName);
serializer.endTag(null, "name");
serializer.startTag(null, "description"); //PARA DESCRIPCION TIEMPOS
serializer.text(poly.gap); //PARA DESCRIPCION TIEMPOS
serializer.endTag(null, "description"); //PARA DESCRIPCION TIEMPOS
serializer.startTag(null, "Style");
serializer.startTag(null, "LineStyle");
serializer.startTag(null, "color");
serializer.text(poly.getLineColor());
serializer.endTag(null,"color");
serializer.startTag(null, "width");
serializer.text(poly.getLineWidth());
serializer.endTag(null,"width");
serializer.endTag(null,"LineStyle");
serializer.startTag(null, "PolyStyle");
serializer.startTag(null, "color");
serializer.text(poly.getPolyColor());
serializer.endTag(null,"color");
//ALE
serializer.startTag(null,"fill");
serializer.text("1");
serializer.endTag(null,"fill");
//ALE
serializer.endTag(null,"PolyStyle");
serializer.endTag(null,"Style");
serializer.startTag(null, "Polygon");
serializer.startTag(null, "tessellate");
if(poly.getTessellate()) serializer.text("1");
else serializer.text("0");
serializer.endTag(null,"tessellate");
serializer.startTag(null, "extrude");
if(poly.getExtrude()) serializer.text("1");
else serializer.text("0");
serializer.endTag(null,"extrude");
serializer.startTag(null, "altitudeMode");
serializer.text(poly.getAltitudeMode().toString());
serializer.endTag(null,"altitudeMode");
serializer.startTag(null, "outerBoundaryIs");
serializer.startTag(null, "LinearRing");
serializer.startTag(null, "coordinates");
serializer.text(poly.getCoorString());
serializer.endTag(null, "coordinates");
serializer.endTag(null, "LinearRing");
serializer.endTag(null, "outerBoundaryIs");
serializer.endTag(null, "Polygon");
serializer.endTag(null,"Placemark");
serializer.flush(); //ALE
}catch(Exception e){
Log.d(TAG,"KMLHelper: Exception occured in SerialPlacePol");
e.printStackTrace();
}
}
public void SerialEnd (XmlSerializer serializer, FileOutputStream fileos ) {
try{
serializer.endTag(null,"Document");
serializer.endTag(null,"kml");
//serializer.endDocument();
serializer.flush();
fileos.close();
Log.d(TAG,"KMLHelper: SerialEnd cierra archivo KML");
}catch(Exception e){
Log.d(TAG,"KMLHelper: Exception occured in SerialEnd");
e.printStackTrace();
}
}
And the result is fine but the indentation, it is lost after some time, it always happens. An example of the resulting file with the difference in the indentation is the following, there is one placemark with the proper indentation but suddenly the following has no indentation at all:
<Placemark>
<name>Tramo 1</name>
<description>1484689867000 - 1484689868000</description>
<Style>
<LineStyle>
<color>55FFFFFF</color>
<width>1</width>
</LineStyle>
<PolyStyle>
<color>4114B464</color>
<fill>1</fill>
</PolyStyle>
</Style>
<Polygon>
<tessellate>1</tessellate>
<extrude>1</extrude>
<altitudeMode>relativeToGround</altitudeMode>
<outerBoundaryIs>
<LinearRing>
<coordinates>-4.46107189168431,36.7189079696287,1.0 -4.461074321984691,36.71889869818065,1.0 -4.46104946831569,36.718892230371296,1.0 -4.461047018015309,36.71890140181935,1.0 -4.46107189168431,36.7189079696287,1.0</coordinates>
</LinearRing>
</outerBoundaryIs>
</Polygon>
</Placemark><Placemark><name>Tramo 1</name><description>-15 - -15</description><Style><LineStyle><color>55464646</color><width>1</width></LineStyle><PolyStyle><color>55FFFFFF</color><fill>1</fill></PolyStyle></Style><Polygon><tessellate>1</tessellate><extrude>1</extrude><altitudeMode>relativeToGround</altitudeMode><outerBoundaryIs><LinearRing><coordinates>-4.461042046219597,36.718907918437075,1.0 -4.461048518308548,36.71890698667229,1.0 -4.461047061691453,36.71889709332772,1.0 -4.461040613780402,36.71889802156293,1.0 -4.461042046219597,36.718907918437075,1.0</coordinates></LinearRing></outerBoundaryIs></Polygon></Placemark><Placemark><name>Tramo 1</name><description>-15 - -15</description><Style><LineStyle><color>55464646</color><width>1</width></LineStyle><PolyStyle><color>55FFFFFF</color><fill>1</fill></PolyStyle></Style><Polygon><tessellate>1</tessellate><extrude>1</extrude><altitudeMode>relativeToGround</altitudeMode><outerBoundaryIs><LinearRing><coordinates>-4.461038813540282,36.718908388824126,1.0 -4.461042046219597,36.718907918437075,1.0 -4.461040613780402,36.71889802156293,1.0 -4.461037386459718,36.71889849117587,1.0 -4.461038813540282,36.718908388824126,1.0</coordinates></LinearRing></outerBoundaryIs></Polygon></Placemark>
Can anyone tell me what is the problem that is causing to lose the indentation? I'll appreciate any ideas that could me help solve this problem
Solved, there was more than a XMLserializer writing to the same file so it didn't work fine. Now only 1 thread can access and write to the file at a time and the problem is gone!