New apps and app updates must target Android 10 (API level 29) or higher; except for Wear OS apps, which must target API level 28.
It is necessary to change targetSdkVersion
from 28
to 29
or higher.
The first problem to do this :
Version 28 (intended for Android Pie and below) is the last version of the legacy support library. Because this project ( the app ) is using support library. It is the initial problem in order to update targetSdkVersion
.
The solution for this initial problem :
As per Support Library Documentation, which states that -
With the release of Android 9.0 (API level 28) there is a new version of the support library called AndroidX which is part of Jetpack. The AndroidX library contains the existing support library and also includes the latest Jetpack components.
So, the project should be migrated from Support Library to AndroidX.
Is this solution enough?
As issue #973 and #989 comments that Image To PDF feature was stopped working after changing targetSdkVersion
from 28
to 29
, further work was to be done to resolves these mentioned issues.
Resolution of Issues #973 and #989 :
The problem is due to scoped storage concept of Google's new storage policy!
Problem?
As Google's new storage policy states that -
To give users more control over their files and to limit file clutter, apps that target Android 10 (API level 29) and higher are given scoped access into external storage, or scoped storage, by default.
What is scoped storage?
Scoped storage as its name suggest, it is the specific storage path or specific folder that user have chosen to save any data, files, etc.
Why google Introduced this storage policy?
When WRITE_EXTERNAL_STORAGE
permission is granted by user then the app get full access to the entire storage. It can do anything with any file in the storage ( except other app's private storage ). And by this behaviour, you can understand how danger this permission is if given to any bad app.
What exactly this policy say?
Now, in API 29+, even if user granted WRITE_EXTERNAL_STORAGE
permission, the app still not granted write access. Rather when the app wanted to write anything in the storage, the user will specifically have to choose a specific directory to save the file. It means app can't do anything with the storage without user's consent (neither can create folder nor can delete any).
What changed, Before policy vs After policy?
- Before, any app with
WRITE_EXTERNAL_STORAGE
permission can do anything with storage.
- Now, any app even with
WRITE_EXTERNAL_STORAGE
permission, can't do anything until user choose to give the permission to specific folder (SPECIFIC FOLDER NOT ENTIRE STORAGE).
More information at developer.android.com.
Thus, implementing scoped storage method to save pdf or images to storage will fix #973 , fix #989
Type of change
How Has This Been Tested?
- [x]
./gradlew assembleDebug assembleRelease
- [x]
./gradlew checkstyle
Successfully tested on :
- Android 9 Pie (Redmi 6A API 28) --Physical device
- Android 10 Q (Pixel 2 API 29) --Android Virtual Device(AVD)
Checklist:
- [x] Migrated to AndroidX
- [x] App targeted to API 30 (Thus satisfy Google requirement)
- [x] Solved scoped storage related issue in android 10 or higher ( api 29+)
Updated README.md
- Added GIF of updated UI in screenshot folder ( image_to_pdf2.gif )
- Delete GIF of previous UI in screenshot folder ( image_to_pdf.gif )
Additional note
Closed #975 (redundant issue), because it is not closed by issue opener even after being resolved.
A note on resolution of scoped storage issue
- Optimized runtime permissions
- Removed unnecessary permissions
- Removed permission request from main activity because runtime permission should only be requested just before the action for which it is needed.
- Camera permission is only needed in Qr scanner activity, so removed from other activities and fragments
- In Api 29+, no permission is needed expect the camera permission ( keeping matisse library in exception because it only need
READ_EXTERNAL_STORAGE
permission.