Meego Wiki
Views

Porting Fremantle Applications to Harmattan

From MeeGo wiki
(Difference between revisions)
Jump to: navigation, search
(Initial version)
(Install the new SDK)
Line 4: Line 4:
== Install the new SDK ==
== Install the new SDK ==
-
The SDK can be downloaded from: TODO: Add link!
+
The SDK can be downloaded from: http://qt.nokia.com/downloads
== Open and run the existing project with the new SDK ==
== Open and run the existing project with the new SDK ==

Revision as of 08:50, 16 July 2011

The following is a rough overview of some steps the author found helpful on migrating an existing Fremantle Application to Harmattan. Feedback, comments, corrections etc. are highly appreciated!


Contents

Install the new SDK

The SDK can be downloaded from: http://qt.nokia.com/downloads

Open and run the existing project with the new SDK

First things first, if the application also runs natively on the OS you are developing, the first thing is to check whether it runs with the newly installed SDK as well.

Build application in Scratchbox and run on the device/QEMU

The next step is to try if the application builds in the Harmattan ARMEL Scratchbox. Chances should be pretty good that it builds out of the box. If the application builds it can be tested on the Device (N950) or in the Emulator (QEMU). Note that at that point the application will look a lot like a common Desktop Qt application.

Add new defines

If necessary add new defines for Harmattan. Unfortunately it seems like there are no defines planned or intended to indicate Harmattan. The following hack by mzanetti helps to work around this issue. In the project file you can use the following to identify Harmattan:

# Thanks to mzanetti for this hack.
exists($$QMAKE_INCDIR_QT"/../qmsystem2/qmkeys.h"): DEFINES += Q_WS_MAEMO_6

Then you can e.g. change your defines from:

#ifdef Q_WS_MAEMO_5

to something like:

#if defined(Q_WS_MAEMO_5) || defined(Q_WS_MAEMO_6)

Redo the UI in QML

If you could already run your application you will have noticed that it had a quite ugly "desktopish" look. To change this the user interface needs to be redone in QML (at least for the time being this seems the only option for now).

Get started with QML

To get a first overview of QML etc. you can simply create a new example QML project using the SDK. In the SDK do

File -> New Project -> Qt Quick Project -> Harmattan Application

This should get you started with a first overview of what a QML project looks like and the parts of it. For more information about QML and the components that can be used see, e.g.:

As a very first step the author just copied the generated QML files, adapted the project file to include the new files and changed the main method of existing application to launch the demo QML application. Note: In the default Harmattan Application example the QML files will be embedded in the binary via resources. While this may be a good start and probably have other benefits (?). Placing these files at some place accessible via the file system will ease and speed up development.

Recreate the basic UI parts in QML

Once QML is running in the application the files copied from the sample project can be changed to the desired look and feel of the application. The following links give some examples and overviews of the bits and pieces that can be used in QML UIs.

Include Custom Widgets in QML

In case the application uses custom widgets, these can be adapted to work in QML as well. To get existing widgets working, using proxies as described in http://doc.qt.nokia.com/4.7-snapshot/declarative-cppextensions-qwidgets.html worked very well (to be honest the author did not try without proxies). The following code shows a quick and dirty declaration of such a proxy for a custom widget "AnalogMeterWidget":

class AnalogMeter : public VolumeMeter
{
   Q_OBJECT
public:
   AnalogMeter(QGraphicsItem* parent = 0)
       : QGraphicsProxyWidget(parent)
   {
       widget = new AnalogMeterWidget(0);
       setWidget(widget);
   }
private:
   AnalogMeterWidget *widget;
};

Also note that it seemed to be more practicable to register the proxies directly in the main method via something like

qmlRegisterType<AnalogMeter>("vumeter", 1, 0, "AnalogMeter");

instead of using a custom QML plugin as described in the link above. In the QML files you would then use

import vumeter 1.0

to import your stuff and something like

AnalogMeter {
  id: vuMeter
}

to instantiate your class. Note: Using the approach as described here, the QML editor will complain about "unknown types" when you use your custom imports and widgets but this did not affect the functionality here. See also the next section for more information about connecting QML and C/C++ code.

Adapters, Proxies, Wrappers for existing C/C++ Code

Similarly as described above, using "qmlRegisterType" lets you use your own Qt classes in QML. This way it is easily possible to include many of the functionality of your "old" project in QML. Usefull links are:

Remove Obsolete Stuff

Some of the existing parts of a Fremantle project are not needed for Harmattan (e.g. forms etc.). Those things do not need to be deleted but can be excluded for Harmattan build by changing the project file accordingly, e.g.:

exists($$QMAKE_INCDIR_QT"/../qmsystem2/qmkeys.h"){
   DEFINES += Q_WS_MAEMO_6
   QT+= declarative
  1. As we use QML anyways we do not need any forms.
   FORMS =
}

Defines Q_WS_MAEMO_6, adds the declarative parts needed for QML etc. and removes all forms for Harmattan builds. This is just an example. Similarly the install targets and files can be changed as well. This way it should still be possible to build the project for all targeted platforms such as Fremantle or Harmattan.

Store QML in Filesystem instead of Resources

One nice feature of QML is that it it interpreted at runtime so changes in the QML part do not require a recompile. We can exploit this feature to speed up the development process by not embedding the QML files in the binary but store these files somewhere else where we can easily edit them. In the project file use, e.g.:

OTHER_FILES += qml/main.qml \
  qml/MainPage.qml
INSTALLS += target ... qml
target.path = /usr/bin
...
qml.path = /usr/share/vumeter/qml
qml.files += qml/main.qml \
       qml/MainPage.qml

In the main method you can then use

view.setSource(QUrl("/usr/share/vumeter/qml/main.qml"));

instead of

view.setSource(QUrl("qrc:/qml/main.qml"));

to load the QML files.

Change Paths for Desktop Files etc.

The desktop files for Harmattan are located in

desktop.path = /usr/share/applications/meegotouch

instead of

desktop.path = /usr/share/applications/hildon

Packaging for Harmattan

TODO


Uploading to OBS

TODO

Personal tools