Can Qt framework be used to create cross platform libraries - android

Qt (http://qt-project.org/) looks like a great cross-platform framework for developing applications, however I can't seem to find if it can be use to create libraries.
Can I use it to create a reusable piece of code that will be compiled to a Windows .dll, OSX and iOS .dylib and Android .jar file?

Usually, the only difference between an application and a shared library is a few option bits in the image file. So yes, you can certainly use Qt to write reusable software libraries.
Here are the caveats:
If the libraries that you create expose C++ interfaces (as opposed to C interfaces), your users will need to use the same compiler version to build their code that links with your library. The C interfaces must be declared extern C.
If the library that you use is linking dynamically against Qt, then your user is forced to use a binary-compatible version of Qt: that means that it must be compiled with the same compiler, and without binary-incompatible changes.
For use on non-package-managed platforms (like Windows), I'd link my library statically to both Qt and the Visual C++ runtime. For platforms with package managers (Linux, macports on OS X), I'd offer both a statically linked library as well as a platform-specific package (say RPMs for RHEL6, macports portfile, etc.) that then depends on platform-standard C++ runtime, and Qt if such exists (some platforms don't provide Qt 5 yet).

Related

How to integrate Qt library inside Android native project

I am a native Android developer, and a client has asked me to re-use his Qt library project in a native Android app. I am really new to Qt development, I mean, I understand C/C++ but have never dealt with Qt development itself, neither the environment or the deployment methods.
I have been looking into these solutions, but I don't get any closer to being able to create an Android project with a Qt library inside with which I can interact.
Similar solutions:
http://thebugfreeblog.blogspot.com/2012/05/embedded-cross-platform-development-for.html
https://developer.android.com/studio/projects/add-native-code#create-sources
My question: How do I export my Qt project to a usable format for my Android project? Any step-by-step guide would be really appreciated.
Thanks!
Assuming your Qt application is only used for its logic (not the GUI side), what you need it to:
Adding JNI to your Qt library for Android
JNI (Java Native Interface) allows creating an interface to link and use native (C++) code from Java. This is used to wrap your C++ code and provide functions visible and usable directly from your Android application
Install the version of Qt you want for Android using Qt's online installer (a checkbox when choosing the version of Qt you want)
Create a JNI interface to allow your application and the library to talk. This is covered in that sample: https://developer.android.com/ndk/samples/sample_hellojni. I would probably recommend creating another C++/JNI library acting as a wrapper for your C++/Qt library. That way you don't contaminate the original library with JNI dependencies.
Integrate your JNI library in your application
Once your have a JNI interface, you have to cross-compile and ship that library with your Android application
Build your native library from Android Studio (after pointing to your Qt libraries and include dir). Alternatively, you can manually build it from Qt Creator (slightly easier) and import only the resulting .so. But that will be painful if your Qt library changes
Package the library (.so), and load it when your application starts. This is also covered in the sample. Once the library is loaded, you will be able to use the JNI functions that you exposed and pass arguments, after some conversion work. Your Android application can also pass a handle to the native library, allowing communication in both ways.
Notes
Be careful to the licensing of your project. Cross-compiling Qt for Android will likely switch to its GPLv3 or Commercial license, versus LGPLv3 without Android.
Qt libraries have to be included in your final pacakge. So they either have to be statically linked against your original library, or dynamically linked, and stored in your APK
You can leverage Qt JNI classes to make the creation of the interface easier, but that is not required: https://doc.qt.io/qt-5/qandroidjniobject.html
Threading can become difficult, as calls to/from JNI have to run from the main thread
I would recommend starting from a working example if you find one, as that whole setup will definitely take some time. I don't know of a complete tutorial covering that, but feel free to share if you find one!

why do we need to use android tool-chain(or NDK) for compiling c/c++ code running in the context of an android app?

I built a library(.so) that is being called from JNI code in some android app. The JNI code is built using NDK.
If I build the library using android tool-chain, the library works well when called from JNI code.
If I build the library using another tool-chain (used on the same ARM device for none android applications), the library crashes when called from JNI code.
why do we need to use android tool-chain (or NDK) for compiling c/c++ code running in the context of an android app? why not use other tool-chains?
You can use other toolchains, but it requires special care.
Maybe a good starter would be to learn the UBERTC and Linaro Wiki.
The main difference is that NDK compilers are tuned for bionic (Android variant of C runtime libraries). Originally, bionic was a modest subset of Linux runtime. On latest platforms, most of the gap is closed, but now there are many extensions that you probably need.
Also, Android dynamic linker may require (depending on target platform) a set of ELF flags that are automatically delivered by NDK binutils, like PIC, id, and others.
It is quite possible to use arm-linux toolchain to build a statically linked executable that will run on Android, but for a library that must play well on the JNI environment the effort is probably not worth it.
Note that NDK provides tools to create a standalone toolchain, which behaves very similar to other toolchains you may be familiar with. This approach makes it easy to adopt 3rd-party libraries with sophisticated build scripts.

How do I create a shared library in C++ for both Android and iOS?

I am using LibGDX to write apps for both Android and iOS and I want to be able to add C++ code to my apps to optimize certain parts and to port some functions etc.
I have been searching the internet and tried to follow some tutorials, but did not find what I need.
How can I write a very basic C++ library which I can load in LibGDX? Which tools do I need to use? Visual Studio? I develop in Android Studio.
I think that I need an .so file for Android and an .a file for iOS, is that correct?
On both platforms, it's possible to include a precompiled library as well as C++ source code directly.
On Android, you'll want to look into using the Android NDK. This allows you to include native C/C++ code that can bridge over to Java. The connection between Java and C/C++ is managed with the JNI. It's a fairly tedious, awkward system for communicating between C++ and Java. You'll want to look into setting up an Android.mk makefile that specifies how to include your library (or source code) into your build.
On iOS, it's a little more tightly linked. You can have Objective-C++ files that can run both C++ and Objective-C code. If you're using Swift, it's a little different (bridging between Objective-C++ and Swift).
In some cases, when the platform (Android/iOS) provides functionality that is superior to what is possible or realistic with C++, you might find yourself architecting the code such that your C++ can reach out to the platform as needed. This means that you might have headers with separate implementation files per platform.
thing.h
thing_android.cpp
thing_ios.mm
The android app's Android.mk file will include thing_android.cpp (but not thing_ios.mm). This file could cross the JNI bridge to talk to Java as needed, whenever you need something from Android SDK.
The iOS app will include thing_ios.mm (but not thing_android.cpp). The .mm extension signifies Objective-C++, so that file could directly call powerful Cocoa libraries as needed.
Finally, on all platforms, you'll want to be sure to either scale back your usage of C++ to the lowest common denominator platform. In other words, if iOS supports a particular feature of C++, and Android doesn't, then you cannot use that particular feature.

How to use Android NDK in Qt project?

Is there a way to use JNI calls directly in the Qt application? I've read how to use NDK itself (creating jni folder, Android.mk, compiling "by hands"). Does Qt give you opportunity to avoid this actions? Or it only uses NDK to work with Qt libraries?
If I understood your question correctly, then this is something that even the Qt Project internally has to use for certain functionality that is not available by the native platform, just through the Darvik layer, so this means a "yes" to your question.
Also, you may wish to look into the Qt Android Extras module to have a convenient Qt wrapper around that functionality to enable the smoother integration.
Qt Android Extras C++ Classes
For your convenience, here goes the gist inline:
QAndroidJniEnvironment Access to the JNI Environment
QAndroidJniObject Provides APIs to call Java code from C++

Android-Ndk vs Cross-Compile? Both work, but what was the need of Android NDK then?

I can cross-compile any C/C++ application, statically link it Linux libraries and run it on Android. What was the need of an Android-ndk then? Android-ndk limits us to bionic which has a small subset of gnu libc. Isn't it a better idea to straightaway cross-compile applications and run them through Android shell? Is there any limitation to cross-compiling that I can't see? This URL : Can Linux apps be run in Android? answers my question to some extent but eventually leaves me confused and without clarity.
I think this is enough for Android-NDK
The Android NDK is a companion tool to the Android SDK that lets you build performance-critical portions of your apps in native code. It provides headers and libraries that allow you to build activities, handle user input, use hardware sensors, access application resources, and more, when programming in C or C++. If you write native code, your applications are still packaged into an .apk file and they still run inside of a virtual machine on the device. The fundamental Android application model does not change.
The NDK provides:
A set of tools and build files used to generate native code libraries
from C and C++ sources
A way to embed the corresponding native libraries into an application
package file (.apk) that can be deployed on Android devices
A set of native system headers and libraries that will be supported
in all future versions of the Android platform, starting from Android
1.5. Applications that use native activities must be run on Android 2.3 or later.
This thing you can not find in other cross-compilation with arm toolchain..
As mentioned in the link http://developer.android.com/sdk/ndk/index.html NDK is a companion for App development folk to create performance sensitive native code. NDK exposes some of the native implementation of Android which could not be found in the general Linux environments. Some of them include the Android/Bitmap, Android/nativeWindow etc. Using these Android natives applcation can speed up CPU intensive processes like some compression or decompression of images.
Even though the externally cross-compiled executables may run in the Android there no guarantee that versions of the standard library implementaions are the same. NDK provides a easier and Android compatible toolchain and other resources, using which is much easier to application developers than having to find a compatible cross-compiler for their usecase.

Categories

Resources