I have a xml file that looks something like this
<App>
<FileLog>
<recording id="1" name="filename1.mp3" date="123467" length="66" />
<recording id="2" name="filename2.mp3" date="123345" length="66" />
<recording id="3" name="filename3.mp3" date="123345" length="66" />
</FileLog>
</App>
I'm trying to insert another recording element after the last recording element (the one with the highest id) using TinyXML.
My code is
string xml="C:/logs.xml";
TiXmlDocument doc(xml.c_str());
if(doc.LoadFile())
{
doc.FirstChild("FileLog");
TiXmlElement recording("recording");
recording.SetAttribute("id",4);
recording.SetAttribute("name","filenamex.mp3");
recording.SetAttribute("date",436636);
recording.SetAttribute("length",34);
doc.InsertAfterChild(recording);
}
else cout << "error loading file" << endl;
if(doc.SaveFile(xml.c_str())){
cout << "file saved succesfully.\n";
}
else cout << "error saving file" << endl;
I'm not getting my desired output. How can I get it to always input the element at the last position?
Well, based on the document, the first child of the document is App
, not FileLog
(you're also not storing the result). Something like the following should work:
if (doc.LoadFile()) {
TiXmlHandle docHandle(&doc);
TiXmlElement* fileLog = docHandle.FirstChild("App").FirstChild("FileLog").ToElement();
if (fileLog) {
TiXmlElement recording("recording");
recording.SetAttribute("id", 4);
recording.SetAttribute("name", "filenamex.mp3");
recording.SetAttribute("date", 436636);
recording.SetAttribute("length", 34);
fileLog->InsertEndChild(recording);
}
}
Note that with TiXmlHandle
, you don't need to worry about the existence of the children nodes in between - you just need to check at the end.