Using Qt's XML library for simple operation - c++

I basically want to use the XML parser from Qt in my existing project. I have only used Qt once before, and that was with Qt Designer, and I am not having much luck finding anything on Google about how to just use the XML library.
I have downloaded a web page that has one large list, and I want to parse it and add each list item to a c++ list. I found this sample code on Ubuntu forums...
http://www.uluga.ubuntuforums.org/showpost.php?p=9112973&postcount=6
I want to use that except I need to know what exactly I need to add to the project to get access to it.
One other small question is QDomDocument seems to be for files (makes sense) but I have the XML in a string. What part of the XML library works for contents of a string?

The following code should give you a quick view of what to do with Qt XML features for what you need.
#include <list>
#include <QDomDocument>
#include <QFile>
int main()
{
QString filename("myfile.xml");
std::list<QString> result;
int errorLine, errorColumn;
QString errorMsg;
QFile modelFile(filename);
QDomDocument document;
if (!document.setContent(&modelFile, &errorMsg, &errorLine, &errorColumn))
{
QString error("Syntax error line %1, column %2:\n%3");
error = error
.arg(errorLine)
.arg(errorColumn)
.arg(errorMsg);
return false;
}
QDomElement rootElement = document.firstChild().toElement();
for(QDomNode node = rootElement.firstChild();
!node .isNull();
node = node .nextSibling())
{
QDomElement element = node.toElement();
result.push_back(element.tagName());
}
return 0;
}
UPDATE
I believe you only need core Qt library as well as XML library.

You have to add QtXml in the .pro file and include QDomDocument
or only include QDomDocument like
include <QtXml/QDomDocument>

Related

Is it possible to have each page of a Stacked Widget specified in a separate ui file

I am using the Stacked Widget in Qt Creator v4.14.2. Right now all of the items for each page reside in the mainwindow.ui file. I do not have a problem switching between pages.
I am wanting to put the items for each Stacked Widget page in a separate ui file for clarity and file size reasons. I understand that there is not a technically reason for this need. I have developed UIs using MVVM and would like to replicate that methodology in Qt (using Qt Creator) if at all possible.
For this project I am working on, I would prefer not do page and/or Widget creation in the C++ code.
You can load as many UI files as you need using QUiLoader. Assuming the files are named page-1.ui, ... page-10.ui you could have something like (untested)...
#include <QStackedWidget>
#include <QUiLoader>
#include <QWidget>
.
.
.
QStackedWidget stack;
QUiLoader loader;
for (int page_no = 1; page_no <= 10; ++page_no) {
QFile f(QString("page-%1.ui").arg(page_no));
if (f.open(QFile::ReadOnly)) {
auto *w = loader.load(&f);
stack.addWidget(w);
} else {
qWarning() << "failed to load UI file.";
}
}

Displaying picture that is not in resources of Qt

I am currently writing an application in Qt, which is basically a warehouse. An application reads CSV, enables user to process it and enables to show picture of each good. I tried displaying picture using QLabel and Pixmap, however nothing happens even though the file is in the same folder and the name provided is exactly as it should be. Is it the resources issue or my code fails somehow? Is there any possibility to display the image without adding it to resources in order to avoid adding many photos manually?
void ImageViewer::viewImage(QString imgName)
{
QString pathWithName = imgName;
pathWithName.append(".jpg");
ui->label->setPixmap( QPixmap(pathWithName) );
ui->label->show();
update();
}
Sorry for any mistakes in post creation or code displaying here- it's my first post.
Edit:
I am adding code from MainWindow (called CsvReader in my project) to how I'm invoking the method viewImage:
void CsvReader::on_imgView_clicked()
{
ImageViewer* img = new ImageViewer(this);
img->setModal(true);
img->exec();
QModelIndex List selInd ui->tableView->selectionModel()->selectedIndexes();
QString id = model->item(selInd.first().row(), 0)->text();
img->viewImage(id);
}
Edit 2:
Solved. Had to change path using QDir:
QDir* directory = new QDir("/home/kokos/Magazyn/photos");
QFileInfo checkFile(*directory, pathWithName);
Thanks in advance,
Kokos
Confirm your file's location and existence first. Add this;
QFileInfo checkFile(pathWithName);
if (checkFile.exists() && checkFile.isFile()) {
// your code
}

QT Creator Main.cpp MainWindow.cpp

I'm currently working on my project for my Master thesis in Mechatronics/Robotics. The goal of y project is to read in a .stl-File and calculate the path for an industrial robot.
Till now everything worked fine for me, but now my professor wants me to develop a GUI, because till now I was just using the command window and wrote all parameters manual. Now I'm working with Qt Creator and developed a simple GUI for my project.
In this interface I got a RadioButton for ascii files. In order my functions work I have to determine if the user is entering a ascii file or an binary file. But here's my first problem. In the command window I just check the argv[] for the string "-ascii". If the user enters this, a flag is set to false.
if(0 == strcmp(argv[i], "-ascii")) {
isBinaryFormat = false;
}
Now I just want to do the same int the GUI. If the RadioButton is checked flag is set to false. So I wrote the following in the main.cpp file
if(ui->radioButton->isChecked()) {
isBinaryFormat = false;
}
But ui is unknown in the main function. After searching for help on google I just found tutorials writing the code in the mainwindow.cpp file. But how can I send the information form the mainwindow file to my main function in the main.cpp file.
A second question would be, if I use the QFileDialog::getOpenFilename method, how can I hand the file name to my other functions. The idea is, the user selects a file anywhere on his PC, and the program opens the file and processes it. But here I got the same problem. I can brows for a file, but how can I transfer the information from the mainwindow.cpp to my main.cpp.
I'm thankful for any help I get. Very grateful a lonely coder
First of all you don't write UI Code in the main.cpp.
You write it where the MainWindow Class is so in MainWindow.cpp and MainWindow.h.
Then your ui-> will work because it then has access to that namespace.
I don't see why you would have functions in Main.cpp?
Without seeing more code you're not likely to get an answer to that.
If you want to use external functions in your classes either declare the methods in the class directly or create a new file like global_function.h and .cpp which you can include in your class. ( don't forget the header guards )
Also shouldn't that code look like this:
if(!ui->radioButton->isChecked())
{
isBinaryFormat = false;
}
because of:
If the RadioButton is checked flag is set to false.
QString fileName = QFileDialog::getOpenFileName(this, tr("Open File"),
"/home",
tr("Images (*.png *.xpm *.jpg)"));
getOpenFileName( ) will return a string containing the path and filename of the selected file which you can pass to your functions then.
Please read some more about how to use Qt.
It's not just about the files, there's a class, too. Learn about them. Solution is to add a getter to your MainWindow class that will return whether the radioButton is checked:
class MainWindow : public QMainWindow
{
public:
// optionally, move implementation in the source file
bool isBinaryFormatChecked() const
{
return ui->radioButton->isChecked();
}
// other stuff ...
};
And then you can access it in your main like window.isBinaryFormatChecked() orwindow->isBinaryFormatChecked() depending on whether you have a pointer or not. Another way would be to make ui in your MainWindow public, so you could access the whole user interface, but that breaks proper encapsulation.
I think you need to go through a few of the (excellent in my opinion) examples supplied with Qt before attempting to integrate your already working console code.
Essentially you really don't want to do that check in the main.cpp, but if you must you could have it in a public function of the mainwindow and call that from your main.cpp file. But then that doesn't really make sense as you don't want to check whether the appropriate radio button is set until the user inputs something. You're going to have to read up on event based programming.

QWebEngine: print a page?

The migration from QWebKit to QWebEngine seems to be much more complicated than Qt guys claimed. With QWebKit I could print a webpage easily via
QWebView->print(&printer);
With QWebEngine class QWebEngine view does not provide a method print(). Their browser example uses a class named QWebEngineFrame which offers a method print() - but the whole QWebEngineFrame is not defined anywhere!
So my question: how do I print a page using QWebEngine?
I think the correct way to use QWebEngineView::render method because QWebEngineView is a QWidget. It accepts paint device as a first argument and you may pass QPrinter there for printing.
Update: If you can use the latest version of Qt, in Qt 5.8 a new function for printing page was added:
void QWebEnginePage::print(QPrinter *printer, FunctorOrLambda resultCallback);
Actually it first prints to temp PDF with QPrinter settings.
Here is the link to Qt docs.
You can read about this in our blog also.
I would offer following code (for a while):
QTextEdit *textEdit = new QTextEdit;
ui.myWebView->page()->toHtml([textEdit](const QString &result){ textEdit->setHtml(result); });
textEdit->print(somerinter);
textEdit->deleteLater();
Qt 5.7 includes print support in to pdf files for QWebEngine.
Use printToPdf function to export the current page in a pdf file. Example:
const QString fileName = QFileDialog::getSaveFileName(0,
tr("Save pdf"),
".",
tr("PDF Files (*.pdf)"));
if (fileName.isEmpty()) {
return;
}
ui->webView->page()->printToPdf(fileName);
QWebView->page()->print(&printer, [=](bool){});

Generating word documents (.doc/.odt) through C++/Qt

I am using Qt 4.5.3 and Windows XP. I need my application to generate documents that contains the information that is being used and generated. The information that is being used will be just strings (QString to be more specific) and the information that is being generated will be strings and images as well.
I want documents to be a MS word document (.doc) or can be an Open Document Format (.odt) Also I want the documents to be formatted with fonts,images, tables of data, some background colors and all.
I have done the creation PDF files using QTextDocument, QTextCursor and QPrinter. But when I tried to apply the same QTextDocument for odt, I ended up with just format error.
Is there a way to generate such documents using any other libraries that use C++? How you guys use to generate such documents (.odt/.doc) in C++? Any pointers, links, examples regarding this are welcome.
I have done this through the Qt way. i.e by using ActiveQt module.
The reference documentation for MS Word can be obtained through,
MSDN documentation, which actually pointed to the VBAWD10.chm file that has the ActiveX apis for MS Word.
The Word Application can be initialized by
QAxWidget wordApplication("Word.Application");
The sub-objects of the word application can be obtained through the function,
QAxBase::querySubObject()
For e.g:
QAxObject *activeDocument = wordApplication.querySubObject("ActiveDocument");
To pass the obtained sub-object as an argument,
QVariant QAxBase::asVariant () const
Any function calls involving the word object can be called using the function using,
QAxBase::dynamicCall ()
For e.g:
activeDocument->dynamicCall("Close(void)");
After a quite good amount of struggle and few convinces, it's working fine. :)
Hope it helps for those who are all looking for similar solutions...
maybe you can use this and write to a file in odf format http://doc.trolltech.com/4.6/qtextdocumentwriter.html#supportedDocumentFormats qt does not know how to output doc docx etc but you can use com(activeQt) or some other library to write in those or other formats you need
For me, a better way of automating Office applications is importing the object model from the MS Word COM type library into the C++ project. This is very similar to the Qutlook Example for the Outlook application. You can extrapolate the technique to Excel and PowerPoint if you want, using oleview.exe to obtain the library Guids. Here is a complete project at GitHub.
The QMake project file :
QT += widgets axcontainer
CONFIG += c++11 cmdline
DEFINES += QT_DEPRECATED_WARNINGS
DUMPCPP=$$absolute_path("dumpcpp.exe", $$dirname(QMAKE_QMAKE))
TYPELIBS = $$system($$DUMPCPP -getfile {00020905-0000-0000-C000-000000000046})
isEmpty(TYPELIBS) {
message("Microsoft Word type library not found!")
REQUIRES += StackOverflow Rocks
} else {
SOURCES = main.cpp
}
The main.cpp source:
#include <QApplication>
#include <QStandardPaths>
#include <QDir>
#include "MSWORD.h"
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
Word::Application word;
if (!word.isNull()) {
word.SetVisible(false);
Word::Documents* docs = word.Documents();
Word::Document* newDoc = docs->Add();
Word::Paragraph* p = newDoc->Content()->Paragraphs()->Add();
p->Range()->SetText("Hello Word Document from Qt!");
p->Range()->InsertParagraphAfter();
p->Range()->SetText("That's it!");
QDir outDir(QStandardPaths::writableLocation(QStandardPaths::DocumentsLocation));
QVariant fileName = outDir.absoluteFilePath("wordaut.docx");
QVariant format = Word::wdFormatXMLDocument;
newDoc->SaveAs2(fileName, format);
QVariant fileName2 = outDir.absoluteFilePath("wordaut2.doc");
QVariant format2 = Word::wdFormatDocument;
newDoc->SaveAs2(fileName2, format2);
newDoc->Close();
word.Quit();
}
return 0;
}