Waterflow
Visualize water in terrain
src/xmlParsing.cpp
Go to the documentation of this file.
00001 
00002 
00003 
00004 #include "xmlParsing.h"
00005 
00006 // This file implement all the parsing functions for the XML file contents and an generating function for the Flowsource class.
00007 
00008 
00009 Flood_Fill_data::Flood_Fill_data(int in_x, int in_z, float in_height)
00010 {
00011   this->x = in_x;
00012   this->z = in_z;
00013   this->height = in_height;
00014 }
00015 
00016 init_Data_struct::init_Data_struct(const char* XMLfile)
00017 {
00018   this->data_filename = loadMapPath(XMLfile);
00019   
00020   this->velocity_save_path = loadVelSavePath(XMLfile);
00021   this->velocity_load_path = loadVelLoadPath(XMLfile);
00022   this->height_save_path = loadHeightSavePath(XMLfile);
00023   this->height_load_path = loadHeightLoadPath(XMLfile);
00024   
00025   this->Flowsources = loadFlows(XMLfile);
00026   this->FFData = loadFFData(XMLfile);
00027 }
00028 
00029 // Converts a string with CSV to a vector with floats.
00030 std::vector<float> fStrToVector(std::string str){
00031   std::vector<float> valueVector;
00032   std::stringstream ss(str);
00033   std::string fValue;
00034 
00035   while(std::getline(ss, fValue, ',')){
00036     std::stringstream fs(fValue);
00037     float f = 0.0;
00038     fs >> f;
00039     valueVector.push_back(f);
00040   }
00041   return valueVector;
00042 }
00043 
00044 //Converts a string with CSV to a vector with ints.
00045 std::vector<int> iStrToVector(std::string str){
00046   std::vector<int> valueVector;
00047   std::stringstream ss(str);
00048   std::string iValue;
00049 
00050   while(std::getline(ss, iValue, ',')){
00051     std::stringstream is(iValue);
00052     int i = 0;
00053     is >> i;
00054     valueVector.push_back(i);
00055   }
00056   return valueVector;
00057 }
00058 
00059 // This function parses the pressure values from the XML file by takeing the Pressure node, the PressureTime node and a pointer to a FlowSource object as input and adding the contents to the provided Object.
00060 void parsePressure(FlowSource* obj, pugi::xml_node pres, pugi::xml_node time){
00061   std::string timestr = time.attribute("t").value();
00062   std::string pstr = pres.attribute("p").value();
00063   std::vector<float> timevec = fStrToVector(timestr);
00064   std::vector<float> pvec = fStrToVector(pstr);
00065   obj->setPressure(pvec, timevec);
00066 }
00067 
00068 // This function parses the Position node and adds it to by pointer provided FlowSource Object.
00069 void parsePosition(FlowSource* obj, pugi::xml_node node){
00070   int x, y, z;
00071   x = node.attribute("x").as_int();
00072   y = node.attribute("y").as_int();
00073   z = node.attribute("z").as_int();
00074   obj->setPosition(x,y,z);
00075 }
00076 
00077 // This function parses the xyz direction of A Normal node and the time of a NormalTime node, then adds the result to an FlowSource Object given by pointer.
00078 void parseNormal(FlowSource* obj, pugi::xml_node norm, pugi::xml_node time){
00079   std::string timestr = time.attribute("t").value();
00080   std::vector<float> ndir;
00081   std::vector<std::vector<float> > nvec;
00082   float x, y, z;
00083   for (pugi::xml_node_iterator it = norm.begin(); it != norm.end(); ++it){
00084   x = it->attribute("x").as_float();
00085   y = it->attribute("y").as_float();
00086   z = it->attribute("z").as_float();
00087   ndir = {x, y, z};
00088   nvec.push_back(ndir);
00089   }
00090   std::vector<int> timevec = iStrToVector(timestr);
00091   obj->setNormal(nvec, timevec);
00092 }
00093 
00094 
00095 void parseTotalWater(FlowSource* obj, pugi::xml_node node){
00096   float tot;
00097   tot = node.attribute("tot").as_float();
00098   obj->setTotalWater(tot);
00099 }
00100 
00101 void parseRadius(FlowSource* obj, pugi::xml_node node){
00102   float r;
00103   r = node.attribute("r").as_float();
00104   obj->setRadius(r);
00105 }
00106 
00107 // This Function transverces all child nodes to a Sources node in a (by input) specified XML file. Fore every source specifed it adds a new FlowSource object and populates it with the contents in the XML file coresponding to the source. It returns a vector with pointers to the objects it creates.
00108 std::vector<FlowSource*> loadFlows(const char* xmlFile) {
00109   pugi::xml_document doc;
00110   std::vector<FlowSource*> srces;
00111   if (!doc.load_file(xmlFile)) return srces;
00112   pugi::xml_node sources = doc.child("Profile").child("Sources");
00113   for (pugi::xml_node_iterator it = sources.begin(); it != sources.end(); ++it){
00114       FlowSource* fsp;
00115       fsp = new FlowSource;
00116       parsePressure(fsp, it->child("Pressure"), it->child("TimeP"));
00117       parsePosition(fsp, it->child("Position"));
00118       parseNormal(fsp, it->child("Normals"), it->child("TimeN"));
00119       parseTotalWater(fsp, it->child("TotWater"));
00120       parseRadius(fsp, it->child("Radius"));
00121       srces.push_back(fsp);
00122   }
00123   return srces;
00124 }
00125 
00126 bool flowChange(std::vector<FlowSource*> flows, float dt){
00127   bool change = false;
00128   for(unsigned int i = 0; i < flows.size(); i++){
00129     if(flows.at(i)->getChange(dt)){
00130       change = true;
00131     }
00132   }
00133   return change;
00134 }
00135 
00136 std::string loadMapPath(const char* xmlFile){
00137   pugi::xml_document doc;
00138   if(!doc.load_file(xmlFile)) return "No XML file";
00139   std::cout << "XML load success" << std::endl;
00140   std::string path = doc.child("Profile").child("Data").child("MapName").attribute("path").value();
00141   return path;
00142 }
00143 
00144 std::string loadVelLoadPath(const char* xmlFile){
00145   pugi::xml_document doc;
00146   if(!doc.load_file(xmlFile)) return "No XML file";
00147   std::string path = doc.child("Profile").child("Data").child("VelLoad").attribute("path").value();
00148   return path;
00149 }
00150 
00151 std::string loadHeightLoadPath(const char* xmlFile){
00152   pugi::xml_document doc;
00153   if(!doc.load_file(xmlFile)) return "No XML file";
00154   std::string path = doc.child("Profile").child("Data").child("HeightLoad").attribute("path").value();
00155   return path;
00156 }
00157 
00158 std::string loadVelSavePath(const char* xmlFile){
00159   pugi::xml_document doc;
00160   if(!doc.load_file(xmlFile)) return "No XML file";
00161   std::string path = doc.child("Profile").child("Data").child("VelSave").attribute("path").value();
00162   return path;
00163 }
00164 
00165 std::string loadHeightSavePath(const char* xmlFile){
00166   pugi::xml_document doc;
00167   if(!doc.load_file(xmlFile)) return "No XML file";
00168   std::string path = doc.child("Profile").child("Data").child("HeightSave").attribute("path").value();
00169   return path;
00170 }
00171 
00172 std::vector<Flood_Fill_data*> loadFFData(const char* xmlFile){
00173   pugi::xml_document doc;
00174   doc.load_file(xmlFile);
00175 
00176   std::vector<Flood_Fill_data*> out_data;
00177   pugi::xml_node floods = doc.child("Profile").child("Floods");
00178 
00179   for (pugi::xml_node_iterator it = floods.begin(); it != floods.end(); ++it){
00180     Flood_Fill_data* Flood_Fill = new Flood_Fill_data(it->attribute("x").as_int(), it->attribute("z").as_int(), it->attribute("height").as_float());
00181 
00182     out_data.push_back(Flood_Fill);
00183   }
00184   return out_data;
00185 }
00186 
00187 
00188 void deleteAllFlows(std::vector<FlowSource*> srces){
00189   for(auto it = srces.begin(); it != srces.end(); ++it){
00190     delete *it;
00191   }
00192 }
00193 
 All Classes Files Functions Variables Enumerations