xmlhandler.cpp
1/***************************************************************************
2 * This file is part of the KDE project
3 * copyright (C) 2005 by Sebastian Sauer (mail@dipe.org)
4 * copyright (C) 2006 by Bernd Steindorff (bernd@itii.de)
5 *
6 * This program is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Library General Public
8 * License as published by the Free Software Foundation; either
9 * version 2 of the License, or (at your option) any later version.
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 * Library General Public License for more details.
14 * You should have received a copy of the GNU Library General Public License
15 * along with this program; see the file COPYING. If not, write to
16 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
17 * Boston, MA 02110-1301, USA.
18 ***************************************************************************/
19
20#include "xmlhandler.h"
21#include "macro.h"
22#include "macroitem.h"
23#include "action.h"
24
25#include <tqdom.h>
26#include <kdebug.h>
27
28using namespace KoMacro;
29
30namespace KoMacro {
31
36 class XMLHandler::Private
37 {
38 public:
39
44 Macro* const macro;
45
52 Private(Macro* const macro)
53 : macro(macro)
54 {
55 }
56 };
57
58}
59
61 : d( new Private(macro) )
62{
63}
64
66{
67 delete d;
68}
69
70bool XMLHandler::parseXML(const TQDomElement& element)
71{
72 // Remove old items. We should clear first.
73 d->macro->clearItems();
74
75 // We expect a <macro> element. Do we really need to be such strict or
76 // would it be more wise to trust the application in that case?
77 if(element.tagName() != "macro") {
78 kdDebug() << TQString("XMLHandler::parseXML() Invalid tagname \"%1\"").arg(element.tagName()) << endl;
79 return false;
80 }
81
82 // To be flexible with the xml-scheme, we need a version-number for xml.
83 // If there is more than one version, parsing should update old macro-data, so that it
84 // could write out in the newer version in toXML().
85 if( element.attribute("xmlversion") != "1"){
86 kdDebug() << TQString("XMLHandler::parseXML() Invalid xml-version \"%1\"").arg(element.attribute("xmlversion")) << endl;
87 return false;
88 }
89
90 // Do we need to load the macro's name?
91 // d->macro->setName(element.attribute("name"));
92
93 // Iterate through the child nodes the passed TQDomElement has and
94 // build the MacroItem elements.
95 for(TQDomNode itemnode = element.firstChild(); ! itemnode.isNull(); itemnode = itemnode.nextSibling()) {
96 // The tagname should be "item"
97 if(itemnode.nodeName() == "item") {
98 // The node is an element.
99 const TQDomElement itemelem = itemnode.toElement();
100
101 // Create a new MacroItem
102 TDESharedPtr<MacroItem> item = new MacroItem();
103
104 // Add the new item to our Macro.
105 d->macro->addItem( item );
106
107 // Each MacroItem may point to an Action instance. We
108 // try to determinate this action now and if it's defined
109 // and available, we set it.
110 TDESharedPtr<Action> action = Manager::self()->action( itemelem.attribute("action") );
111 if(action.data()) {
112 item->setAction(action);
113 }
114
115 // Set the comment
116 item->setComment( itemelem.attribute("comment") );
117
118 // Iterate through the children this item has and try
119 // to fill the list of variables our new MacroItem has.
120 for(TQDomNode childnode = itemnode.firstChild(); ! childnode.isNull(); childnode = childnode.nextSibling()) {
121 // The tagname should be "variable"
122 if(childnode.nodeName() == "variable") {
123 // The node is an element.
124 const TQDomElement childelem = childnode.toElement();
125
126 // The name the variable has.
127 const TQString name = childelem.attribute("name");
128 // The value the variable has.
129 const TQString value = childelem.text();
130
131 // Store the new variable in our macroitem.
132 item->addVariable(name, value);
133 }
134 }
135 }
136 }
137
138 // Job was done successfully.
139 return true;
140}
141
142TQDomElement XMLHandler::toXML()
143{
144 // The TQDomDocument provides us the functionality to create new TQDomElement instances.
145 TQDomDocument document;
146
147 // Create the Macro-TQDomElement. This element will be returned.
148 TQDomElement macroelem = document.createElement("macro");
149
150 // Set the Macro-XML-Version, it should be the newest Version.
151 macroelem.setAttribute("xmlversion","1");
152
153 // Do we need to store the macro's name? Normaly the application
154 // could/should take care of it cause we don't know how the app
155 // may store the XML and cause we don't like to introduce
156 // redundancy at this point.
157 //macroelem.setAttribute("name",d->macro->name());
158
159 // The list of MacroItem-children a Macro provides.
160 TQValueList<TDESharedPtr<MacroItem > > items = d->macro->items();
161
162 // Create an iterator...
163 TQValueList<TDESharedPtr<MacroItem > >::ConstIterator it(items.constBegin()), end(items.constEnd());
164 // ...and iterate over the list of children the Macro provides.
165 for(;it != end; ++it) {
166 // We are iterating over MacroItem instances.
167 TDESharedPtr<MacroItem> item = *it;
168
169 // Flag to determinate if we really need to remember this item what
170 // is only the case if comment or action is defined.
171 bool append = false;
172
173 // Each MacroItem will have an own node.
174 TQDomElement itemelem = document.createElement("item");
175
176 // Each MacroItem could point to an Action provided by the Manager.
177 const TDESharedPtr<Action> action = item->action();
178 if( action ) {
179 append = true;
180
181 // Remember the name of the action.
182 itemelem.setAttribute("action", action->name());
183
184 // Each MacroItem could have a list of variables. We
185 // iterate through that list and build a element
186 // for each single variable.
187 TQMap<TQString, TDESharedPtr<Variable > > varmap = item->variables();
188
189 for(TQMap<TQString, TDESharedPtr<Variable > >::ConstIterator vit = varmap.constBegin(); vit != varmap.constEnd(); ++vit) {
190 const TDESharedPtr<Variable> v = vit.data();
191 if(! v.data()) {
192 // skip if the variable is NULL.
193 continue;
194 }
195 // Create an own element for the variable. The tagname will be
196 // the name of the variable.
197 TQDomElement varelement = document.createElement("variable");
198
199 // Remember the name the value has.
200 varelement.setAttribute("name", vit.key());
201
202 // Remember the value as textnode.
203 varelement.appendChild(document.createTextNode(v->toString()));
204
205 // Add the new variable-element to our MacroItem.
206 itemelem.appendChild(varelement);
207 }
208 }
209
210 // Each MacroItem could have an optional comment.
211 const TQString comment = item->comment();
212 if(! comment.isEmpty()) {
213 append = true;
214 itemelem.setAttribute("comment", item->comment());
215 }
216
217 // Check if we really need to remember the item.
218 if(append) {
219 macroelem.appendChild(itemelem);
220 }
221
222 }
223
224 // Job done. Return the macro's element.
225 return macroelem;
226}
The MacroItem class is an item in a Macro and represents one single execution step.
Definition macroitem.h:47
The Macro class implements all the action-handling.
Definition macro.h:45
static Manager * self()
Definition manager.cpp:76
TDESharedPtr< Action > action(const TQString &name) const
Definition manager.cpp:132
bool parseXML(const TQDomElement &element)
Reads a given TQDomElement, extracts given Actions into the managed Macro-Instance.
~XMLHandler()
Destructor to XMLHandler .
TQDomElement toXML()
Converts the macro to a TQDomElement.
XMLHandler(Macro *const macro)
Constructor to init a XMLHandler .