.. --------------------------------------------------------------------------- Copyright (C) 2012 Digia Plc and/or its subsidiary(-ies). All rights reserved. This work, unless otherwise expressly stated, is licensed under a Creative Commons Attribution-ShareAlike 2.5. The full license document is available from http://creativecommons.org/licenses/by-sa/2.5/legalcode . --------------------------------------------------------------------------- Creating the NoteApp Qt Application =================================== The goal is to create a single executable NoteApp* binary file that the user will just run to get *NoteApp* loaded. Let's see how we can use Qt Creator for this. Creating a Qt Quick Application ------------------------------- First we need to create a :creator:`Qt Quick Application ` using Qt Creator and make sure that we have selected *Built-in elements only (for all platforms)** in the Qt Quick Application wizard. Let's name the application *noteapp*. So now we have a newly created project from the wizard and we notice that a qmlapplicationviewer* project is generated for us. The generated *qmlapplicationviewer* project is a basic 'template' application that loads QML files. This application, as being a very generic one for deploying Qt Quick applications across devices and targets, includes several platform specific code for each of those deployment targets. We will not go through these specific parts of the code because it doesn't fit the purpose of this guide. Nevertheless, there are certain peculiarities of the qmlapplicationviewer* that somewhat limit us to achieve what we want. The application expects the developer to ship the QML files along with with the executable binary. Using the Qt Resource System becomes impossible, but you will see how to overcome this problem as we proceed. For the noteapp* project, there is just one CPP source file, `main.cpp`. In the `main.cpp` file, you will see how the `viewer` object, the `QmlApplicationViewer` class, is used to load the `main.qml` file by calling the `QmlApplicationViewer::setMainQmlFile()` function. .. code-block:: cpp // main.cpp ... Q_DECL_EXPORT int main(int argc, char argv[]) { QScopedPointer app(createApplication(argc, argv)); QScopedPointer viewer( QmlApplicationViewer::create()); viewer->setOrientation(QmlApplicationViewer::ScreenOrientationAuto); viewer->setMainQmlFile("qml/noteapp/main.qml"); viewer->showExpanded(); return app->exec(); } Note, there is a basic `main.qml` file generated by the Qt Quick Application wizard which will be replaced by the `main.qml` file we have created for NoteApp*. The folder structure of the generated noteapp* project is very straightforward to understand. noteapp - root folder of the *noteapp* project qml - this folder contains all the QML files qmlapplicationviwer - the generated application used for loading QML files noteapp.pro - the project file main.cpp - the C++ file where a Qt Application is created that will produce a binary file for us We need to copy our QML files including the `fonts` and `images` directories in the `qml` directory of the newly created noteapp* project. Additionally, we need to import these files into the project so that we will be able to work with them in Qt Creator. .. image:: img/importqmlfiles.png :scale: 80% :align: center .. note:: Make sure to add all existing files including images called from the `nodeDDB.js` file At this point, let's start to build and run the project and see if everything has gone well with the project creation. Before building the noteapp* project, let's make sure we have the right settings in place for our project. Please refer to :creator:`Configure Projects ` in Qt Creator documentation. Once the application is successfully built, an executable binary file called `noteapp` should be produced in the root folder of the project. If you have Qt configured properly for your system, you'll be able run the file by clicking on it. Using Qt Resource System to Store QML Files and Images ------------------------------------------------------ We have created an executable that loads the QML file for the application to run. As you can see in the `main.cpp` file, the `viewer` object loads the `main.qml` file by passing the relative path of that file. Additionally, we open the `noteapp.pro` file to understand deployment and build settings so we notice the first lines: .. code-block:: bash # Add more folders to ship with the application, here folder_01.source = qml/noteapp folder_01.target = qml DEPLOYMENTFOLDERS = folder_01 .... Seems that it is expected to actually ship the QML files along with the executable file, but this is not what we would like to achieve. Qt provides a quite intuitive :qt:`Resource System ` that works seamlessly with QML. We need to create a resource file, `noteapp.qrc` for the noteapp* root project so that we can add our QML and image files in it. Please refer to the :qt:`Creating a Resource File ` in Qt Creator documentation for detailed steps. .. image:: img/resourcefile.png :scale: 100% :align: center We need to apply minor changes to the `noteapp.pro` and the `main.cpp` in order to be able to use the newly created resource file, `noteapp.qrc`. First we comment out the first lines in the `noteapp.pro`: .. code-block:: bash # Add more folders to ship with the application, here #folder_01.source = qml/noteapp #folder_01.target = qml #DEPLOYMENTFOLDERS = folder_01 .... In addition to that, we can remove the following lines from the `noteapp.pro` file since they are Symbian platform related. .. code-block:: bash ... symbian:TARGET.UID3 = 0xE68D5D88 ... # Allow network access on Symbian symbian:TARGET.CAPABILITY += NetworkServices ... In the `main.cpp` file, we see the `QmlApplicationViewer::setMainQmlFile()` function being called with the relative path to the `main.qml` file. .. code-block:: cpp // qmlapplicationviewer.cpp ... void QmlApplicationViewer::setMainQmlFile(const QString &file) { d->mainQmlFile = QmlApplicationViewerPrivate::adjustPath(file); setSource(QUrl::fromLocalFile(d->mainQmlFile)); } ... The `QmlApplicationViewer` class inherits :qt:`QDeclarativeView `, which is a convenient class for loading and displaying QML files. The `QmlApplicationViewer::setMainQmlFile()` function is not optimized for using resources because it adjusts the path of the QML file before calling the :qt:`setSource() ` function. The simplest approach to overcome this would be to directly call :qt:`setSource() ` on the `viewer` object in the `main.cpp` file, but this time we pass the `main.qml` as part of the resource file. .. code-block:: cpp // main.cpp ... Q_DECL_EXPORT int main(int argc, char argv[]) { QScopedPointer app(createApplication(argc, argv)); QScopedPointer viewer( QmlApplicationViewer::create()); viewer->setOrientation(QmlApplicationViewer::ScreenOrientationAuto); viewer->setSource(QUrl("qrc:/main.qml")); viewer->showExpanded(); return app->exec(); } There is no other change to be done in the QML files where we use the image files and the font file since the path of the files is a relative one, which will point to the resource internal filesystem. So now we can build the project in Qt Creator that will produce us a binary executable file that bundles all the QML files, images and the font. Let's try to make a build and see how that works! Setting an Application Icon and Title ------------------------------------- A graphical enhancement that is highly recommended is to set an icon for the application, which will uniquely identify your application when deployed in a desktop platform. Inside the noteapp* folder, you may have noticed a few *PNG* files and one *SVG* file by now. These image files will be used to set the icon for the application depending on the icon size since we can have 64x64 or 80x80 icons or a vectorized one. For more details concerning how these icon files are deployed on various platforms, you need to take a close look at the `qmlapplicationviewer.pri` file. You can find find detailed information on application icons in the :qt:`How to Set the Application Icon ` Qt reference documentation. We need to call the :qt:`setWindowIcon() ` function on the `viewer` in order to set the icon for the application window. .. code-block:: cpp // main.cpp ... QScopedPointer app(createApplication(argc, argv)); QScopedPointer viewer( QmlApplicationViewer::create()); viewer->setWindowIcon(QIcon("noteapp80.png")); ... We need a default window-title for our application and we will use the :qt:`setWindowTitle() ` function for this. .. code-block:: cpp // main.cpp ... QScopedPointer app(createApplication(argc, argv)); QScopedPointer viewer( QmlApplicationViewer::create()); viewer->setWindowIcon(QIcon("noteapp80.png")); viewer->setWindowTitle(QString("Keep Your Notes with NoteApp!")); ... The NoteApp* is now ready to be shipped and deployed onto various desktop platforms. Deploying NoteApp ----------------- NoteApp* is a typical Qt application so you need to decide whether you would like to statically or dynamically link against Qt. Additionally, every desktop platform has specific linking configurations to be considered. You can find detailed information on :qt:`Deploying Qt Applications ` reference documentation for each deployment desktop target. .. rubric:: What's Next? A summary of what we have learned in this developer guide.