Archives For Mobile Development

Please read at first my blog HowTo install Qt 5.9.

Here are some issues and workarounds I found out while testing my apps under 5.9

 

Update QML Imports

This is always the first step after moving a project from 5.8 to 5.9: I’m updating the QML Imports.

From a technical point you can use the ‘old’ imports. I’m always doing search/replace to update the imports. Then I’m sure all my QML files are accessing the newest Controls and Properties. Updating from  5.8 to 5.9 I replaced

import QtQuick 2.8
import QtQuick.Controls 2.1
import QtQuick.Controls.Material 2.1

with

import QtQuick 2.9
import QtQuick.Controls 2.2
import QtQuick.Controls.Material 2.2

You can see the newest imports here.

Using a source control system like Git it’s a good idea to do this in an extra Branch – then it’s easier to go back if something went wrong.

 

Drawer ignores taps outside the Drawer

Normaly if you opened a Drawer you can tap outside the Drawer to close. This works well up to 5.8.

Under 5.9 there’s a bug:

tapping outside the Drawer not always closes the Drawer.

This would be no big problem because you can drag the Drawer back or click inside the Drawer.

Unfortunately the Drawer ignores the Tap to close but the underlying (dimmed) Page gets touch events so users can by accident do something unwanted.

I opened QTBUG-61581.

I found a workaround to block those unwanted touch events on the Pages below the Drawer by inserting another Popup between Drawer und Pages below. looks ugly but it works in the meantime. The bug is classified as P1 so hopefully will be fixed soon.

Drawer {
    id: myDrawer
    z: 1
    ....
    // workaround:
    onOpened: {
        fakePopup.open()
    }
    onAboutToHide: {
        fakePopup.close()
    }
    Popup {
        id: fakePopup
        z: 0
        width: appWindow.width
        height: appWindow.height
    }
    // end workaround

 

Bug is only on Android and iOS – tested from macOS: MouseClick is working.

MonthGrid onClicked gets no events

I’m using MonthGrid as part of my DatePicker.

Works well up to 5.8 but now under 5.9 I’m getting no clicked events.

I opened QTBUG-61585. and also found an easy workaround: I added a MouseArea:

ApplicationWindow {
    visible: true
    width: 640
    height: 480
    title: qsTr("Hello World")
    id: appWindow

    Page {
        id: myPage

        GridLayout {
            columns: 3
            rows: 5
            width: appWindow.width
            height: appWindow.height

            MonthGrid {
                id: monthGrid
                Layout.fillHeight: true
                Layout.fillWidth: true

                onClicked: {
                    console.log("tapped on a date ")
                }

                delegate: Label {
                    id: dayLabel
                    text: model.day
                    font.bold: model.today? true: false
                    opacity: model.month === monthGrid.month ? 1 : 0
                    color: pressed ? Material.foreground : model.today ? Material.accent : Material.foreground
                    minimumPointSize: 8
                    fontSizeMode: Text.Fit
                    horizontalAlignment: Text.AlignHCenter
                    verticalAlignment: Text.AlignVCenter

                    background: Rectangle {
                        anchors.centerIn: parent
                        width: Math.min(parent.width, parent.height) * 1.2
                        height: width
                        radius: width / 2
                        color: Material.primary
                        visible: pressed
                    }
//                    MouseArea {
//                        anchors.fill: parent
//                        onClicked: {
//                            console.log("mouse area click")
//                        }
//                    } // mouse
                } // label in month grid

            } // month grid
        } // grid layout
    } // myPage
} // app window

Bug is only on Android and iOS – tested from macOS: MouseClick is working.

iOS Release Build: getting thousands of Warnings

While testing my APPs under 5.9 I noticed a strange behavior while doing a RELEASE build for iOS.

I’m getting many Warnings:

With some help from Jake Petroules I found a workaround:

ios {
...
 disable_warning.name = GCC_WARN_64_TO_32_BIT_CONVERSION
 disable_warning.value = NO
 QMAKE_MAC_XCODE_SETTINGS += disable_warning
...
}

I opened QTBUG-61587.

iOS: isOnline() not reliable from QNCM

Under Android it’s easy to know if the device is online: QNetworkConfigurationManager is your friend:

    mNetworkConfigManager = new QNetworkConfigurationManager(this);
    qDebug() << "INIT IS   O N L I N E ?" << mNetworkConfigManager->isOnline();

Up to iOS 10.2.1 with a little trick QNCM also could be used by observing active configurations and filter out a config with name “utun0”.

Now with iOS 10.3.2 I had devices also reporting an active configuration ‘en2’ even if iPhone was in airplane mode.

It’s better to rely on Apple’s Reachability Class.

see also QTBUG-56151 and this great article about “CheckingNetwork Status in iOS

here’s my workaround by including Reachability:

Download sources from attachment to bugreport.

Copy Reachability classes to <project>/ios/src

Change your .pro:

LIBS += -framework SystemConfiguration
....
ios {
 OBJECTIVE_SOURCES += ios/src/Reachability.mm \
 ios/src/ReachabilityListener.mm
...
}

add this include

#if defined (Q_OS_IOS)
#include "ios/src/ReachabilityListener.h"
#endif

change class definition:

class YourClass : public QObject
#if defined (Q_OS_IOS)
 , private utility::ReachabilityDelegate
#endif

add a statusChanged method:

#if defined (Q_OS_IOS)
void DataServer::statusChanged(utility::NetworkStatus newStatus)
{
 if (newStatus == utility::NotReachable) {
 // offline
 } else {
 // online
 }
}
#endif

Now you’re getting events if online state is changing on iOS devices.

At startup you can check the current state:

qDebug() << "I O S REACHABILITY: INIT IS O N L I N E ?" << status() != utility::NotReachable;

if you need some more informations you can check for different states:

#if defined (Q_OS_IOS)
    switch (status()) {
    case utility::NotReachable:
        networkInfo.append(tr("Internet not reachable"));
        break;
    case utility::ReachableViaWiFi:
        networkInfo.append(tr("WiFi internet connection"));
        break;
    case utility::ReachableViaWWAN:
        networkInfo.append(tr("mobile data internet connection"));
        break;
    default:
        break;
    }
#endif

This was the first time ever I’m using a ObjectiveC class 😉

I got warnings from Reachability.mm about unused parameters.

you can suppress these warnings by adding #pragma unused(theName)

static void PrintReachabilityFlags(SCNetworkReachabilityFlags flags, const char* comment)
{
#pragma unused(flags)
#pragma unused(comment)
#if kShouldPrintReachabilityFlags

Have tested Reachability under different situations at customer site and it’s working great.


Updating from 5.8 to 5.9 was easier and has less issues as my last update from 5.7 to 5.8

I’ll tweet @ekkescorner if finding more issues while working on my apps. Also I have to check all the issues I reported from 5.8 which ones are solved and which are still open.


← Back (Install Qt 5.9)

→ Next Article (Qt Creator Intro)

⇐ Home (Overview / Topics)


Install Qt 5.9

June 23, 2017 — 1 Comment

Qt 5.9 Release Blog from Qt

Qt Quick Controls 2 Blog from Qt

This blog series is about the new Qt Quick Controls 2 to develop mobile apps for Android and iOS.

Before going on you should have read my blog – esp. on ‘Prepare for Android / iOS‘ and ‘Prepare Devices

Besides Qt 5.9 you’ll also get a new Qt Creator 4.3

Perhaps you already have an older version of Qt already installed, you can use the Maintenance Tool to update. I’m always doing a fresh install for each Beta, RC or Release.

Before downloading and installing you should know if you want to install the Open Source or Commercial version of Qt for Application Development.

Please take a look at Qt FAQ‘s and also my blog post about licensing and the new license for small Startups and Independent Developers.

I’m using the Commercial version for Startups – see Qt’s offer here: https://www.qt.io/start-up-plan/

Read more about Open Source vs Commercial also in my blog about ‘Install Qt 5.6


Here are my steps to download and install Qt 5.9 (commercial):

Install Qt 5.9

Go to your Qt Account – Downloads and select the Qt Online Installer:

01_download_01

 

See available downloads:

 

I selected the macOS online installer:

 

Here’s my download on OSX:

 

Double click to install:

 

Log into your Account:

 

Select the folder where to install:

 

It’s a good idea to use installation pathes without spaces. see also here.

As next select your components:

accept the license:

 

 

and wait for the installer:

 

If Installer finished, I’m not launching Qt Creator yet.

 

 

Start Qt Creator with -settingsPath

All Qt Creator instances by default share the settings. Having the new Qt Creator 4.3 and old 4.2.1, 4.0.2, 3.6.2 using the same settings is no good idea. Also I want to use different working directories for my Qt 5.6, 5.7, 5.8 and the new Qt 5.9 Release.

You can start Qt Creator with parameter -settingsPath – here’s HowTo do this from OSX:

Search for the Qt Creator.app from Qt 5.9 and do a right-click on the app. Here’s the content:

 

rename Qt Creator to something like Qt Creator-bin:

 

From a Text Editor create a Script to execute the Qt Creator-bin with a parameter.

something like this:

#!/bin/sh
exec "/daten/_qt_sdks/sdk_590/Qt Creator.app/Contents/MacOS/Qt Creator-bin" -settingspath /daten/_qt_sdks/sdk_590/qtc_settings "$@"

Save this file named “Qt Creator” besides the Qt Creator-bin:

 

Now you can start Qt Creator, which will execute the script:

 

Qt Creator will create the QtProject folder to store all the configuration settings.

Now you can start multiple Qt Creator versions without any collision.

Qt Creator 4.3

At first I’m changing QtCreator’s language on my german MacBookPro to english and restart

 

 

Qt Creator Preferences Working Directory

Set your working directory for 5.9, if you are using different directories as I’m doing:

 

Qt Creator Preferences Android

Take a look at your Devcies -> Android preferences:

 

Select your SDK and NDK locations and check ‘Gradle’:

 

Important: Don’t use a newer NDK ! Please always use r10e because of some trouble with the newer ones.

 

Qt Creator External Tools

Translations

I’m developing business apps and business apps always need support of languages (i18n). Configuring the External Tools for Linguist (Qt’s Tool to translate text from your QML and C++ sources) will make it more comfortable.

As first step we’ll add the Linguist App.You’ll find the Linguist at 5.8 –> clang_64 –> bin:

 

I like to use Tools in english, but the language cannot be changed yet for Linguist, so the trick is to rename the translations file, which in my case is 5.9 –> clang_64 –> translations –> linguist_de.qm:

 

Under Preferences –> Environment –> External Tools there already exist access to commands for lupdate and lrelease. (lupdate is looking for the strings you marked as translatable and to create or update the translation files <app>.ts. Using Linguist or external tools you can then translate the strings. lrelease compiles these translations from *.ts into *.qm. Only *.qml files will be deployed to your device)

I found out that the default configuration doesn’t work on Android and iOS – so I’m using the executable from …/5.9/clang_64/bin:

 

 

Test if Linguist will start. From External Tools

06_qtc_ext_tools_06

Linguist should start:

 

it’s a good idea to use a shortcut:

Refresh .pro

Adding new QML files to a project doesn’t refresh the project view automatically. Open the .pro change something, close .pro updates project folders.

I wanted to do this by a shortcut. The trick is to execute a script to “touch” the .pro file.

for OSX the script looks like this:

#!/bin/sh

# *****************
# External Tool for QT Creator.
# Touches the projects PRO file to trigger an IDE refresh after adding new files
# *****************

echo ""
echo "*** Touches the projects PRO file to trigger an IDE refresh after adding new files ***"
echo ""

proFilePath=$1

if [ -f "$proFilePath" ]
then
	now=$(date "+%Y%m%d%H%M")
	echo "Touching file on path: '$proFilePath' now... Setting the current time to '$now'"
	touch -mt $now $proFilePath
	echo "FINISHED!"
else
	echo "ERROR File under give path '$proFilePath' not found!!!"
fi

 

and here’s the shortcut:

Run Android for Work APPs

Some of my mobile business apps are installed on customers mobile management systems (BlackBerry UEM 12.6 or so) and deployed as ‘AndroidForWork’ APPs. see also my blog here. Unfortunately Qt Creator doesn’t support setting the user id, so after debug/run on device I have to stop the deployed App using the default user and start the same app for another (AndroidForWork) user.

I created external commands for those projects and execute from External tools.

Here’s an example script on OSX:

#!/bin/sh

# *****************
# External Tool for QT Creator.
# Runs the APP as work APP
# *****************

cd /daten/_android/android-sdk-macosx/platform-tools
./adb shell pm clear --user 0 org.ekkescorner.enbw.pegelmeter.dev
# doesn't close the app ./adb shell am force-stop --user 0 org.ekkescorner.enbw.pegelmeter.dev
./adb shell am start --user 10 -n org.ekkescorner.enbw.pegelmeter.dev/org.qtproject.qt5.android.bindings.QtActivity

and here’s the external tool i created:

Manage Qt Creator Plugins

Qt Creator has many Plugins installed as default.

It’s a good idea to disable Plugins you’re not using.

per ex. I manage all my Git repos using GitTower and I don’t want always to be asked about my source repo:

Open the list of Qt Creator Plugins:

then uncheck all unwanted Version Controls:

you can do the same with the unused Devices:

Restart Qt Creator.

Create a new QtQuickControls2 Project

Now verify if all is correct configured. easiest way is to create a new QtQuickControls2 APP and let it run on your devices.

From Welcome Tab click on “New Project” and select Application –> QtQuickControls2 Application:

give it a name and create in your workspace:

Select the build system: qmake

Select the QQC2 style. I’m using the Material style. This will create a config file. (There are other ways to set styles and colors)

Select the Kits you need. I’m developing mobile apps for Android and iOS and always testing on real devices.

Also for testing without deploying on devices I always add the Desktop Kit.

Qt 5.9 brings a cool new feature for iOS.

You can select the Development Team directly from Project Settings for iOS:

Now try the different Kits. Select the Kit, the Debug Build and hit “Run”:

Running on a connected Android Device the devices should be listed:

same is for iOS: you should see your connected devices:

I not only updated from Qt 5.8 to Qt 5.9, but also OSX 10.11.6 to macOS 10.12.5, Xcode from 8.2 to 8.3.3, iOS from 10.2.1 to 10.3.2 and my first try to run on an iOS device brings this error:

You can easy fix this. Go to Xcode 8.3.3, right-click to see the content:

duplicate the 10.3.1 folder and rename to 10.3 or create a symbolic link.

see more details at QTCREATORBUG-18380

 

Gallery Qt Quick Controls 2

Best way to get a first impression of all the new QtQuick Controls 2 is to run the Quick Controls 2 Gallery App.

From Overview – Examples search for “Gallery” and select the right one:

 

 

 

… and run the Gallery App:

 

Congrats –  you have installed Qt 5.9.  Now you can try out all the new Controls.

If you already have projects using Qt 5.8 – take a look what’s good to know if moving projects from 5.8 to 5.9

New to Qt for mobile ? Here are some more appetizers:

Clone my Examples from Github and Run

  1. First app with One Page
  2. StackView
  3. SwipeView
  4. TabBar
  5. Bottom Navigation
  6. Drawer Navigation

Please follow my blog series: https://appbus.wordpress.com/category/qt-for-mobile/overview/


← Back (Qt Community (Wiki, Forum, Lists))

→ Next Article (Issues and Workarounds: 5.8–> 5.9)

⇐ Home (Overview / Topics)

Qt 5.8 brings some more support of Text Selection Handles, but there are still also some problems. Text Selection Handles are important to make it easy on touch devices to insert text, copy text, replace text or cut text. With 5.7 single taps to get a handle to move the insert position around already works.

Select words by double tap

Qt 5.8 also supports double tap to select words – but it doesn’t work as expected. This selection mode will only be enabled if you set

selectByMouse: true

on TextField or TextArea. This works fine with TextFields, but having TextArea inside Flickable makes scrolling difficult or impossible. Qt doesn’t know if you want to change the selection or scroll inside the TextField or scroll the Page. Users will be confused and it’s not easy to know where outside the Textfield scrolling works. Hopefully in Qt 5.9 this will befixed and double tap works without setting ‘selectByMouse’.

One of my app contains many TextAreas and users are waiting for word-selection-mode, so I developed some workarounds for 5.8.

To make it easier to distinguish where’s the TextArea I placed the TextArea on top of a Pane. Now you can tell your user to scroll the Page place fingers outside the TextArea:

As soon as TextArea gets active focus, 3 buttons will appear on the right side:

  • clear
  • toggle selection mode
  • done

As soon as the user does a double-tap on a word both text selection handlers become visible and it’s easy to move them around to select more or less.

Also please notice on top a menu to select all, cut, copy and paste.

On iOS this is different: at first do the double tap to select a word – then please do a long press on the selection to get a cut, copy, paste, delete menu just on top of the selection:

Single tap does work with or without setting ‘selectByMouse’:

To insert from clipboard do a long-press: ‘insert’ menu appears on top of cursor position.

Tap on the Toggle Button to set selectByMouse = false to make it easier to scroll also while inside the Textfield.

When you’re ready with text editing tap on the ‘Done’ Button. Done Button gets focus and all Handles disappear. Also Done and Toggle Button disappear.

As long as there’s some text, the clear Button makes it easy to clear the field:

Here’s the workaround. I placed all of this into ‘TextAreaRow.qml’ – then it will be easy to change when 5.9 comes out.

TextAreaRow{
    id: remarksTextRow
    placeholderText: qsTr("Your Remarks (RETURN for new line)")
    text: tourDetail.remark
    onTextChanged: {
        tourDetail.remark = text
    }
    onDone: {
        // do something: set active focus to another field or so
    }
} // remarksTextRow

And here’s the implementation:

RowLayout {
    id: theTextRow
    signal done()
    property alias text: theTextField.text
    property alias placeholderText: theTextField.placeholderText
    property alias textField: theTextField
    property int minHeightTextPane: 140
    property bool doubleTapIsDefault: true
    Pane {
        id: textPane
        anchors.top: parent.top
        Material.elevation: 6
        Layout.fillWidth: true
        Layout.minimumHeight: theTextField.activeFocus? minHeightTextPane : 60
        TextArea {
            id: theTextField
            // Qt 5.8
            // only if set to true we can mark words by double tap
            selectByMouse: doubleTapIsDefault
            // important - otherwise text goes endless without wrapping
            width: parent.width
            text: ""
            wrapMode: TextArea.WordWrap
        } // theTextField
    } // text pane
    Column {
        spacing: 0
        anchors.top: textPane.top
        Layout.minimumWidth: textClearButton.visible || textSelectToggleButton.visible || textDoneButton.visible? 48 : 0
        ButtonIconActive {
            id: textClearButton
            anchors.horizontalCenter: parent.horizontalCenter
            visible: theTextField.activeFocus || theTextField.text.length
            focusPolicy: Qt.ClickFocus
            imageName: "clear.png"
            onClicked: {
                theTextField.text = ""
            }
        } // textClearButton
        ButtonIconActive {
            id: textSelectToggleButton
            anchors.horizontalCenter: parent.horizontalCenter
            visible: theTextField.activeFocus
            focusPolicy: Qt.ClickFocus
            imageName: "code.png"
            onClicked: {
                theTextField.selectByMouse = !theTextField.selectByMouse
                if(theTextField.selectByMouse) {
                    appWindow.showToast(qsTr("Word Selection by Double Tap switched ON"))
                } else {
                    appWindow.showToast(qsTr("Word Selection by Double Tap switched OFF"))
                }
            }
        } // textSelectButton
        ButtonIconActive {
            id: textDoneButton
            anchors.horizontalCenter: parent.horizontalCenter
            visible: theTextField.activeFocus
            focusPolicy: Qt.ClickFocus
            imageName: "done.png"
            onClicked: {
                // we only need the focus
                // emit signal so users can give another field the activeFocus
                theTextRow.done()
            }
        } // textDoneButton
    }
} // row w text area

ButtonIconActive is a customized Button showing Icon. You’ll find all of this in my sample apps at Github – I also have updated QtWorldSummit Conference App.

On Android there are two bugs:

Selection handles overlap while scrolling (Android only)

The selection handle(s) can overlap the keyboard or selection menu:

Take a look at BUG 58700

Selection Handle visible when Component invisible

If the Component containing your TextField or TextArea becomes invisible and the TextField still has active focus, the handles will still be visible.

See BUG 58700

Workaround is easy: set focus to another field as soon as TextField becomes invisible.


← Back (Update 5.7 to 5.8)

→ Next Article (Qt Creator – Intro)

⇐ Home (Overview / Topics)


Before debugging and running a work APP on your managed Android device from Qt Creator

  • your device must be activated as Android for Work device
  • your must have sent a release build to your Admin and this APP must be published to Google Play for Work
  • you must have installed the work APP on your managed device

Deploy to Device

Build and deploy your APP as usual from Qt Creator to your (managed) Android device.

If all works well, the APP (named PegelMeter) will appear twice on your device.

This is expected behavior – read more here – topic “Testing on managed profiles – tips and tricks“.

Run the work APP

Unfortunately you’ll notice that Qt Creator runs the private version of the APP and not the work version.

This is because Qt Creator doesn’t know that we want to run a work app. Private and Work apps are bound to the user.

Work User vs Private User (managed Android Device)

Default user is user 0, where the work user normally is user 10. You can list your users from Terminal:

adb shell pm list users

you’ll get something like this:

Users:
    UserInfo{0:1799924875:13} running
    UserInfo{10:141078676:30} running

User 0 –> default (private) user

User 10 –> work user

Run as Work App

You can run the APP from Terminal as Work APP:

adb shell am start --user 10 -n org.ekkescorner.xxx.pegelmeter.dev/org.qtproject.qt5.android.bindings.QtActivity

QtCreator starts the APP without –user which always will use the default one (0)

I’ll open a bug report and request to add a Variable USER_ID so this can be placed inside .pro and added to adb start command by Qt build process.

Starting the work APP from Terminal you’re loosing the log output inside QT Creator. Workaround could be to log from adb or to use an extra tool.

This will give you the logs using adb:

adb -d logcat libpegelMeter_x.so:D *:S

A special tool gives you some more comfort filtering the logs. For OSX I can recommend LogRabbit. It’s easy to filter out the logs from your APP.

External Tool

As we have seen, Build and Run the APP starts the private APP.  So you have to stop and close the private APP and then start the work APP from Terminal.

To make this easier I added this to External Tools in Qt Creator:

I checked Output: Show in Pane – but nothing is printed. Probably I forgot something to tell External Tools that APP output should be visible in Application Output Pane. As long as this doesn’t work I’m using LogRabbit (see above)

External Tools ‘start_pegelmeter_work.sh’ executes this script:

#!/bin/sh
cd <path-to->/platform-tools
./adb shell pm clear --user 0 org.ekkescorner.xxx.pegelmeter.dev
./adb shell am start --user 10 -n org.ekkescorner.xxx.pegelmeter.dev/org.qtproject.qt5.android.bindings.QtActivity

Now it’s easier:

  • Build and Run APP
  • ExternalTools – Kill running private APP and Start Work APP

I would like to use a variable for User Id and also for APP Name and APP Package. (see QTCREATORBUG-17863)

and here’s the request to add USER_ID to be placed inside .pro: QTCREATORBUG-17862


← Back (Deploy Android Work App to Google Play)

→ Next Article (…work in progress…)

⇐ Home (Overview / Topics)


Publish to Google Play Store for Work

Your BlackBerry UEM Admin must publish your APP to Google Play Store for Work.

The APP must not be uploaded to Google Play but will be registered.

The workflow is similar to publishing a ‘normal’ APP to Google Play, so you need screenshots, artwork, description, …

Here’s a guide what the Admin has to do:

This guide is from 2016 – but the workflow still is the same. All described for BES12 will work using UEM 12.6

As soon as Google has approved the APP the Admin can configure on which devices / users / user-groups the APP should be installed.

Developer Policies

The Admin typically will create Policy profiles matching the rights a user-group should have for work APPs.

Attention: To be able to deploy debug builds from QtCreator to your device the Admin must add these extra policies to developers:

  • Apps
    • Allow installation of non Google Play apps
    • Allow developer options

If you cannot deploy and run work apps from QtCreator ask your Admin if these policies are set for your device.


← Back (Activate Android Device for Work)

→ Next Article (Debug and Run managed Qt Android App | QtCreator)

⇐ Home (Overview / Topics)


There are different ways to activate a Device:

  • Managed Accounts
  • Google Domains

My example and sceenshots are based on ‘Managed Accounts’, which is the easiest way. If you’re using Google Domains then it’s much more complex and for each User you need a dedicated Work Google Play Account. The newest BlackBerry UEM 12.6 supports ‘Managed Accounts’.

To activate a Android device for work (‘Managed Account’), you’ll receive an eMail from the Admin (email address, password)

BlackBerry UEM Client

Please download the BlackBerry UEM Client APP from Google Play

Open the UEM Client and enter email address and password.

Configure your profile.

Device will be activated:

Play Store for Work

Automatically some work apps will be added. Here you see the Play Store for Work (left) and the usual private Play Store:

Please open the Play Store for Work. If you don’t have used a Google Mail address (different from your personal Goofle Mail address) for activation, it can happen that you get an error:

try to switch off / on the airplane-mode or restart the device to see your work apps.

Your Work APPs

in this case there’s one app available – the app you sent to the admin:

Two APPs (Work, Private)

Install the APP as usual and you’ll get 2 APPs: one as private, one as work app:

we only need this app as work APP, so you can delete the private one.

Now as your APP exists as a work APP you can deploy updates from Qt Creator and use the work profile.

Android for Work Statusbar

Open your work APP and take a look at Android statusbar:

you’ll always see if the current APP is a work app and you’ll also see if currently there’s a secure connection to server (VPN)

Secure Connection

All your Work APPs will use the secure connection. There’s also a second Browser: Chrome for Work. Opening sites from Chrome for Work or accessing URLs from your Work APP always goes thru the secure connection – this means those URLs will be opened behind the firewall same way as if you’re sitting in your office using the Intranet. Data used by Work APPs is encrypted and secure out of the box on transport and also on your device.

Secure Boot

Using BlackBerry Android Devices there’s some extra security built into the hardware. Those devices cannot be rooted.

Read more here and here.

BlackBerry and Android Devices ? You have read that there will be no more Devices built by BlackBerry ?

Yes – BlackBerry finished transition from hardware to software. BlackBerry licensed Devices to partners, but verifies security. First new device was presented by TCL at Mobile World Congress in Barcelona: keyONE with Android Nougat 7.1 – three more new devices will follow. BlackBerry Android Devices always get the monthly security updates for Android – per ex. Security Patches from march 2017.

It’s up to you or your customers how many levels of security they need. Android for Work is the first step, using devices with secure boot the next one.

Samsung does something similar with Samsung KNOX and Samsung devices, but fails with monthly security updates.


← Back (Overview managed Android Devices)

→ Next Article (Deploy Android Work App to Google Play)

⇐ Home (Overview / Topics)


If you’re developing mobile business apps sooner or later customers will request to debug, build and run on managed devices. This blog post is focused on Google for Work | Android (aka Android for Work).

Google for Work | Android

There are different ways to run work applications: devices may only contain work apps or private and work apps are installed together. From my experiences in most cases there are private and work apps together on devices. Read more about EMM (Enterprise Mobile Management) and different scenarios here.

There are some EMM solution providers:

  • BlackBerry
  • Mobileiron
  • VMware AirWatch

BlackBerry UEM 12.6

My examples are based on BlackBerry UEM 12.6 (formely known as BES 12)

You can try out UEM for 30 days (Cloud version) or 60 days (on-premises) for free.

Using a managed device is like working behind the firewall via VPN, but all is transparently managed by the EMM solution provider.

EMM Admin manages users, user groups, devices, policies and apps. Here you can download the policies for BlackBerry UEM. Get an overview of BlackBerry UEM here.

Development Stages (Dev, Test, Production)

Developing a new app there are typically 3 stages:

  1. develop UI with MockUp data (no access to servers needed)
  2. test against test environment
  3. release for production environment

Stage 1 I’m using GooglePlay Closed Beta Test to deploy the apps to beta testers from customer. Adding testers only gMail address is needed.

For stages 2 and 3 your device must be activated as Android for Work device or you should request a device to test on from your customer. This is the only way to get access to data servers behind the firewall – in most cases there will be no URL you can use from outside. One device can only be activated as work device for one server (BlackBerry UEM).

It’s highly recommended to test your APP as Work APP – the admin can forbid features (Bluetooth, NFC, Camera, …)

To manage apps your customer has to use a Google developer account to be able to publish apps through Google Play for Work.

Multi Android Package Names in Manifest

Attention: you must change the Android package name to enable your customer publishing the app to Google Play for work because the package name from stage 1 is already connected to your own Google developer account from Beta testing.

Also your Enterprise Customers can have different environemts for dev, test, production with different Google Developer Accounts to get a specific Play Store for Work for each environment. This means you must build releases for up to three or more different package names. Changing the package name manually in Android Manifest is not so comfortable. You can have a dynamic way following this blog article.

Best would be Qt Creator supports this directly using variables in .pro. see QTCREATORBUG-17863

Develop – Test – Release Workflow for Work APPs

Here’s an example workflow:

  • add your APP to Google Play Closed Beta Test (Android package name: my.example.beta)
  • deploy updates to beta testers until stage 1 finished
  • build release (Android package name: my.example.test) and send APK to your customer
  • your customer publishes APP to GooglePlay for Work
  • your customer creates user and profile for you and adds the APP to your user or user group
  • your customer sends an email to activate a device
  • you activate your device and install the APP from Google Play for Work on your device
  • now you can develop, build and run your APP from Qt Creator
  • build update releases and send to your customer
  • your customer publishes update to Google Play for Work so others can test your update

Hint: you can only build and run your app as work app if customer has published your app once to Google Play for Work and you installed it once !

Following pages will explain the steps in more detail:


← Back (EclipseCON Europe)

→ Next Article (Activate Android Device for Work)

⇐ Home (Overview / Topics)