Search code examples
c++xmlqtparsingqbytearray

QT5 C++ QByteArray XML Parser


I get the following xml

<Tra Type="SomeText">   
   <tr>Abcdefghij qwertzu</tr>
   <Rr X="0.0000" Y="0.0000" Z="0.0000" A="0.0000" B="0.0000" C="0.0000" />
   <Ar A1="0.0000" A2="0.0000" A3="0.0000" A4="0.0000" A5="0.0000" A6="0.0000" />
   <Er E1="0.0000" E2="0.0000" E3="0.0000" E4="0.0000" E5="0.0000" E6="0.0000" />
   <Te T21="1.09" T22="2.08" T23="3.07" T24="4.06" T25="5.05" T26="6.04" T27="7.03" T28="8.02" T29="9.01" T210="10.00" />
   <D>125</D>
   <IP></IP>
</Tra>

through a socket that saves it in a QByteArray called Data.

I want to extract and save every value from the xml to different variables (some as Integers some as QString's).

My main problem is that I dont know how to distinguish xml strings like <D>125</D> with a value in between the Tags and xml strings like <Te T210="10.00" T29="9... /> that got the value in the Tag-String itself.

My code looks like this so far:

QByteArray Data = socket->readAll();

QXmlStreamReader xml(Data);
while(!xml.atEnd() && !xml.hasError())
{
.....  
}

Solution

  • There's just so many examples already, aren't there? =(

    Anyway, like Frank said, if you want to read data (characters) from within tags - use QXmlStreamReader::readElementText.

    Alternatively, you can do this:

    QXmlStreamReader reader(xml);
    while(!reader.atEnd())
    {  
      if(reader.isStartElement())
      {
        if(reader.name() == "tr")
        {
          reader.readNext();
    
          if(reader.atEnd()) 
            break;
    
          if(reader.isCharacters())
          {
            // Here is the text that is contained within <tr>
            QString text = reader.text().toString();
          }
        }
      }
    
      reader.readNext();
    }
    

    For attributes, you should use QXmlStreamReader::attributes which will give you a container-type class of attributes.

    QXmlStreamReader reader(xml);
    while(!reader.atEnd())
    {  
      if(reader.isStartElement())
      {
        if(reader.name() == "Rr")
        {
          QXmlStreamAttributes attributes = reader.attributes();
          // This doesn't check if the attribute exists... just a warning.
          QString x = attributes.value("X").toString();
          QString y = attributes.value("Y").toString();
          QString a = attributes.value("A").toString();
          // etc...
        }
      }
    
      reader.readNext();
    }