Getting Started

If you have any questions that are beyond the scope of this help file, Please feel free to email via Discussion Page.

How To Integrate

In your main project CMakeLists.txt enable the library tools you need and include the library project as well:

set(QTAT_APP_PERMISSIONS ON)
set(QTAT_APK_INFO ON)
set(QTAT_SCREEN ON)
set(QTAT_SYSTEM ON)
set(QTAT_BATTERY_STATE ON)
set(QTAT_SIGNAL_STRENGTH ON)
set(QTAT_IMAGES ON)
set(QTAT_NOTIFICATION ON)
set(QTAT_ADMOB_BANNER ON)
set(QTAT_ADMOB_INTERSTITIAL ON)
set(QTAT_ADMOB_REWARDED_AD ON)
set(QTAT_PLAY_STORE ON)
set(QTAT_GOOGLE_ACCOUNT ON)
set(QTAT_GOOGLE_DRIVE ON)
set(QTAT_SHARING ON)
set(QTAT_USER_MESSAGING_PLATFORM ON)
set(QTAT_AUDIO ON)
set(QT_ANDROID_PACKAGE_SOURCE_DIR "${CMAKE_CURRENT_SOURCE_DIR}/android")
include_directories(${CMAKE_CURRENT_SOURCE_DIR}/../QtAndroidTools)
add_subdirectory(${CMAKE_CURRENT_SOURCE_DIR}/../QtAndroidTools build)
target_link_libraries(QtAndroidToolsDemo PRIVATE QtAndroidTools)

Tools

AppPermissions

This tool allow to request Android app permissions in an easier way.

From Android version 23 (Marshmallow) there are a list of special permission called "dangerous" because are directly connected to personal data of the user like calendar, contacts list and so on (official documentation here). If your app is target for this version and above and your manifest file contains one of the dangerous permissions you have to explicitly get the user authorization for have such permission granted. In the demo app four of these dangerous permission will be requested as follow:

There are two functions for request permissions, one accept a list of permissions for allow a unique request for all and another can be used to ask for a single permission only. In this example the multiple request function will be used as follow:

import QtAndroidTools
...
readonly property var permissionsNameList: ["android.permission.WRITE_EXTERNAL_STORAGE","android.permission.READ_CALENDAR","android.permission.READ_PHONE_STATE","android.permission.READ_CONTACTS"]
...
QtAndroidAppPermissions {
    id: permission
}

permission.requestPermissions(permissionsNameList)

The call of this function will have a result to show the system message informing the user the app require the specific permissions and ask for approval:

Once the user will finish to make the choice a signal will be generated with a list of struct as param as follow:

QtAndroidAppPermissions {
    id: permission
    onRequestPermissionsResults: function(results)
    {
        for(var i = 0; i < results.length; i++)
        {
            if(results[i].granted === true)
            {
                setPermissionGranted(results[i].name, true);
            }
            else
            {
                if(permission.shouldShowRequestPermissionInfo(results[i].name) === true)
                {
                    if(results[i].name === permissionsNameList[0])
                        requestPermissionWRITE_EXTERNAL_STORAGE.open();
                    else if(results[i].name === permissionsNameList[1])
                        requestPermissionREAD_CALENDAR.open();
                    else if(results[i].name === permissionsNameList[2])
                        requestPermissionREAD_PHONE_STATE.open();
                    else if(results[i].name === permissionsNameList[3])
                        requestPermissionREAD_CONTACTS.open();
                }
                else
                {
                    setPermissionGranted(results[i].name, false);
                }
            }
        }
    }
}

Each item in the list contain the param name containing the permission string name and the boolean field granted informing if the user allowed the app to get the permission or not. Please note, if you app will be target under version 23 this signal will be emitted immediately without show any messagebox and, obviously, with all the permission automatically granted. This for allow the code working in the same way independently by the Android target version selected. In case the user don't granted a permission this special call is used in the code:

permission.shouldShowRequestPermissionInfo(...)

This function is quite particular and return true only in the case a first attempt to ask to permission has been denied. Basically it "suggest" to show a message to the user explaining why your app need the specific permission before retry to ask for permission again:

Once explained the reasons you can ask again for the same permission by using this time the single request function:

permission.requestPermission(...)

Now please note a very important particular. Theoretically you can ask for the same permission infinitely, however from the second time you ask for the same permission the system message window will appear as following:

As you can note in this case there is a checkbox allowing the user to not be annoyed by your request anymore (Don't ask again). If the user will check it and will deny the request again any next request for the permission will be automatically denied without show any message than be careful in decide when ask for permission and, above all, to explain very clearly why you need that permission. After the second try the signal reporting the choice result will be generated again with the updated situation:


AdMobBanner

This tool allows to show AdMob banner inside QML app.

Official documentation about AdMob banner is here, please read before continue for understand the options exported by the tool. Remember for allow banner to be loaded your app need the following permissions:

android.permission.INTERNET
android.permission.ACCESS_NETWORK_STATE
android.permission.WRITE_EXTERNAL_STORAGE

In add of this you have to install the AdMob required packages through Android SDK Manager. The packages you have to install are the following:

  • Google Repository
  • Google Play services
  • Support Repository

Than you have to add the following dependencies into your app gradle file:

dependencies {
    ....
    implementation 'com.google.android.gms:play-services-ads:21.+'
}

and the application id inside the manifest file (this in the example is the demo id):

<meta-data android:name="com.google.android.gms.ads.APPLICATION_ID" android:value="ca-app-pub-3940256099942544~3347511713"/>
<meta-data android:name="com.google.android.gms.ads.AD_MANAGER_APP" android:value="true"/>

Banner is showed inside the following QML item:

import QtAndroidTools

QtAndroidAdMobBanner {
    id: banner
    unitId: "admob-banner-unit-id"
    type: QtAndroidAdMobBanner.TYPE_BANNER
    keywords: ["keyword_1", "keyword_2", "keyword_3"]
    nonPersonalizedAds: false
}

The unitId is the string generated when you create a new ad unit inside the AdMob site. It's used to identify the ad connected to your app. Using this id you can know how much you earn from this ad unit. The keywords property is an optional list of keywords needed for better targeting the banner ad. The nonPersonalizedAds property is optional (default is false). Set this property to true impose to AdMob to don't use collected user personal data for ads targeting. The property type is the banner type you want to show. Possible values are:

TYPE_BANNER
TYPE_FULL_BANNER
TYPE_LARGE_BANNER
TYPE_MEDIUM_RECTANGLE
TYPE_SMART_BANNER
TYPE_WIDE_SKYSCRAPER
TYPE_ADAPTIVE_BANNER

This item generate the following signals informing regarding the ad status:

onLoadError
onLoading
onLoaded
onClosed
onClicked

The only signal passing a param is onLoadError, called in case of problem in loading ad. The param is errorId and possible values are:

ERROR_INTERNAL
ERROR_NETWORK
ERROR_INVALID_REQUEST
ERROR_NO_FILL

When you want to load and show the banner you have to call the show() function and for hide the hide() functions (banner is the id name of the item in the example above). Function reload() force reload of a new banner.

banner.show()
banner.hide()
banner.reload()

Please note the banner is a native android view over the QML window, that's mean will stay over anything painted into in and you can not place nothing over the banner.


AdMobInterstitial

This tool allows to show AdMob interstitial inside QML app.

Official documentation about AdMob interstitial is here, please read before continue for understand the options exported by the tool. Remember for allow interstitial to be loaded your app need the following permissions:

android.permission.INTERNET
android.permission.ACCESS_NETWORK_STATE
android.permission.WRITE_EXTERNAL_STORAGE

In add of this you have to install the AdMob required packages through Android SDK Manager. The packages you have to install are the following:

  • Google Repository
  • Google Play services
  • Support Repository

Than you have to add the following dependencies into your app gradle file:

dependencies {
    ....
    implementation 'com.google.android.gms:play-services-ads:21.+'
}

Interstitial ad show on full screen but you have to define the AdMob unitId using the item as follow:

QtAndroidAdMobInterstitial {
    id: interstitial
    unitId: "admob-interstitial-unit-id"
    nonPersonalizedAds: false

The unitId is the string generated when you create a new ad unit inside the AdMob site. It's used to identify the ad connected to your app. Using this id you can know how much you earn from this ad unit. The nonPersonalizedAds property is optional (default is false). Set this property to true impose to AdMob to don't use collected user personal data for ads targeting.

This item generate the following signals informing regarding the ad status:

onLoadError
onLoading
onLoaded
onClicked
onDismissed
onShowFailed
onImpression
onShowed

Item have two functions as follow:

interstitial.load()
interstitial.show()

The interstitial have to be loaded before show and since loading is not immediate you have to preload a bit in advance before the time to show. You can follow the loading status through the item signals. Once revecied the onLoaded signal this mean your new interstitial is ready to be showed.

This type of ad have a button allowing the user to close it than you just have to wait about the user choice. Remember also in this case the ad window will go over the QML window and you can not paint anithing on top of it.


AdMobRewardedAd

This tool allow to show AdMob Rewarded Ad inside QML app.

IMPORTANT NOTE: The current implementation of Rewarded Ad API must to be used with only a single instance of the tool cause only one video can be loaded at a time.

Official documentation about AdMob Rewarded Ad is here, please read before continue for understand the options exported by the tool. Remember for allow video to be loaded your app need the following permissions:

android.permission.INTERNET
android.permission.ACCESS_NETWORK_STATE
android.permission.WRITE_EXTERNAL_STORAGE

In add of this you have to install the AdMob required packages through Android SDK Manager. The packages you have to install are the following:

  • Google Repository
  • Google Play services
  • Support Repository

Than you have to add the following dependencies into your app gradle file:

dependencies {
    ....
    implementation 'com.google.android.gms:play-services-ads:21.+'
}

Rewarded Video ad show on full screen but you have to define the AdMob unitId using the item as follow:

QtAndroidAdMobRewardedAd {
    id: rewardedVideo
    unitId: "admob-rewarded-video-unit-id"
    nonPersonalizedAds: false	
}

The unitId is the string generated when you create a new ad unit inside the AdMob site. It's used to identify the ad connected to your app. Using this id you can know how much you earn from this ad unit. The nonPersonalizedAds property is optional (default is false). Set this property to true impose to AdMob to don't use collected user personal data for ads targeting.

This item generate the following signals informing regarding the ad status:

onRewarded
onLoadError
onLoading
onLoaded
onClicked
onDismissed
onShowFailed
onImpression
onShowed

The only signal passing a param is onRewarded. This is is called to inform about the rewarded values. It have two params, type and amount. Check the official documentation for know the value meaning.

Item have two function as follow:

rewardedVideo.load()
rewardedVideo.show()

The video have to be loaded before show and since loading is not immediate you have to preload a bit in advance before the time to show. You can follow the loading status through the item signals. Once revecied the onLoaded signal this mean your new video is ready to be played.

This type of ad have a button allowing the user to close it than you just have to wait about the user choice. Remember also in this case the ad window will go over the QML window and you can not paint anithing on top of it.

After the user close the video you'll receive the rewarded info.


Images

This tool allow to retrieve the device albums and images

There are only the following functions, the first return the list of device albums and the second return the list of all images inside the album (full absolute path of each image):

import QtAndroidTools
							
QtAndroidImages.getAlbumsList()
QtAndroidImages.getAlbumImagesList(albumName)

In particular the first function return an array of string with the names of all albums found and the second one return a list of all image paths inside the selected album name passed as parameter.

The following function add the image to the gallery:

QtAndroidImages.addImageToGallery(imagePath)

The image is not moved from original location but it became part of the system gallery and is showed in the gallery app.

On the contrary the following function:

QtAndroidImages.saveImageToGallery(name, image, format)

save the image into the system gallery. With the param format is possible to set the image format to use and can be QAndroidImages.FORMAT_JPEG or QAndroidImages.FORMAT_PNG.


Notification

This tool will show Android system notifications.

As usual for better understand how to use notification is strongly reccomended to read the official documentation here.

The tool QtAndroidNotification allow to compose and show a system notification in a very easy way as follow:

QtAndroidNotification {
   id: notification
   title: "Notification title"
   text: "This is the notification content"
   expandableText: "This is a very very very very very very very very very very long expandable content"
   channelName: "Notification channel"
   smallIconName: "notification_icon_name"
   largeIconSource: ":/images/logo.jpg"
}

Available notification properties are the the following:

  • title : title of the notification.
  • text : main content of the notification. This filed is mandatory and is limited to one line size.
  • expandableText : in case you need to show a text longer than a line you can set this property with your full text. Based to the Android version the result will be a little different but, in any case, this part will be showed in addition of the text content.
  • channelName : in Android 8.0 and above notification have to be associated to a channel, this for allow user to disable notifications associated to the specific channel. This is a mandatory value.
  • smallIconName : another mandatory value. Basically this is the special format icon showed on system bar connected to the notification. You can find many tools allow to make this icon in the right format. Unfortunately, for support old Android verion, is not possible to pass this icon from Qt resource or from a image file on storage but have to be mandatorily use the apk drawable folders. For try to simplify you don't need to get the full app path but you simply can insert the name of the icon file (without extension) you set into drawable folder (check the demo source).
  • largeIconSource : large icon you can show into notification. You can use an image from Qt resource system of from a file.

In case you need to show a progress bar in the notification there are available the following additional properties:

  • progressBar.max : the max value of the progress bar.
  • progressBar.current : The current value of the progress bar between zero and the max value.
  • progressBar.indeterminate : boolean value for set the prograss bar in the indeterminate state. The result is an indicator that has the same style as the progress bar above, except the progress bar is a continuous animation that does not indicate completion.

The progress bar is showed if you set the max value with a value greater than zero. For hide the progress bar set zero to both max nad current properties value.

The following methods can be called:

show()
cancel()

Once set all the required properties you can show the notification by calling the corresponding function. The notification can be read and cleared directly by the user you can remove from app by using the cancel() call. For update the nodifcation information or the progress bar level you have to call the show() function again. If the user will touch over the notification the app will be ported on foreground or opened if previously closed.


ApkInfo

This tool will return info about the apk containing the executed app.

The info regarding the app apk can be read directly from the QtAndroidApkInfo item as follow:

QtAndroidApkInfo.firstInstallTime
QtAndroidApkInfo.lastUpdateTime
QtAndroidApkInfo.packageName
QtAndroidApkInfo.versionCode
QtAndroidApkInfo.versionName
QtAndroidApkInfo.requestedPermissions

Explanation about fields above can be found in the official Android documentation here. The tool export only the most important info but if you need to have some additional data you can easily add you code by using JNI interface as showed in the sources.


BatteryState

This allow monitoring the battery level and state.

This tool install a listener for monitor the battery level and on charge state. There is nothing difficult in use since there are only two properties as follow:

import QtAndroidTools

QtAndroidBatteryState.level
QtAndroidBatteryState.onCharge

Both properties support QML value binding than you can assign to a control for show always the updated value as in the demo example.


Screen

This tool allow to change screen orientation and set screen to stay always on.

Call to change screen orientation as follow:

QtAndroidScreen.setOrientation(orientaion)

Possible values are the following:

  • SCREEN_ORIENTATION_LANDSCAPE
  • SCREEN_ORIENTATION_REVERSE_LANDSCAPE
  • SCREEN_ORIENTATION_SENSOR_LANDSCAPE
  • SCREEN_ORIENTATION_PORTRAIT
  • SCREEN_ORIENTATION_REVERSE_PORTRAIT
  • SCREEN_ORIENTATION_SENSOR_PORTRAIT

Check official Android documentation about behaviour of each value.

Call to set screen always on as follow:

QtAndroidScreen.keepScreenOn(keepOn)

SignalStrength

This tool allow to monitoring the strength of the phone signal.

This tool install a listener for monitor the phone signal. Remember for allow the library to work in this case the app need to have the following permission:

android.permission.READ_PHONE_STATE

There are two properties reporting the strength of the phone signal in row number and based to the conventional states as follow:

import QtAndroidTools

QtAndroidSignalStrength.signalStrength
QtAndroidSignalStrength.signalLevel

Signal level possible states are the following:

  • LEVEL_GREAT
  • LEVEL_GOOD
  • LEVEL_MODERATE
  • LEVEL_POOR
  • LEVEL_NONE

PLEASE NOTE: the report the the signal strength change doesn't arrive immediately but, instead, require some seconds to be updated after the change. Don't worry if you don't see an immediate update, just wait a little.


PlayStore

This tool allow to open Play Store app details and developer apps list.

import QtAndroidTools

QtAndroidPlayStore.openAppDetails(packageName)
QtAndroidPlayStore.openDeveloperAppList(developerName)

The first call open the Play Store app with the details page of the package name app provided (in the format "com.company.appname").

NOTE: it's possible to call this method without any param, in this case the tool will use the app package name automatically.

The second call will open Play Store listing all the apps connected with the developer name passed in the param.


GoogleAccount

This tool allow to signin using one of the Google accounts currently registered in the device. Please, read carefully the official documentation for knwo how the sigin procedure work here. The tool export the basic methods for easily signin to the last signed account or a new one as the official documentation explain:

import QtAndroidTools

QtAndroidGoogleAccount.signIn(scopeName)
QtAndroidGoogleAccount.signInSelectAccount(scopeName)
QtAndroidGoogleAccount.signOut()
QtAndroidGoogleAccount.revokeAccess()

The second method signInSelectAccount allow to select one of the registered accounts to signin. If only one Google account is present in the device it will be selected automatically. In case of more than one accounts the system activity will start for allow user to select the desired account. Once signedin the app, at each next start, will have only to call the first method to be signedin again with the same account without any other request to user. If you want to signedout and allow to request again the user permission just use the last two methods. After call the signin procedure you have to wait for result through the following signals:

onSignedIn
onSignedOut

The first signal have the signInSuccessfully param informing about the operation result. Once signed successfull you can read the account info using the following fields:

QtAndroidGoogleAccount.signedInAccount.id
QtAndroidGoogleAccount.signedInAccount.displayName
QtAndroidGoogleAccount.signedInAccount.email
QtAndroidGoogleAccount.signedInAccount.familyName
QtAndroidGoogleAccount.signedInAccount.givenName
QtAndroidGoogleAccount.signedInAccount.photo

The photo field export the binary image of the account. For show in a standard Image control you can use the generic image provider as follow:

QtAndroidTools.insertImage("AccountPhoto", QtAndroidGoogleAccount.signedInAccount.photo);
accountPhoto.source = "image://QtAndroidTools/AccountPhoto";

For know which type of scopes use for signin you have to check the documentation cause it changes based to the Google resource you want to access in.


GoogleDrive

This tool export a basic set of methods for work with Google Drive.

PLEASE NOTE: be very careful in using these methods cause you risk deleting some important files from user's Google drive. It's important to TEST VERY WELL your app before release. I take no responsibility for any damage that can be done using these methods.

For know how to use these methods and how to configure the Google drive access you have to read the official documentation here. As first operation you have to authenticate your app by using the corresponding methods:

QtAndroidGoogleDrive.authenticate(appName, scopeName)

The method return a bool value informing the result of the operation. Scope is used to declare the type of access you want to get for Google Drive. The user must authorize the type of access requested before being able to operate. The list of possible scopes is the following, for use of each scope read the documentation here:

  • SCOPE_DRIVE
  • SCOPE_DRIVE_APPDATA
  • SCOPE_DRIVE_FILE
  • SCOPE_DRIVE_METADATA
  • SCOPE_DRIVE_METADATA_READONLY
  • SCOPE_DRIVE_PHOTOS_READONLY
  • SCOPE_DRIVE_READONLY
  • SCOPE_DRIVE_SCRIPTS

Once got the authorization to access the following methods are available:

QtAndroidGoogleDrive.getFilesList(query)
QtAndroidGoogleDrive.getRootId()
QtAndroidGoogleDrive.downloadFile(fileId, localFilePath)
QtAndroidGoogleDrive.uploadFile(localFilePath, mimeType, parentFolderId)
QtAndroidGoogleDrive.createFolder(name, parentFolderId)
QtAndroidGoogleDrive.isFolder(fileId)
QtAndroidGoogleDrive.moveFile(fileId, folderId)
QtAndroidGoogleDrive.deleteFile(fileId)

The first method return an array of structs listing the drive files as showed in the example:

var filesList = QtAndroidGoogleDrive.getFilesList();
var rootId = QtAndroidGoogleDrive.getRootId();

filesListModel.clear();
for(var i = 0; i < filesList.length; i++)
{
	var data = filesList[i];
	var parentId = "null";

	if(data.parents.length > 0)
	{
		if(data.parents[0] === rootId)
			parentId = "root";
		else
			parentId = data.parents[0];
	}

	filesListModel.append({ "id": data.id,
				"name": data.name,
				"mimeType": data.mimeType,
				"parentId": parentId
				});
}

The param query is optional. If you don't pass it the method return the list of all files inside the drive. In case you need a more specific search the documentation about how to use the query is here. All the files and folder have a string id, the method getRootId() return the id of the root folder. Is possible to download a drive file or upload inside drive. The localFilePath is a full path of the file to upload/download including the file name (also for download). The remaining methods allow to manage the drive files. Remember for download a file you must to have granted the WRITE_EXTERNAL_STORAGE permission. Two signals are used to update info regarding the download/upload operations as follow:

Connections {
	target: QtAndroidGoogleDrive
	function onDownloadProgressChanged(state, progress)
	{
		switch(state)
		{
			case QtAndroidGoogleDrive.STATE_MEDIA_IN_PROGRESS:
				break;
			case QtAndroidGoogleDrive.STATE_MEDIA_COMPLETE:
				break;
		}
	}
	function onUploadProgressChanged(state, progress)
	{
		switch(state)
		{
			case QtAndroidGoogleDrive.STATE_INITIATION_STARTED:
				break;
			case QtAndroidGoogleDrive.STATE_INITIATION_COMPLETE:
				break;
			case QtAndroidGoogleDrive.STATE_MEDIA_IN_PROGRESS:
				break;
			case QtAndroidGoogleDrive.STATE_MEDIA_COMPLETE:
				break;
		}
	}
}

Both signal have tow params state and progress.


Sharing

This tool allow to use the Android sharing feature for share file, text and binary data.

For know how to configure and use the app for manage sharing data you have to carefully read the official documentation here for simple data and here for files. As you can read the "standard" way should be do create a dedicated activity fo each sharing data type but, cause Qt for android have only a single activity loading the native code, my solution is to use this unique main activity for all tha cases and check during startup phase if the activity has been launched for sharing purposes. Than inside the AndroidManifest.xml activity section you can add the required action based to the data you want to share (the following is from the demo app code):

<intent-filter>
   <action android:name="android.intent.action.SEND"/>
   <category android:name="android.intent.category.DEFAULT"/>
   <data android:mimeType="text/plain"/>
</intent-filter>
<intent-filter>
   <action android:name="android.intent.action.SEND"/>
   <category android:name="android.intent.category.DEFAULT"/>
   <data android:mimeType="image/*"/>
</intent-filter>
<intent-filter>
   <action android:name="android.intent.action.PICK"/>
   <category android:name="android.intent.category.DEFAULT"/>
   <category android:name="android.intent.category.OPENABLE"/>
   <data android:mimeType="image/*"/>
</intent-filter>

Regarding the file sharing provider make sure the following tag is present:

<provider android:name="androidx.core.content.FileProvider"
          android:authorities="${applicationId}.qtprovider"
          android:grantUriPermissions="true"
          android:exported="false">
    <meta-data android:name="android.support.FILE_PROVIDER_PATHS" android:resource="@xml/qtprovider_paths"/>
</provider>

You can name the resource as you prefer but don't change the authorities name cause the tool refer to this label (qtandroidtoolsfileprovider) for configure the correct resource.

For share simple data from your app to other apps the following function are available:

QtAndroidSharing.shareText(text)
QtAndroidSharing.shareBinaryData(mimeType, dataFilePath)

A system window will be showed with all the apps able to receive the data type you want to share as follow:

Once the user will select the preferred one the data will be transfered automatically.

In case you want to ask for a file shared by other apps the procedure is a bit different. At first you have to use the following function with the param the file mime type you need:

QtAndroidSharing.requestSharedFile(mimeType)

Anothe different systme window will show the apps able to share the file type you need:

The selection will open the app sharing the file and the user have to choose the file or cancel the operation. Both actions will return the two events as follow:

Connections {
   target: QtAndroidSharing
   function onRequestedSharedFileReadyToSave(mimeType, name, size)
   {
   }
   function onRequestedSharedFileNotAvailable()
   {
   }
}

The second event will inform thet the requested file is not available for various reasons (probably the user cancelled the operation). The first event will export three params named name, size and mimeType with info regarding the user selected file. Please note in this phase the file has not been imported yet. The info will help you to "decide" if the selected file can be imported (for example if the selected file is too much big in size). If you decide the file is correct you have to call the function to import and save somewhere in your app space:

QtAndroidSharing.saveRequestedSharedFile(filePath)

In case you are not interested to have the file you have to cancel the operation by call:

QtAndroidSharing.closeRequestedSharedFile()

Now the opposite part, that's mean reply to shared requested from other apps. As explained in the first part of this section the activity receiving the request is always the main one. This mean the only way to know if our app has been lanuched from another app asking for share something is to check on startup phase as follow:

Component.onCompleted: {
    if(QtAndroidTools.activityAction === QtAndroidTools.ACTION_SEND)
    {
        if(QtAndroidTools.activityMimeType === "text/plain")
        {
        }
        else if(QtAndroidTools.activityMimeType.startsWith("image") === true)
        {
        }
    }
    else if(QtAndroidTools.activityAction === QtAndroidTools.ACTION_PICK)
    {
    }
}

Currently the supported actions are the following:

QtAndroidTools.ACTION_NONE
QtAndroidTools.ACTION_SEND
QtAndroidTools.ACTION_SEND_MULTIPLE
QtAndroidTools.ACTION_PICK

For the first two requests (ACTION_SEND and ACTION_SEND_MULTIPLE) you can receive the shared data sent to you by using the following functions:

QtAndroidSharing.getReceivedSharedText()
QtAndroidSharing.getReceivedSharedBinaryData()
QtAndroidSharing.getReceivedMultipleSharedBinaryData()

For the action requesting to share a file (ACTION_PICK) you have to show a window for allow the user to select the file he want to import into the requesting app. In the demo app we have only one file to share that the choose is only if you want or not the file:

After the user made a selection you have to reply by using the following function:

QtAndroidSharing.shareFile(fileAvailable, mimeType, filePath)

In case the user want the file you have to set the fileAvailable as true and provide the other params. In the opposite case (the user refused) you have to call this function by set the first param as false without provide the other params.


UserMessagingPlatform

Under the Google EU User Consent Policy, you must make certain disclosures to your users in the European Economic Area (EEA) along with the UK and obtain their consent to use cookies or other local storage, where legally required, and to use personal data (such as AdID) to serve ads. This policy reflects the requirements of the EU ePrivacy Directive and the General Data Protection Regulation (GDPR).

This tool support the use of the UMP SDK but for a clear explanation about how to use this SDK and how to configure the consent form you have to read the official guide here. At first you must to request the consent form that can be or not be available for the zone your current user is:

QtAndroidUserMessagingPlatform.loadAndShowConsentFormIfRequired(underAgeOfConsent)

Param underAgeOfConsent is a boolean value to inform if the user is under age.

This function will generate two possibile events. One informing about failure with the error message string and the other informing about the form has been closed by the user. The two params inform, the first, if the form has been processed corrently or some error has occurred and, the second, if is required to show an option allowing the user to change the initial selection by showing again the form.

Connections {
    target: QtAndroidUserMessagingPlatform
    function onConsentFormRequestFailure(errorMessage)
    {
    }
    function onConsentFormDismissed(consentGathered, privacyOptionsRequired)
    {
    }
}

To show the form again just call the function:

QtAndroidUserMessagingPlatform.showPrivacyOptionsForm()

To know if it will be possible to show ads it should be used this function (but, at least right now, it seems always return true also if the user negate consent to show ads):

QtAndroidUserMessagingPlatform.showPrivacyOptionsForm()

If you want to reset these data for restart from scratch you can use the call:

QtAndroidUserMessagingPlatform.canRequestAds()

This will clean all saved data.

PLEASE NOTE: the problem is that if the user does not accept consent, the Ads is not displayed. Or if the user accepts only some parts the Ads must be set as non-personalised. Unfortunately there is no "official" way to understand what the user has selected. I found these two functions that allow you to understand whether the user has authorized complete Ads or only non-personalized Ads or nothing at all. However, as it is not an official code, it is not guaranteed that it will work correctly in the future so keep this in mind when using them. If the first funtion return false you should prompt the user or to accept all, or explain in details what to check to display at least Non-Personalized Ads, or ask the user to opt for a premium version of the app, otherwise you will earn absolutely nothing. If true you can check, using the second function, if user granted at least minimum requirements to show Personalized Ads.

QtAndroidSharing.consentCanShowAds()
QtAndroidSharing.consentCanShowPersonalizedAds()

Audio

This tool allow to get the audio focus and be notified when audio is requested by another application (typical when a call comes in).

You can request and abandon the audio focus using the following calls. If you don't get the audio focus you will not be advised if some other apps request the focus. This is important because, for example, if you are generating a sound and a call comes in, your sound will be generated in parallel with the voice of the call itself. Using this feature you must stop the sound when you lose focus and resume when the focus returns to your application.

QtAndroidAudio.requestFocus()
QtAndroidAudio.abandonFocus()

Once the focus has been acquired, the following variable indicates whether the focus is present or lost.

QtAndroidAudio.focus

System

This tool allows to request to send an email:

import QtAndroidTools

QtAndroidSystem.requestEmailSend(emails, subject, body, description)

emails is an array of email addresses to send same email to multiple destinations. subject and body can prefill the mail content and description is a text advising the user regarding the requested action.

It also export three simply conversion functions from graphic units to pixel size:

import QtAndroidTools
							
QtAndroidSystem.spToPx()
QtAndroidSystem.dipToPx()
QtAndroidSystem.ptToPx()