Add a service in an Android Qt app
-
Hi, I'm going crazy on how to start a service of an Android app in a separate .so with a own main() function. I haven't got a particular error on console and I don't know how the app should start the service. Should it to call a jni function?
The service section of AndroidManifest.xml file of the app that has to start the service is the follow:
<service android:process=":qt_service" android:name="com.kdab.training.MyService"> <meta-data android:name="android.app.lib_name" android:value="service"/> <meta-data android:name="android.app.background_running" android:value="true"/> </service>
The main.cpp of the library is
#include <QDebug> int main(int argc, char *argv[]) { qInfo() << "Hello from service"; qInfo() << "Hello from service"; qWarning() << "Service starting from a separate .so file"; return 0; }
Its .pro file is
TEMPLATE = lib TARGET = service CONFIG += dll QT += core androidextras SOURCES += \ main.cpp
MyService.java class
// java file android/src/com/kdab/training/MyService.java package com.kdab.training; import android.content.Context; import android.content.Intent; import org.qtproject.qt5.android.bindings.QtService; public class MyService extends QtService { private static final String TAG= "QtAndroidService"; @Override public void onCreate() { super.onCreate(); android.util.Log.i(TAG, "onCreate()"); } @Override public void onDestroy() { android.util.Log.i(TAG, "onDestroy()"); super.onDestroy(); } public static void startMyService(Context ctx) { android.util.Log.i("aa", "bbbbbbbbbbbbbbbbbbbb1"); android.util.Log.i("aa", "bbbbbbbbbbbbbbbbbbbb2"); ctx.startService(new Intent(ctx, MyService.class)); } }
The jni call
QAndroidJniObject::callStaticMethod<void>("com/kdab/training/MyService", "startMyService", "(Landroid/content/Context;)V", QtAndroid::androidActivity().object());
In console I read
Hello from client1 (from gui main.cpp) and onCreate() from java class -
Hi, I'm going crazy on how to start a service of an Android app in a separate .so with a own main() function. I haven't got a particular error on console and I don't know how the app should start the service. Should it to call a jni function?
The service section of AndroidManifest.xml file of the app that has to start the service is the follow:
<service android:process=":qt_service" android:name="com.kdab.training.MyService"> <meta-data android:name="android.app.lib_name" android:value="service"/> <meta-data android:name="android.app.background_running" android:value="true"/> </service>
The main.cpp of the library is
#include <QDebug> int main(int argc, char *argv[]) { qInfo() << "Hello from service"; qInfo() << "Hello from service"; qWarning() << "Service starting from a separate .so file"; return 0; }
Its .pro file is
TEMPLATE = lib TARGET = service CONFIG += dll QT += core androidextras SOURCES += \ main.cpp
MyService.java class
// java file android/src/com/kdab/training/MyService.java package com.kdab.training; import android.content.Context; import android.content.Intent; import org.qtproject.qt5.android.bindings.QtService; public class MyService extends QtService { private static final String TAG= "QtAndroidService"; @Override public void onCreate() { super.onCreate(); android.util.Log.i(TAG, "onCreate()"); } @Override public void onDestroy() { android.util.Log.i(TAG, "onDestroy()"); super.onDestroy(); } public static void startMyService(Context ctx) { android.util.Log.i("aa", "bbbbbbbbbbbbbbbbbbbb1"); android.util.Log.i("aa", "bbbbbbbbbbbbbbbbbbbb2"); ctx.startService(new Intent(ctx, MyService.class)); } }
The jni call
QAndroidJniObject::callStaticMethod<void>("com/kdab/training/MyService", "startMyService", "(Landroid/content/Context;)V", QtAndroid::androidActivity().object());
In console I read
Hello from client1 (from gui main.cpp) and onCreate() from java class -
In the apk there isn't the .so service file. To put it into I have added it using ANDROID_EXTRA_LIBS but still does not work.
In order to start an app service of an external .so library, which are the steps?
Have I to call the "startMyService" function or the <service> section od manifest file is enought? -
In the apk there isn't the .so service file. To put it into I have added it using ANDROID_EXTRA_LIBS but still does not work.
In order to start an app service of an external .so library, which are the steps?
Have I to call the "startMyService" function or the <service> section od manifest file is enought?@mrdebug You have to create a BroadcastReceiver and call it through the manifest to start the service
cf. :https://doc.qt.io/qt-5/android-services.html#start-a-service-on-demandSomething like:
public class BootMyServiceBroadcastReceiver extends BroadcastReceiver { @Override public void onReceive(Context context, Intent intent) { Intent startServiceIntent = new Intent(context, MyService.class); context.startService(startServiceIntent); } }
And in Manifest, in
application
section:<receiver android:name=".BootMyServiceBroadcastReceiver"> <intent-filter> <action android:name="android.intent.action.MAIN" /> </intent-filter> </receiver>
-
Thanks for the reply. My problem is not when to call "context.startService(startServiceIntent);" (i call it on demand). The problem is how to call the "main(int argc, char *argv[])" function of the separate .so library.
My "startMyService(Context ctx)" method is called correctly (I see the log of it). After that I see the log of "onCreate()" method but my .so library library never starts.
Is this section of manifest file wrong?<service android:process=":qt_service" android:name="com.kdab.training.MyService"> <meta-data android:name="android.app.lib_name" android:value="service"/> <meta-data android:name="android.app.background_running" android:value="true"/> </service>
-
Thanks for the reply. My problem is not when to call "context.startService(startServiceIntent);" (i call it on demand). The problem is how to call the "main(int argc, char *argv[])" function of the separate .so library.
My "startMyService(Context ctx)" method is called correctly (I see the log of it). After that I see the log of "onCreate()" method but my .so library library never starts.
Is this section of manifest file wrong?<service android:process=":qt_service" android:name="com.kdab.training.MyService"> <meta-data android:name="android.app.lib_name" android:value="service"/> <meta-data android:name="android.app.background_running" android:value="true"/> </service>
@mrdebug said in Add a service in an Android Qt app:
Thanks for the reply. My problem is not when to call "context.startService(startServiceIntent);" (i call it on demand). The problem is how to call the "main(int argc, char *argv[])" function of the separate .so library.
My "startMyService(Context ctx)" method is called correctly (I see the log of it). After that I see the log of "onCreate()" method but my .so library library never starts.
Is this section of manifest file wrong?Sorry, I don't understand what your problem is.
Themain()
function is called on Activity or Service start, so if your service is running,main()
has been called. -
I've same problem too. Three months ago I wrote a sample app to test Android services. All worked well. Now, when I rebuild that code, i see the same behavior that you described. QtService seems never loading the library, so my service main function is never called. I'm trying to understand... I don't remember if i upgraded some part of toolchain or library in last 3 months, but it's very probable. Anyway, @mrdebug code is correct in my opinion. It's very similar to mine (I followed kdab example too).
-
After a long time (and 1 night at the pc) I have found the solution. There are many steps to do in order to have a pure c++ service embedded in an Qt Android app. The Qt - C++ service work perfecly, fast and stable.
Sorry if I don't write the solution here. The solution requires a full project and it is not possible to upload it here. -
After a long time (and 1 night at the pc) I have found the solution. There are many steps to do in order to have a pure c++ service embedded in an Qt Android app. The Qt - C++ service work perfecly, fast and stable.
Sorry if I don't write the solution here. The solution requires a full project and it is not possible to upload it here. -
Here you are
https://github.com/denisgottardello/QtAndroidServiceExternalLib
Keep adb logcat active to see the full log -
as @mrdebug wrote, the service .so library file is never copied into apk. Coming back to Qt Creator 5.0.0 from 6.0.2, all files are copied properly into the package and all works well again.
@Darude-0 , as tricks I use "ANDROID_EXTRA_LIBS" to copy library into apk.
for (abi, ANDROID_ABIS): { message(The LibCore will be installed in $${abi}) ANDROID_EXTRA_LIBS += $$OUT_PWD/../LibCore/libLibCore_$${abi}.so LIBS += -L$$OUT_PWD/../LibCore/ -lLibCore_$${abi} }