Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. General and Desktop
  4. Reading XML file
Forum Updated to NodeBB v4.3 + New Features

Reading XML file

Scheduled Pinned Locked Moved Solved General and Desktop
16 Posts 3 Posters 2.3k Views 1 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • R Offline
    R Offline
    russjohn834
    wrote on last edited by russjohn834
    #1

    Hi all,

    In my application, I need to implement options to save, modify, remove xml files.
    I can save the data (getting information with a tab widget), as follows:

    void StageTwoNew::on_pushButton_clicked()
    {
    
        QString filename = ui->lineEdit_3->text();
        QString path = QCoreApplication::applicationDirPath()+"/data/"+filename+".xml";
        QFile file(path);
    
        if(!file.open(QFile::WriteOnly | QFile::Text))
        {
            qDebug () << "Error saving XML file...."; 
            file.close();
            return;
        }
    
        QDomDocument xml("dataentry");
    
        QDomElement root = xml.createElement("subject details");
        root.setAttribute("catagory","run session");
        xml.appendChild(root);
    
        QDomElement tagName = xml.createElement("Name");
        root.appendChild(tagName);
        QDomText textName = xml.createTextNode(ui->lineEdit->text());
        tagName.appendChild(textName);
    
        QDomElement tagSname = xml.createElement("Surname");
        root.appendChild(tagSname);
        QDomText textSname = xml.createTextNode(ui->lineEdit_2->text());
        tagSname.appendChild(textSname);
    
        QDomElement tagPID = xml.createElement("Subject ID");
        root.appendChild(tagPID);
        QDomText textPID = xml.createTextNode(ui->lineEdit_3->text());
        tagPID.appendChild(textPID);
    
        QDomElement tagDateTime = xml.createElement("Date");
        root.appendChild(tagDateTime);
        QDomText textDateTime = xml.createTextNode(ui->dateTimeEdit->text());
        tagDateTime.appendChild(textDateTime);
    
        QDomElement tagNote = xml.createElement("Extra Note");
        root.appendChild(tagNote);
        QDomText textNote = xml.createTextNode(ui->textEdit->toPlainText());
        tagNote.appendChild(textNote);
    
    
        QTextStream output(&file);
        output << xml.toString();
    
    
        file.close();
    
        
    }
    

    I now want to implement modify part. Basically I need to open the xml file and to present content to the same tab widget for user to modify and save it.

    I did this when clicked modify button in the form:

    void MainWindow::on_pushButton_2_clicked()
    {
         QDomDocument document;
    
             QString path = QCoreApplication::applicationDirPath()+"/data/";
    
             QString filename = QFileDialog::getOpenFileName(this, ("Open file"), path, "Xml files (*.xml)");
    
            // Open a file for reading
            QFile file(filename);
            if(!file.open(QIODevice::ReadOnly | QIODevice::Text))
            {
    
                qDebug() << "Failed to open the file for reading.";
    
            }
    
            else
            {
                // loading
                if(!document.setContent(&file))
                {
               
                    qDebug() << "Failed to load the file for reading.";
    
                }
                file.close();
            }
    
            // Getting root element
            QDomElement root = document.firstChildElement();
    
            // retrievelements(QDomElement root, QString tag, QString att)
            retrievElements(root, "Dorm", "Name");
    
            qDebug() << "Reading finished";
    }
    

    Here the file is opened OK but I can't load the file for reading. What I'm doing wrong here?
    I need to load the content of xml file and present into the tab widget for the user to edit.

    Any suggestion will be helpful. Thanks in advance

    JonBJ 1 Reply Last reply
    0
    • R russjohn834

      Hi all,

      In my application, I need to implement options to save, modify, remove xml files.
      I can save the data (getting information with a tab widget), as follows:

      void StageTwoNew::on_pushButton_clicked()
      {
      
          QString filename = ui->lineEdit_3->text();
          QString path = QCoreApplication::applicationDirPath()+"/data/"+filename+".xml";
          QFile file(path);
      
          if(!file.open(QFile::WriteOnly | QFile::Text))
          {
              qDebug () << "Error saving XML file...."; 
              file.close();
              return;
          }
      
          QDomDocument xml("dataentry");
      
          QDomElement root = xml.createElement("subject details");
          root.setAttribute("catagory","run session");
          xml.appendChild(root);
      
          QDomElement tagName = xml.createElement("Name");
          root.appendChild(tagName);
          QDomText textName = xml.createTextNode(ui->lineEdit->text());
          tagName.appendChild(textName);
      
          QDomElement tagSname = xml.createElement("Surname");
          root.appendChild(tagSname);
          QDomText textSname = xml.createTextNode(ui->lineEdit_2->text());
          tagSname.appendChild(textSname);
      
          QDomElement tagPID = xml.createElement("Subject ID");
          root.appendChild(tagPID);
          QDomText textPID = xml.createTextNode(ui->lineEdit_3->text());
          tagPID.appendChild(textPID);
      
          QDomElement tagDateTime = xml.createElement("Date");
          root.appendChild(tagDateTime);
          QDomText textDateTime = xml.createTextNode(ui->dateTimeEdit->text());
          tagDateTime.appendChild(textDateTime);
      
          QDomElement tagNote = xml.createElement("Extra Note");
          root.appendChild(tagNote);
          QDomText textNote = xml.createTextNode(ui->textEdit->toPlainText());
          tagNote.appendChild(textNote);
      
      
          QTextStream output(&file);
          output << xml.toString();
      
      
          file.close();
      
          
      }
      

      I now want to implement modify part. Basically I need to open the xml file and to present content to the same tab widget for user to modify and save it.

      I did this when clicked modify button in the form:

      void MainWindow::on_pushButton_2_clicked()
      {
           QDomDocument document;
      
               QString path = QCoreApplication::applicationDirPath()+"/data/";
      
               QString filename = QFileDialog::getOpenFileName(this, ("Open file"), path, "Xml files (*.xml)");
      
              // Open a file for reading
              QFile file(filename);
              if(!file.open(QIODevice::ReadOnly | QIODevice::Text))
              {
      
                  qDebug() << "Failed to open the file for reading.";
      
              }
      
              else
              {
                  // loading
                  if(!document.setContent(&file))
                  {
                 
                      qDebug() << "Failed to load the file for reading.";
      
                  }
                  file.close();
              }
      
              // Getting root element
              QDomElement root = document.firstChildElement();
      
              // retrievelements(QDomElement root, QString tag, QString att)
              retrievElements(root, "Dorm", "Name");
      
              qDebug() << "Reading finished";
      }
      

      Here the file is opened OK but I can't load the file for reading. What I'm doing wrong here?
      I need to load the content of xml file and present into the tab widget for the user to edit.

      Any suggestion will be helpful. Thanks in advance

      JonBJ Offline
      JonBJ Offline
      JonB
      wrote on last edited by
      #2

      @russjohn834
      I assume you mean it fails on document.setContent(&file)? So use the https://doc.qt.io/qt-5/qdomdocument.html#setContent-6 overload to obtain all the error information via the optional parameters?

      1 Reply Last reply
      2
      • R Offline
        R Offline
        russjohn834
        wrote on last edited by
        #3

        @JonB Thank you. Could you please show me how to use optional parameters of setContent to get error information?

        jsulmJ JonBJ 2 Replies Last reply
        0
        • R russjohn834

          @JonB Thank you. Could you please show me how to use optional parameters of setContent to get error information?

          jsulmJ Offline
          jsulmJ Offline
          jsulm
          Lifetime Qt Champion
          wrote on last edited by jsulm
          #4

          @russjohn834 Please read documentation, this is nothing special:

          QString errorMsg;
          int errorLine;
          int errorColumn;
          if(!document.setContent(&file, &errorMessage, &errorLine, &errorColumn))
          

          https://forum.qt.io/topic/113070/qt-code-of-conduct

          1 Reply Last reply
          1
          • R russjohn834

            @JonB Thank you. Could you please show me how to use optional parameters of setContent to get error information?

            JonBJ Offline
            JonBJ Offline
            JonB
            wrote on last edited by JonB
            #5

            @russjohn834
            Well I'm not a C++-er, I thought you'd know from the doc page syntax, you're already managing to pass &file for QIODevice *dev.

            QDomDocument::setContent(QIODevice *dev, QString *errorMsg = nullptr, int *errorLine = nullptr, int *errorColumn = nullptr)
            

            so something like

            QFile file;
            QString errorMsg;
            int errorLine, errorColumn;
            if (!document.setContent(&file, &errorMsg, &errorLine, &errorColumn))
            {
                qDebug () << errorMsg << errorLine << errorColumn
            }
            

            and then look at your XML in that light.

            1 Reply Last reply
            3
            • R Offline
              R Offline
              russjohn834
              wrote on last edited by
              #6

              Thank you @JonB, @jsulm

              I'm getting following error (AND error line and column) while loading the xml file:

              "unexpected character" 2 18

              I'm trying to read xml file, which looks like this:

              <!DOCTYPE detailsentry>
              <subject details catagory="run session">
               <Name>Rob</Name>
               <Surname>John</Surname>
               <Patient ID>PID12HL</Patient ID>
               <Date>06/11/2019 20:00</Date>
               <Clinician Note>Some notes to test this section</Clinician Note>
              </subject details>
              

              Any thoughts where I'm getting wrong!?

              JonBJ 1 Reply Last reply
              0
              • R russjohn834

                Thank you @JonB, @jsulm

                I'm getting following error (AND error line and column) while loading the xml file:

                "unexpected character" 2 18

                I'm trying to read xml file, which looks like this:

                <!DOCTYPE detailsentry>
                <subject details catagory="run session">
                 <Name>Rob</Name>
                 <Surname>John</Surname>
                 <Patient ID>PID12HL</Patient ID>
                 <Date>06/11/2019 20:00</Date>
                 <Clinician Note>Some notes to test this section</Clinician Note>
                </subject details>
                

                Any thoughts where I'm getting wrong!?

                JonBJ Offline
                JonBJ Offline
                JonB
                wrote on last edited by JonB
                #7

                @russjohn834
                Yes, on line #2 at character #18! That's what the error info is telling you!

                <subject details catagory="run session">
                

                Count to character #18. What is that space in details catagory? (BTW, if you care, category is the correct spelling.) You can't have a space there. Nor for that matter in your <Patient ID> and others. Where did you get this XML from? You need to test your code with well-formed XML before you do anything.

                1 Reply Last reply
                3
                • R Offline
                  R Offline
                  russjohn834
                  wrote on last edited by
                  #8

                  Thank you @JonB !

                  Now I can load the xml file:

                  <!DOCTYPE detailsentry>
                  <subject_details>
                   <Name>Pete</Name>
                   <Surname>Batty</Surname>
                   <Patient_ID>GH34TRM</Patient_ID>
                   <Date>06/11/2019 16:00</Date>
                   <Clinician_Note>test note to display</Clinician_Note>
                  </subject_details>
                  

                  I'm trying to parse data ( Name, Surname, Patient_ID, Date and Clinician_Note ) from this xml file.

                   domDocument.setContent(&file);
                   QDomElement topElement = domDocument.documentElement();
                   QDomNode domNode = topElement.firstChild();
                  
                   while (!domNode.isNull())
                   {
                      QDomElement domElement = domNode.toElement();
                       if (!domElement.isNull())
                          {
                           qDebug()<<"Tag name"<<topElement.tagName();
                          }
                    domNode = domNode.nextSibling();
                   }
                  
                  

                  This does output Tag name "subject_details" for 5 times. How can I parse content in each line?

                  JonBJ 1 Reply Last reply
                  0
                  • R russjohn834

                    Thank you @JonB !

                    Now I can load the xml file:

                    <!DOCTYPE detailsentry>
                    <subject_details>
                     <Name>Pete</Name>
                     <Surname>Batty</Surname>
                     <Patient_ID>GH34TRM</Patient_ID>
                     <Date>06/11/2019 16:00</Date>
                     <Clinician_Note>test note to display</Clinician_Note>
                    </subject_details>
                    

                    I'm trying to parse data ( Name, Surname, Patient_ID, Date and Clinician_Note ) from this xml file.

                     domDocument.setContent(&file);
                     QDomElement topElement = domDocument.documentElement();
                     QDomNode domNode = topElement.firstChild();
                    
                     while (!domNode.isNull())
                     {
                        QDomElement domElement = domNode.toElement();
                         if (!domElement.isNull())
                            {
                             qDebug()<<"Tag name"<<topElement.tagName();
                            }
                      domNode = domNode.nextSibling();
                     }
                    
                    

                    This does output Tag name "subject_details" for 5 times. How can I parse content in each line?

                    JonBJ Offline
                    JonBJ Offline
                    JonB
                    wrote on last edited by
                    #9

                    @russjohn834 said in Reading XML file:

                    qDebug()<<"Tag name"<<topElement.tagName();
                    

                    This does output Tag name "subject_details" for 5 times. How can I parse content in each line?

                    Now come on :) Nicely, if it prints the same thing 5 times, look at what it's printing! topElement doesn't change in the loop, does it? But domElement does ...

                    1 Reply Last reply
                    5
                    • R Offline
                      R Offline
                      russjohn834
                      wrote on last edited by russjohn834
                      #10
                      This post is deleted!
                      JonBJ 1 Reply Last reply
                      0
                      • R russjohn834

                        This post is deleted!

                        JonBJ Offline
                        JonBJ Offline
                        JonB
                        wrote on last edited by JonB
                        #11

                        @russjohn834
                        I'm not going to answer every question, you have to do some work yourself! Did you try looking at the documentation for QDomElement since that is what you are asking about? Did you like the look of https://doc.qt.io/qt-5/qdomelement.html#text?

                        1 Reply Last reply
                        1
                        • R Offline
                          R Offline
                          russjohn834
                          wrote on last edited by russjohn834
                          #12

                          Thanks @JonB . Sorry I just found what I need. I can directly parse content of eachdomElement by following

                          QDomElement topElement = domDocument.documentElement();
                          topElement.elementsByTagName("Name").at(0).firstChild().nodeValue();
                          topElement.elementsByTagName("Surname").at(0).firstChild().nodeValue(); ....
                          
                          JonBJ 1 Reply Last reply
                          0
                          • R russjohn834

                            Thanks @JonB . Sorry I just found what I need. I can directly parse content of eachdomElement by following

                            QDomElement topElement = domDocument.documentElement();
                            topElement.elementsByTagName("Name").at(0).firstChild().nodeValue();
                            topElement.elementsByTagName("Surname").at(0).firstChild().nodeValue(); ....
                            
                            JonBJ Offline
                            JonBJ Offline
                            JonB
                            wrote on last edited by
                            #13

                            @russjohn834
                            You can, but why change over to that way of doing it when you are already using QDomElement calls elsewhere which is more convenient?

                            1 Reply Last reply
                            1
                            • R Offline
                              R Offline
                              russjohn834
                              wrote on last edited by russjohn834
                              #14

                              I was too much confused about different terminologies of xml and methods of QDomDocument. I'm fiddling with my very basic knowledge to parse data from xml :) Yes, the documentation makes it more clear.

                              @JonB said in Reading XML file:

                              @russjohn834
                              You can, but why change over to that way of doing it when you are already using QDomElement calls elsewhere which is more convenient?

                              Did not get your point. You recommend topElement.elementsByTagName("Name").at(0).firstChild().nodeValue();
                              than using loop to fetch content?

                              JonBJ 1 Reply Last reply
                              0
                              • R russjohn834

                                I was too much confused about different terminologies of xml and methods of QDomDocument. I'm fiddling with my very basic knowledge to parse data from xml :) Yes, the documentation makes it more clear.

                                @JonB said in Reading XML file:

                                @russjohn834
                                You can, but why change over to that way of doing it when you are already using QDomElement calls elsewhere which is more convenient?

                                Did not get your point. You recommend topElement.elementsByTagName("Name").at(0).firstChild().nodeValue();
                                than using loop to fetch content?

                                JonBJ Offline
                                JonBJ Offline
                                JonB
                                wrote on last edited by
                                #15

                                @russjohn834
                                My thought/inclination is to make the reading code look like the code you already show, which uses QDomElement. So something like:

                                QDomNode domElement = topElement.elementsByTagName("Name").at(0).firstChild();
                                QDomElement domElement = domNode.toElement();
                                if (!domElement.isNull())
                                    return domElement.text();
                                

                                It's just a matter of style. If I access things in one place via QDomElement calls, with its dedicated text() method, I prefer not to go via QDomNode and its nodeValue() method somewhere else. Just makes code easier to search/maintain/debug if you keep consistency where possible.

                                1 Reply Last reply
                                2
                                • R Offline
                                  R Offline
                                  russjohn834
                                  wrote on last edited by
                                  #16

                                  Thanks for your feedback @JonB , @jsulm

                                  1 Reply Last reply
                                  1

                                  • Login

                                  • Login or register to search.
                                  • First post
                                    Last post
                                  0
                                  • Categories
                                  • Recent
                                  • Tags
                                  • Popular
                                  • Users
                                  • Groups
                                  • Search
                                  • Get Qt Extensions
                                  • Unsolved