From 9e7a9b410faaf6695a4561478c5ace1e92a78604 Mon Sep 17 00:00:00 2001 From: thelittlefireman Date: Sun, 28 Mar 2021 18:45:44 +0200 Subject: [PATCH] Add scan document feature Signed-off-by: tobiasKaminsky Signed-off-by: thelittlefireman Signed-off-by: tobiasKaminsky --- build.gradle | 2 + drawable_resources/ic_scan_document.svg | 9 +++ ...ialog.DialogFragmentIT_testBottomSheet.png | Bin 26150 -> 27167 bytes .../android/ui/dialog/DialogFragmentIT.java | 5 ++ src/main/AndroidManifest.xml | 5 ++ .../android/ui/activity/AppScanActivity.kt | 59 ++++++++++++++++++ .../ui/activity/FileDisplayActivity.java | 30 +++++++++ .../ui/activity/UploadFilesActivity.java | 3 +- .../OCFileListBottomSheetActions.java | 5 ++ .../fragment/OCFileListBottomSheetDialog.java | 5 ++ .../ui/fragment/OCFileListFragment.java | 16 +++++ .../ui/helpers/FileOperationsHelper.java | 26 ++++++-- src/main/res/drawable/ic_scan_document.xml | 13 ++++ ...ile_list_actions_bottom_sheet_fragment.xml | 32 +++++++++- src/main/res/values/strings.xml | 2 + 15 files changed, 205 insertions(+), 7 deletions(-) create mode 100644 drawable_resources/ic_scan_document.svg create mode 100644 src/main/java/com/owncloud/android/ui/activity/AppScanActivity.kt create mode 100644 src/main/res/drawable/ic_scan_document.xml diff --git a/build.gradle b/build.gradle index 8c2cc635bc..b7b88363f0 100644 --- a/build.gradle +++ b/build.gradle @@ -274,6 +274,8 @@ dependencies { implementation "com.github.cotechde.hwsecurity:hwsecurity-fido:$fidoVersion" implementation "com.github.cotechde.hwsecurity:hwsecurity-fido2:$fidoVersion" + implementation 'com.github.zynkware:Document-Scanning-Android-SDK:1.0.1' + spotbugsPlugins 'com.h3xstream.findsecbugs:findsecbugs-plugin:1.11.0' spotbugsPlugins 'com.mebigfatguy.fb-contrib:fb-contrib:7.4.7' diff --git a/drawable_resources/ic_scan_document.svg b/drawable_resources/ic_scan_document.svg new file mode 100644 index 0000000000..5d8d876202 --- /dev/null +++ b/drawable_resources/ic_scan_document.svg @@ -0,0 +1,9 @@ + + + + + + \ No newline at end of file diff --git a/screenshots/gplay/debug/com.owncloud.android.ui.dialog.DialogFragmentIT_testBottomSheet.png b/screenshots/gplay/debug/com.owncloud.android.ui.dialog.DialogFragmentIT_testBottomSheet.png index 7b351248b435b64ec3e3645c8f7bd142b72b0557..11fb3fb7b2db7fb69d74bf6a1007655d1bbc796d 100644 GIT binary patch literal 27167 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 literal 26150 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 diff --git a/src/androidTest/java/com/owncloud/android/ui/dialog/DialogFragmentIT.java b/src/androidTest/java/com/owncloud/android/ui/dialog/DialogFragmentIT.java index d11c82cea2..b554918c46 100644 --- a/src/androidTest/java/com/owncloud/android/ui/dialog/DialogFragmentIT.java +++ b/src/androidTest/java/com/owncloud/android/ui/dialog/DialogFragmentIT.java @@ -334,6 +334,11 @@ public class DialogFragmentIT extends AbstractIT { } + @Override + public void scanDocUpload() { + + } + @Override public void showTemplate(Creator creator, String headline) { diff --git a/src/main/AndroidManifest.xml b/src/main/AndroidManifest.xml index fd15977a44..3a65dc9468 100644 --- a/src/main/AndroidManifest.xml +++ b/src/main/AndroidManifest.xml @@ -117,6 +117,11 @@ android:name="android.app.searchable" android:resource="@xml/users_and_groups_searchable" /> + diff --git a/src/main/java/com/owncloud/android/ui/activity/AppScanActivity.kt b/src/main/java/com/owncloud/android/ui/activity/AppScanActivity.kt new file mode 100644 index 0000000000..6d80172b13 --- /dev/null +++ b/src/main/java/com/owncloud/android/ui/activity/AppScanActivity.kt @@ -0,0 +1,59 @@ +/* + * + * Nextcloud Android client application + * + * @author Tobias Kaminsky + * Copyright (C) 2022 Tobias Kaminsky + * Copyright (C) 2022 Nextcloud GmbH + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU Affero General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Affero General Public License for more details. + * + * You should have received a copy of the GNU Affero General Public License + * along with this program. If not, see . + */ + +package com.owncloud.android.ui.activity + +import android.app.Activity +import android.content.Intent +import android.os.Bundle +import com.owncloud.android.R +import com.owncloud.android.utils.DisplayUtils +import com.zynksoftware.documentscanner.ScanActivity +import com.zynksoftware.documentscanner.model.DocumentScannerErrorModel +import com.zynksoftware.documentscanner.model.ScannerResults + +class AppScanActivity : ScanActivity() { + override fun onCreate(savedInstanceState: Bundle?) { + super.onCreate(savedInstanceState) + addFragmentContentLayout() + } + + override fun onError(error: DocumentScannerErrorModel) { + DisplayUtils.showSnackMessage(this, R.string.error_starting_scan_doc) + } + + override fun onSuccess(scannerResults: ScannerResults) { + val intent = Intent() + + intent.putExtra( + "file", + scannerResults.transformedImageFile?.absolutePath ?: scannerResults.croppedImageFile?.absolutePath + ) + + setResult(Activity.RESULT_OK, intent) + finish() + } + + override fun onClose() { + finish() + } +} diff --git a/src/main/java/com/owncloud/android/ui/activity/FileDisplayActivity.java b/src/main/java/com/owncloud/android/ui/activity/FileDisplayActivity.java index 6342d3bfe8..20ee39908d 100644 --- a/src/main/java/com/owncloud/android/ui/activity/FileDisplayActivity.java +++ b/src/main/java/com/owncloud/android/ui/activity/FileDisplayActivity.java @@ -192,6 +192,7 @@ public class FileDisplayActivity extends FileActivity public static final int REQUEST_CODE__MOVE_FILES = REQUEST_CODE__LAST_SHARED + 3; public static final int REQUEST_CODE__COPY_FILES = REQUEST_CODE__LAST_SHARED + 4; public static final int REQUEST_CODE__UPLOAD_FROM_CAMERA = REQUEST_CODE__LAST_SHARED + 5; + public static final int REQUEST_CODE__UPLOAD_SCAN_DOC_FROM_CAMERA = REQUEST_CODE__LAST_SHARED + 6; protected static final long DELAY_TO_REQUEST_REFRESH_OPERATION_LATER = DELAY_TO_REQUEST_OPERATIONS_LATER + 350; @@ -916,6 +917,35 @@ public class FileDisplayActivity extends FileActivity } } }, new String[]{FileOperationsHelper.createImageFile(getActivity()).getAbsolutePath()}).execute(); + } else if (requestCode == REQUEST_CODE__UPLOAD_SCAN_DOC_FROM_CAMERA && + (resultCode == RESULT_OK || resultCode == UploadFilesActivity.RESULT_OK_AND_DELETE)) { + Uri fileUri = Uri.parse(data.getStringExtra("file")); + + new CheckAvailableSpaceTask(new CheckAvailableSpaceTask.CheckAvailableSpaceListener() { + @Override + public void onCheckAvailableSpaceStart() { + Log_OC.d(this, "onCheckAvailableSpaceStart"); + } + + @Override + public void onCheckAvailableSpaceFinish(boolean hasEnoughSpaceAvailable, String... filesToUpload) { + Log_OC.d(this, "onCheckAvailableSpaceFinish"); + + if (hasEnoughSpaceAvailable) { + File file = new File(filesToUpload[0]); + File renamedFile = new File(file.getParent() + PATH_SEPARATOR + FileOperationsHelper.getCapturedImageName()); + + if (!file.renameTo(renamedFile)) { + DisplayUtils.showSnackMessage(getActivity(), "Fail to upload taken image!"); + return; + } + + requestUploadOfFilesFromFileSystem(renamedFile.getParentFile().getAbsolutePath(), + new String[]{renamedFile.getAbsolutePath()}, + FileUploader.LOCAL_BEHAVIOUR_DELETE); + } + } + }, new String[]{fileUri.getPath()}).execute(); } else if (requestCode == REQUEST_CODE__MOVE_FILES && resultCode == RESULT_OK) { exitSelectionMode(); final Intent fData = data; diff --git a/src/main/java/com/owncloud/android/ui/activity/UploadFilesActivity.java b/src/main/java/com/owncloud/android/ui/activity/UploadFilesActivity.java index 9b28bbf227..50766642d1 100644 --- a/src/main/java/com/owncloud/android/ui/activity/UploadFilesActivity.java +++ b/src/main/java/com/owncloud/android/ui/activity/UploadFilesActivity.java @@ -499,7 +499,8 @@ public class UploadFilesActivity extends DrawerActivity implements LocalFileList // return the list of files (success) Intent data = new Intent(); - if (requestCode == FileDisplayActivity.REQUEST_CODE__UPLOAD_FROM_CAMERA) { + if (requestCode == FileDisplayActivity.REQUEST_CODE__UPLOAD_FROM_CAMERA || + requestCode == FileDisplayActivity.REQUEST_CODE__UPLOAD_SCAN_DOC_FROM_CAMERA) { data.putExtra(EXTRA_CHOSEN_FILES, new String[]{filesToUpload[0]}); setResult(RESULT_OK_AND_DELETE, data); diff --git a/src/main/java/com/owncloud/android/ui/fragment/OCFileListBottomSheetActions.java b/src/main/java/com/owncloud/android/ui/fragment/OCFileListBottomSheetActions.java index 769a4c6cca..97b3f9f327 100644 --- a/src/main/java/com/owncloud/android/ui/fragment/OCFileListBottomSheetActions.java +++ b/src/main/java/com/owncloud/android/ui/fragment/OCFileListBottomSheetActions.java @@ -62,6 +62,11 @@ public interface OCFileListBottomSheetActions { */ void directCameraUpload(); + /** + * offers scanning document upload to the current folder. + */ + void scanDocUpload(); + /** * open template selection for creator @link Creator */ diff --git a/src/main/java/com/owncloud/android/ui/fragment/OCFileListBottomSheetDialog.java b/src/main/java/com/owncloud/android/ui/fragment/OCFileListBottomSheetDialog.java index a070ac699c..84be01db91 100644 --- a/src/main/java/com/owncloud/android/ui/fragment/OCFileListBottomSheetDialog.java +++ b/src/main/java/com/owncloud/android/ui/fragment/OCFileListBottomSheetDialog.java @@ -183,6 +183,11 @@ public class OCFileListBottomSheetDialog extends BottomSheetDialog { dismiss(); }); + binding.menuScanDocUpload.setOnClickListener(v -> { + actions.scanDocUpload(); + dismiss(); + }); + binding.menuUploadFiles.setOnClickListener(v -> { actions.uploadFiles(); dismiss(); diff --git a/src/main/java/com/owncloud/android/ui/fragment/OCFileListFragment.java b/src/main/java/com/owncloud/android/ui/fragment/OCFileListFragment.java index e82810b122..917bcb9574 100644 --- a/src/main/java/com/owncloud/android/ui/fragment/OCFileListFragment.java +++ b/src/main/java/com/owncloud/android/ui/fragment/OCFileListFragment.java @@ -42,6 +42,7 @@ import android.view.View; import android.view.ViewGroup; import android.widget.AbsListView; import android.widget.PopupMenu; +import android.widget.Toast; import com.google.android.material.appbar.AppBarLayout; import com.google.android.material.behavior.HideBottomViewOnScrollBehavior; @@ -478,6 +479,21 @@ public class OCFileListFragment extends ExtendedListFragment implements } } + @Override + public void scanDocUpload() { + FileDisplayActivity fileDisplayActivity = (FileDisplayActivity) getActivity(); + + if (fileDisplayActivity != null) { + fileDisplayActivity.getFileOperationsHelper() + .scanFromCamera(fileDisplayActivity, FileDisplayActivity.REQUEST_CODE__UPLOAD_SCAN_DOC_FROM_CAMERA); + } else { + Toast.makeText(getContext(), + getString(R.string.error_starting_direct_camera_upload), + Toast.LENGTH_SHORT) + .show(); + } + } + @Override public void uploadFiles() { UploadFilesActivity.startUploadActivityForResult( diff --git a/src/main/java/com/owncloud/android/ui/helpers/FileOperationsHelper.java b/src/main/java/com/owncloud/android/ui/helpers/FileOperationsHelper.java index c59926c7fa..dda5b44447 100755 --- a/src/main/java/com/owncloud/android/ui/helpers/FileOperationsHelper.java +++ b/src/main/java/com/owncloud/android/ui/helpers/FileOperationsHelper.java @@ -37,6 +37,7 @@ import android.content.Context; import android.content.Intent; import android.content.pm.PackageManager; import android.content.pm.ResolveInfo; +import android.graphics.Bitmap; import android.net.Uri; import android.os.Build; import android.os.Environment; @@ -68,6 +69,7 @@ import com.owncloud.android.lib.resources.shares.ShareType; import com.owncloud.android.lib.resources.status.OCCapability; import com.owncloud.android.operations.SynchronizeFileOperation; import com.owncloud.android.services.OperationsService; +import com.owncloud.android.ui.activity.AppScanActivity; import com.owncloud.android.ui.activity.ConflictsResolveActivity; import com.owncloud.android.ui.activity.ExternalSiteWebView; import com.owncloud.android.ui.activity.FileActivity; @@ -84,6 +86,7 @@ import com.owncloud.android.utils.DisplayUtils; import com.owncloud.android.utils.FileStorageUtils; import com.owncloud.android.utils.PermissionUtil; import com.owncloud.android.utils.UriUtils; +import com.zynksoftware.documentscanner.ui.DocumentScanner; import org.greenrobot.eventbus.EventBus; @@ -92,7 +95,7 @@ import java.io.File; import java.io.FileInputStream; import java.io.IOException; import java.io.InputStreamReader; -import java.nio.charset.Charset; +import java.nio.charset.StandardCharsets; import java.text.SimpleDateFormat; import java.util.ArrayList; import java.util.Arrays; @@ -123,9 +126,9 @@ public class FileOperationsHelper { private static final String FILE_EXTENSION_WEBLOC = "webloc"; public static final int SINGLE_LINK_SIZE = 1; - private FileActivity fileActivity; - private CurrentAccountProvider currentAccount; - private ConnectivityService connectivityService; + private final FileActivity fileActivity; + private final CurrentAccountProvider currentAccount; + private final ConnectivityService connectivityService; /// Identifier of operation in progress which result shouldn't be lost private long mWaitingForOpId = Long.MAX_VALUE; @@ -145,7 +148,7 @@ public class FileOperationsHelper { InputStreamReader fr = null; BufferedReader br = null; try { - fr = new InputStreamReader(new FileInputStream(storagePath), Charset.forName("UTF-8")); + fr = new InputStreamReader(new FileInputStream(storagePath), StandardCharsets.UTF_8); br = new BufferedReader(fr); String line; @@ -1072,6 +1075,19 @@ public class FileOperationsHelper { } } + public void scanFromCamera(Activity activity, int requestCode) { + DocumentScanner.Configuration configuration = new DocumentScanner.Configuration(); + configuration.setImageType(Bitmap.CompressFormat.PNG); + DocumentScanner.INSTANCE.init(activity, configuration); + + Intent scanIntent = new Intent(activity, AppScanActivity.class); + if (PermissionUtil.checkSelfPermission(activity, Manifest.permission.CAMERA)) { + activity.startActivityForResult(scanIntent, requestCode); + } else { + PermissionUtil.requestCameraPermission(activity); + } + } + public static File createImageFile(Activity activity) { File storageDir = activity.getExternalFilesDir(Environment.DIRECTORY_PICTURES); diff --git a/src/main/res/drawable/ic_scan_document.xml b/src/main/res/drawable/ic_scan_document.xml new file mode 100644 index 0000000000..780fa2153f --- /dev/null +++ b/src/main/res/drawable/ic_scan_document.xml @@ -0,0 +1,13 @@ + + + diff --git a/src/main/res/layout/file_list_actions_bottom_sheet_fragment.xml b/src/main/res/layout/file_list_actions_bottom_sheet_fragment.xml index d11602e4e8..06440c2e51 100644 --- a/src/main/res/layout/file_list_actions_bottom_sheet_fragment.xml +++ b/src/main/res/layout/file_list_actions_bottom_sheet_fragment.xml @@ -125,6 +125,36 @@ + + + + + + + + android:background="@color/list_divider_background" /> Add to %1$s Upload files Upload from camera + Scan document from camera Upload content from other apps Create new folder Virus detected. Upload cannot be completed! @@ -803,6 +804,7 @@ Close Failed to load details Error starting camera + Error using document scanning source folder is read-only; file will only be uploaded kept in original folder, as it is readonly Login via QR code