presage  0.9.2~beta
profile.cpp
Go to the documentation of this file.
1 
2 /******************************************************
3  * Presage, an extensible predictive text entry system
4  * ---------------------------------------------------
5  *
6  * Copyright (C) 2008 Matteo Vescovi <matteo.vescovi@yahoo.co.uk>
7 
8  This program is free software; you can redistribute it and/or modify
9  it under the terms of the GNU General Public License as published by
10  the Free Software Foundation; either version 2 of the License, or
11  (at your option) any later version.
12 
13  This program is distributed in the hope that it will be useful,
14  but WITHOUT ANY WARRANTY; without even the implied warranty of
15  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16  GNU General Public License for more details.
17 
18  You should have received a copy of the GNU General Public License along
19  with this program; if not, write to the Free Software Foundation, Inc.,
20  51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
21  *
22  **********(*)*/
23 
24 
25 #include "core/profile.h"
26 
27 #include <iostream>
28 #include <sstream>
29 
30 Profile::Profile(const std::string& profile_file)
31 {
32  xmlProfileDoc = new TiXmlDocument();
33  assert( xmlProfileDoc );
34 
35  xml_filename = profile_file;
36 
37  xml_profile_read_ok = xmlProfileDoc->LoadFile (xml_filename.c_str());
38 }
39 
41 {
42  delete xmlProfileDoc;
43 }
44 
45 bool Profile::file_read_ok () const
46 {
47  return xml_profile_read_ok;
48 }
49 
51 {
53 }
54 
56 {
57  std::vector<std::string> variable;
58 
59  visit_node(config, root, variable);
60 }
61 
62 void Profile::visit_node(Configuration* configuration,
63  TiXmlNode* node,
64  std::vector<std::string> variable)
65 {
66  if (node) {
67  // visit the node only if it is one
68 
69  // first visit our siblings
70  visit_node(configuration, node->NextSibling(), variable);
71 
72  // then check this element contains a
73  // configuration variable
74  TiXmlElement* element = node->ToElement();
75  if (element) {
76  // append element name to variable to
77  // build fully qualified variable name
78  // before visit children
79  variable.push_back(element->Value());
80 
81  // if element contains text, we have a value for our
82  // config variable, so add it to our configuration
83  const char* text = element->GetText();
84  if (text) {
85  configuration->insert (Variable::vector_to_string(variable), text);
86 
87  //std::cerr << "[Profile] Inserted variable: " << Variable::vector_to_string(variable) << " = " << text << std::endl;
88  }
89  }
90 
91  // then descend down the tree
92  visit_node(configuration, node->FirstChild(), variable);
93  }
94 }
95 
97 {
98  //std::cerr << "Saving profile to file: " << xml_filename << std::endl;
99  return xmlProfileDoc->SaveFile(xml_filename.c_str());
100 }
101 
103 {
104  TiXmlNode* node = 0;
105 
106  // insert initial mandatory declaration if not present
107  TiXmlNode* decl = 0;
108  for (TiXmlNode* child = xmlProfileDoc->FirstChild();
109  child && !decl; child = child->NextSibling() ) {
110  decl = child->ToDeclaration ();
111  }
112  if (! decl) {
113  node = xmlProfileDoc->InsertEndChild( TiXmlDeclaration( "1.0", "UTF-8", "no" ) );
114  assert (node);
115  }
116 
117  // for each configuration variable in configuration
118  for (std::map<std::string, Variable*>::const_iterator conf_it = configuration->begin();
119  conf_it != configuration->end();
120  conf_it ++) {
121 
122  // start from root of DOM
123  node = xmlProfileDoc;
124 
125  // get the variable name and break it up in its component vector
126  std::string variable_name = conf_it->second->get_name ();
127  std::vector<std::string> variable_name_vector = Variable::string_to_vector (variable_name);
128 
129  // for each component in variable name vector
130  for (size_t i = 0; i < variable_name_vector.size(); i++) {
131 
132  // check if component element exists
133  TiXmlElement* existing = node->FirstChildElement (variable_name_vector[i].c_str());
134  if (existing) {
135  // carry on with existing component
136  node = existing;
137 
138  } else {
139  // create missing component element and carry on with new component
140  node = node->InsertEndChild (TiXmlElement (variable_name_vector[i].c_str()));
141  assert (node);
142  }
143  }
144 
145  // check if a text node for element exists
146  TiXmlText* text = 0;
147  for(TiXmlNode* child = node->FirstChild(); child && !text; child = child->NextSibling() ) {
148  text = child->ToText ();
149  }
150  if (text) {
151  // text child already exists, so remove it to set new value
152  node->RemoveChild (text);
153  }
154  node = node->InsertEndChild (TiXmlText (conf_it->second->get_value ().c_str ()));
155  assert (node);
156 
157  }
158 }
static std::vector< std::string > string_to_vector(const std::string &str)
Definition: variable.cpp:82
bool xml_profile_read_ok
Definition: profile.h:101
void insert(const std::string &variable, const std::string &value)
std::map< std::string, Variable * >::const_iterator end() const
static std::string vector_to_string(const std::vector< std::string > &var)
Definition: variable.cpp:107
std::string config
Definition: presageDemo.cpp:70
bool file_read_ok() const
Definition: profile.cpp:45
bool write_to_file() const
Definition: profile.cpp:96
void read_from_configuration(Configuration *configuration)
Definition: profile.cpp:102
TiXmlDocument * xmlProfileDoc
Definition: profile.h:99
std::string xml_filename
Definition: profile.h:100
void visit_node(Configuration *config, TiXmlNode *node, std::vector< std::string > variable)
Definition: profile.cpp:62
void read_into_configuration(Configuration *configuration)
Definition: profile.cpp:50
void init_configuration(Configuration *config, TiXmlDocument *node)
Definition: profile.cpp:55
virtual ~Profile()
Definition: profile.cpp:40
std::map< std::string, Variable * >::const_iterator begin() const
Profile(const std::string &filename)
Definition: profile.cpp:30