2012-03-21 39 views
6

Tôi có một ứng dụng tạo trình đơn bên trái dựa trên thành phần Qt của cây. Để tải nó, tôi cần phải phân tích cú pháp một tệp XML. Tệp XML trông giống như:Cập nhật tệp XML bằng cách sử dụng Qt DOM

<comandos> 
     <categoria> 
       <nome>Cupom fiscal</nome> 
       <comando> 
         <nome>01 - Abrir Cupom Fiscal</nome> 
         <env>3</env> 
         <rec>4</rec> 
         <desc>CNPJ/CPF : </desc> 
         <desc>Nome : </desc> 
         <desc>Endereco: </desc> 
       </comando> 
     </categoria> 
</comandos> 

Tôi thực sự có thể đọc XML này bằng QtDOM.

QDomDocument doc("ComandosML"); 

    QFile file("comandos.xml"); 

    int r = 0; 

    datafields.clear(); 
    receFields.clear(); 
    categories.clear(); 

    if(!file.open(QIODevice::ReadOnly)) 
     return -1; 

    if(!doc.setContent(&file)) 
    { 
     file.close(); 
     return -2; 
    } 

    // Ok we are ready to parse DOM 
    QDomElement root = doc.documentElement(); 
    if(root.tagName() != "comandos") 
     return -3; 

    QDomNode n = root.firstChild(); 
    while(!n.isNull()) 
    { 
      QDomElement e = n.toElement(); 
      if(!e.isNull()) 
      { 
      if(e.tagName() == "categoria") 
      { 
       QDomNode cat = n.firstChild(); 
       while(!cat.isNull()) 
       { 
        QDomElement CatName = cat.toElement(); 

        if (CatName.tagName() == "nome") 
        { 
         QString s = CatName.text(); 

         if (s != "") 
         { 
          categories.push_back(s); 
          item = new QStandardItem((s)); 
          item->setEditable(false); 
         } 
        } 

        if (CatName.tagName() == "comando") 
        { 

         QDomNode params = cat.firstChild(); 
         QString qdCmd; 
         int env = 0; 
         int rec = 0; 
         Categories Desc; 

         while (!params.isNull()) 
         { 
          QDomElement ParamName = params.toElement(); 

          if (ParamName.tagName() == "nome") 
          { 
           qdCmd = ParamName.text(); 
           child = new QStandardItem((qdCmd)); 
           child->setEditable(false); 
           child->setDragEnabled(false); 
           item->appendRow(child); 
          } 
          else 
          if (ParamName.tagName() == "env") 
          { 
           env = ParamName.text().toInt(); 
          } 
          else 
          if (ParamName.tagName() == "rec") 
          { 
           rec = ParamName.text().toInt(); 
          } 
          else 
          if (ParamName.tagName() == "desc") 
          { 
           Desc.push_back(ParamName.text()); 
          } 

          params = params.nextSibling(); 
         } 

         datafields.insert(pair<QString,int>( qdCmd,  env )); 
         receFields.insert(pair<QString,int>( qdCmd,  rec )); 
         descriptions.insert(pair<QString, Categories>(qdCmd, Desc)); 
        } 
        cat= cat.nextSibling(); 
       } 
       model->setItem(r++,item); 
      } 
      } 
      n = n.nextSibling(); 
    } 

    file.close(); 

    return 0; 

Giữa phân tích cú pháp Tôi đã lắp ráp menu. Sau khi tất cả, tôi đã có tất cả các thiết lập để cập nhật XML khi người dùng chỉnh sửa các tập tin xml và tải lại tại ứng dụng, tôi chỉ cần xóa cây và tạo lại nó. Bạn có thể thấy rằng tôi cũng truyền một số dữ liệu vào một số cấu trúc, chúng về cơ bản là std :: vector và std :: map. Đoạn mã trên đã được viết với các ví dụ từ tài liệu Qt, mà khá phong nha bằng cách này.

Điều xảy ra là tôi đã viết một hộp thoại đơn giản để làm cho người dùng tránh chỉnh sửa XML. Ok, đối với tôi, có thể dễ dàng và đơn giản hơn để chỉnh sửa XML ngay cả từ góc độ người dùng, nhưng những người dùng có thể sẽ thích chỉnh sửa mọi thứ trên hộp thoại. Tất cả đều ổn. Tôi có thể lấy dữ liệu chuyển nó vào ứng dụng. Không có rắc rối gì cả.

Nhưng tôi cần cập nhật XML. Về cơ bản, bản chỉnh sửa sẽ bao gồm việc cập nhật nút bằng cách thêm nút mới hoặc chèn nút con vào bên dưới. Làm thế nào để cập nhật một nút? Có cách nào cụ thể để thực hiện điều đó không? Kinh nghiệm của tôi với XML là ngắn, tôi thường viết, cập nhật, phân tích cú pháp các tệp txt và nhị phân.

tôi muốn làm một cái gì đó như:

if(root.tagName() != "comandos") 
     return -3; 

    QDomNode n = root.firstChild(); 
    while(!n.isNull()) 
    { 
      QDomElement e = n.toElement(); 
      if(!e.isNull()) 
      { 
      if(e.tagName() == "categoria") 
      { 
       QDomNode cat = n.firstChild(); 
       while(!cat.isNull()) 
       { 

        QDomElement CatName = cat.toElement(); 

        if (CatName.tagName() == "nome") 
        { 
         QString s = CatName.text(); 

         if (s != qsCategory) 
         { 
          // we have not found the category 
          // add it here 

         } 
         else 
         { 
          // the category exists simply update 
         } 



        } 

        cat= cat.nextSibling(); 
       } 
      } 
      } 
      n = n.nextSibling(); 
    } 

Có vẻ như rằng việc sử dụng Qt Dom là khá phong nha để phân tích và tạo file XML, nhưng nó thiếu các công cụ để cập nhật. Bất kỳ trợ giúp nào cũng sẽ được đánh giá cao, thậm chí là một ví dụ.

chủ đề này khác ở đây, trông rất hữu ích

Edit Value of a QDomElement?

Tôi đã nhìn qua internet cho các ví dụ mà sẽ cập nhật một tập tin XML. Có vẻ như nếu tôi nắm bắt được nút hiện tại, tôi có thể thêm một đứa trẻ vào nó, cho đến nay tôi đã không tìm ra cách để làm như vậy.

Cảm ơn sự giúp đỡ và rõ ràng là xin lỗi vì sự thiếu hiểu biết của tôi.

+1

nó là gì mà bạn muốn hơn là câu trả lời bạn đề cập đến? – Koying

+0

Xin chào, tôi muốn cập nhật nút. Ví dụ: người dùng sẽ nhập danh mục, lệnh và dữ liệu khác, và điều này cần được cập nhật trong XML. Tôi không tìm ra cách chèn một nút mới nhưng dựa trên một tồn tại trước đó. – zlogdan

Trả lời

7

QDomElement newCategoriaTag = doc.createElement(QString("categoria")); 
QDomElement newNomeTag = doc.createElement(QString("nome")); 
QDomText newNomeText = doc.createTextNode(QString("Cupom fiscal 2")); 
newNomeTag.appendChild(newNomeText); 
newCategoriaTag.appendChild(newNomeTag); 
root.appendChild(newCategoriaTag); 

này sẽ cho kết quả:

<comandos> 
     <categoria> 
       <nome>Cupom fiscal</nome> 
       <comando> 
         <nome>01 - Abrir Cupom Fiscal</nome> 
         <env>3</env> 
         <rec>4</rec> 
         <desc>CNPJ/CPF : </desc> 
         <desc>Nome : </desc> 
         <desc>Endereco: </desc> 
       </comando> 
     </categoria> 
     <categoria> 
       <nome>Cupom fiscal 2</nome> 
     </categoria> 
</comandos> 
+0

Rất nhiều người cảm ơn, tôi nghĩ bạn đã cho tôi câu trả lời. – zlogdan

Các vấn đề liên quan