diff --git a/app/src/androidTest/java/com/owncloud/android/ui/fragment/OCFileListFragmentStaticServerIT.kt b/app/src/androidTest/java/com/owncloud/android/ui/fragment/OCFileListFragmentStaticServerIT.kt index 59bf0b97f64f..60d2098fa2dd 100644 --- a/app/src/androidTest/java/com/owncloud/android/ui/fragment/OCFileListFragmentStaticServerIT.kt +++ b/app/src/androidTest/java/com/owncloud/android/ui/fragment/OCFileListFragmentStaticServerIT.kt @@ -398,13 +398,27 @@ class OCFileListFragmentStaticServerIT : AbstractIT() { testFolder.richWorkspace = " " activity.storageManager.saveFile(testFolder) - sut.adapter.swapDirectory(user, testFolder, activity.storageManager, false, "") + sut.adapter.swapDirectory( + user, + testFolder, + activity.storageManager, + false, + "" + ) { + } Assert.assertFalse(sut.adapter.shouldShowHeader()) testFolder.richWorkspace = null activity.storageManager.saveFile(testFolder) - sut.adapter.swapDirectory(user, testFolder, activity.storageManager, false, "") + sut.adapter.swapDirectory( + user, + testFolder, + activity.storageManager, + false, + "" + ) { + } Assert.assertFalse(sut.adapter.shouldShowHeader()) EspressoIdlingResource.increment() diff --git a/app/src/main/java/com/nextcloud/utils/TimeConstants.kt b/app/src/main/java/com/nextcloud/utils/NumberConstants.kt similarity index 100% rename from app/src/main/java/com/nextcloud/utils/TimeConstants.kt rename to app/src/main/java/com/nextcloud/utils/NumberConstants.kt diff --git a/app/src/main/java/com/owncloud/android/ui/activity/FileDisplayActivity.kt b/app/src/main/java/com/owncloud/android/ui/activity/FileDisplayActivity.kt index 382590f6a945..8b67b21e7fdb 100644 --- a/app/src/main/java/com/owncloud/android/ui/activity/FileDisplayActivity.kt +++ b/app/src/main/java/com/owncloud/android/ui/activity/FileDisplayActivity.kt @@ -1591,7 +1591,11 @@ class FileDisplayActivity : return } - ocFileListFragment.listDirectory(currentDir, MainApp.isOnlyOnDevice()) + ocFileListFragment.listDirectory(currentDir, MainApp.isOnlyOnDevice()) { + if (ocFileListFragment.isBrowseUp) { + ocFileListFragment.restoreIndexAndTopPosition() + } + } } private fun handleScrollBehaviour(ocFileListFragment: OCFileListFragment?) { diff --git a/app/src/main/java/com/owncloud/android/ui/adapter/CommonOCFileListAdapterInterface.kt b/app/src/main/java/com/owncloud/android/ui/adapter/CommonOCFileListAdapterInterface.kt index 94962be8a753..b62737f238ab 100644 --- a/app/src/main/java/com/owncloud/android/ui/adapter/CommonOCFileListAdapterInterface.kt +++ b/app/src/main/java/com/owncloud/android/ui/adapter/CommonOCFileListAdapterInterface.kt @@ -22,7 +22,8 @@ interface CommonOCFileListAdapterInterface { directory: OCFile, storageManager: FileDataStorageManager, onlyOnDevice: Boolean, - mLimitToMimeType: String + mLimitToMimeType: String, + onComplete: () -> Unit ) fun setHighlightedItem(file: OCFile) diff --git a/app/src/main/java/com/owncloud/android/ui/adapter/GalleryAdapter.kt b/app/src/main/java/com/owncloud/android/ui/adapter/GalleryAdapter.kt index 864e856999c5..1a577fac478d 100644 --- a/app/src/main/java/com/owncloud/android/ui/adapter/GalleryAdapter.kt +++ b/app/src/main/java/com/owncloud/android/ui/adapter/GalleryAdapter.kt @@ -387,7 +387,8 @@ class GalleryAdapter( directory: OCFile, storageManager: FileDataStorageManager, onlyOnDevice: Boolean, - mLimitToMimeType: String + mLimitToMimeType: String, + onComplete: () -> Unit ) = Unit override fun setHighlightedItem(file: OCFile) = Unit diff --git a/app/src/main/java/com/owncloud/android/ui/adapter/OCFileListAdapter.java b/app/src/main/java/com/owncloud/android/ui/adapter/OCFileListAdapter.java index 4e0c11632045..595fc5178280 100644 --- a/app/src/main/java/com/owncloud/android/ui/adapter/OCFileListAdapter.java +++ b/app/src/main/java/com/owncloud/android/ui/adapter/OCFileListAdapter.java @@ -87,6 +87,7 @@ import androidx.recyclerview.widget.RecyclerView; import kotlin.Pair; import kotlin.Unit; +import kotlin.jvm.functions.Function0; import me.zhanghai.android.fastscroll.PopupTextProvider; /** @@ -832,7 +833,8 @@ public void swapDirectory( @NonNull OCFile directory, @NonNull FileDataStorageManager updatedStorageManager, boolean onlyOnDevice, - @NonNull String limitToMimeType) { + @NonNull String limitToMimeType, + @NonNull Function0 onComplete) { this.onlyOnDevice = onlyOnDevice; @@ -861,6 +863,7 @@ public void swapDirectory( (newList, fileSortOrder) -> { updateAdapter((List) newList, directory); + onComplete.invoke(); return Unit.INSTANCE; }); } diff --git a/app/src/main/java/com/owncloud/android/ui/fragment/ExtendedListFragment.kt b/app/src/main/java/com/owncloud/android/ui/fragment/ExtendedListFragment.kt index e6adf81c5a25..5177c3934155 100644 --- a/app/src/main/java/com/owncloud/android/ui/fragment/ExtendedListFragment.kt +++ b/app/src/main/java/com/owncloud/android/ui/fragment/ExtendedListFragment.kt @@ -415,10 +415,6 @@ open class ExtendedListFragment : if (savedInstanceState.getBoolean(KEY_IS_GRID_VISIBLE, false) && recyclerView?.adapter != null) { switchToGridView() } - - val referencePosition = savedInstanceState.getInt(KEY_SAVED_LIST_POSITION) - Log_OC.v(TAG, "Setting grid position $referencePosition") - scrollToPosition(referencePosition) } override fun onSaveInstanceState(savedInstanceState: Bundle) { @@ -445,16 +441,12 @@ open class ExtendedListFragment : return mScale.roundToInt() } - /* - * Restore index and position - */ - protected fun restoreIndexAndTopPosition() { + fun restoreIndexAndTopPosition() { if (mIndexes.isEmpty()) { Log_OC.d(TAG, "Indexes is null or empty") return } - // needs to be checked; not every browse-up had a browse-down before val index = mIndexes.removeAt(mIndexes.size - 1) val firstPosition = mFirstPositions.removeAt(mFirstPositions.size - 1) val top = mTops.removeAt(mTops.size - 1) @@ -467,30 +459,41 @@ open class ExtendedListFragment : ) ) - firstPosition?.let { scrollToPosition(it) } + if (firstPosition != null && firstPosition >= 0) { + mainThread(delay = 0L) { + scrollToPosition(firstPosition, top ?: 0) + } + } } - private fun scrollToPosition(position: Int) { + private fun scrollToPosition(position: Int, top: Int = 0) { val layoutManager = mRecyclerView?.layoutManager - if (layoutManager is LinearLayoutManager) { - val visibleItemCount = layoutManager.findLastCompletelyVisibleItemPosition() - - layoutManager.findFirstCompletelyVisibleItemPosition() - layoutManager.scrollToPositionWithOffset(position, (visibleItemCount / 2) * mHeightCell) + if (position < 0) { + return + } + + when (layoutManager) { + is GridLayoutManager -> { + layoutManager.scrollToPositionWithOffset(position, top) + } + + is LinearLayoutManager -> { + val visibleItemCount = layoutManager.findLastCompletelyVisibleItemPosition() - + layoutManager.findFirstCompletelyVisibleItemPosition() + val offsetTop = if (top != 0) top else (visibleItemCount / 2) * mHeightCell + layoutManager.scrollToPositionWithOffset(position, offsetTop) + } } } - /* - * Save index and top position - */ protected fun saveIndexAndTopPosition(index: Int) { mIndexes.add(index) - val layoutManager = mRecyclerView?.layoutManager - val firstPosition: Int = if (layoutManager is GridLayoutManager) { - layoutManager.findFirstCompletelyVisibleItemPosition() - } else { - (layoutManager as LinearLayoutManager).findFirstCompletelyVisibleItemPosition() + val firstPosition: Int = when (val layoutManager = mRecyclerView?.layoutManager) { + is GridLayoutManager -> layoutManager.findFirstCompletelyVisibleItemPosition() + is LinearLayoutManager -> layoutManager.findFirstCompletelyVisibleItemPosition() + else -> RecyclerView.NO_POSITION } mFirstPositions.add(firstPosition) @@ -504,9 +507,7 @@ open class ExtendedListFragment : mHeightCell = if (view == null || mHeightCell != 0) mHeightCell else view.height } - override fun onItemClick(parent: AdapterView<*>?, view: View?, position: Int, id: Long) { - // to be @overridden - } + override fun onItemClick(parent: AdapterView<*>?, view: View?, position: Int, id: Long) = Unit override fun onRefresh() { if (searchView != null) { @@ -803,8 +804,6 @@ open class ExtendedListFragment : companion object { protected val TAG: String = ExtendedListFragment::class.java.getSimpleName() - protected const val KEY_SAVED_LIST_POSITION: String = "SAVED_LIST_POSITION" - private const val KEY_INDEXES = "INDEXES" private const val KEY_FIRST_POSITIONS = "FIRST_POSITIONS" private const val KEY_TOPS = "TOPS" diff --git a/app/src/main/java/com/owncloud/android/ui/fragment/OCFileListFragment.java b/app/src/main/java/com/owncloud/android/ui/fragment/OCFileListFragment.java index ae434dbebba3..bcd50d9f0631 100644 --- a/app/src/main/java/com/owncloud/android/ui/fragment/OCFileListFragment.java +++ b/app/src/main/java/com/owncloud/android/ui/fragment/OCFileListFragment.java @@ -80,7 +80,6 @@ import com.owncloud.android.lib.resources.e2ee.ToggleEncryptionRemoteOperation; import com.owncloud.android.lib.resources.files.SearchRemoteOperation; import com.owncloud.android.lib.resources.files.ToggleFavoriteRemoteOperation; -import com.owncloud.android.lib.resources.files.model.RemoteFile; import com.owncloud.android.lib.resources.status.E2EVersion; import com.owncloud.android.lib.resources.status.OCCapability; import com.owncloud.android.lib.resources.status.Type; @@ -148,6 +147,7 @@ import androidx.recyclerview.widget.LinearLayoutManager; import androidx.recyclerview.widget.RecyclerView; import kotlin.Unit; +import kotlin.jvm.functions.Function0; import static com.owncloud.android.datamodel.OCFile.ROOT_PATH; import static com.owncloud.android.ui.dialog.setupEncryption.SetupEncryptionDialogFragment.SETUP_ENCRYPTION_DIALOG_TAG; @@ -228,6 +228,7 @@ public class OCFileListFragment extends ExtendedListFragment implements protected String mLimitToMimeType; private FloatingActionButton mFabMain; public static boolean isMultipleFileSelectedForCopyOrMove = false; + private static boolean isBrowseUp = false; private static final Intent scanIntentExternalApp = new Intent("org.fairscan.app.action.SCAN_TO_PDF"); @@ -246,6 +247,10 @@ protected enum MenuItemAddRemove { private static OCFileDepth fileDepth = OCFileDepth.Root; + public boolean isBrowseUp() { + return isBrowseUp; + } + @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); @@ -1042,6 +1047,7 @@ public int onBrowseUp() { searchFragment = true; } + isBrowseUp = true; updateFileList(); return result.first; } @@ -1088,9 +1094,11 @@ private String ensureTrailingSeparator(String path) { } private void updateFileList() { - listDirectory(mFile, MainApp.isOnlyOnDevice()); - onRefresh(false); - restoreIndexAndTopPosition(); + listDirectory(mFile, MainApp.isOnlyOnDevice(), () -> { + Log_OC.d(TAG, "list directory completed"); + onRefresh(false); + return Unit.INSTANCE; + }); } /** @@ -1306,6 +1314,9 @@ private void browseToFolder(OCFile file, int position) { listDirectory(file, MainApp.isOnlyOnDevice()); // then, notify parent activity to let it update its state and view mContainerActivity.onBrowsedDownTo(file); + + isBrowseUp = false; + // save index and top position saveIndexAndTopPosition(position); } @@ -1551,7 +1562,15 @@ public void refreshDirectory() { } public void listDirectory(@Nullable OCFile directory, boolean onlyOnDevice) { - listDirectory(directory, null, onlyOnDevice); + listDirectory(directory, null, onlyOnDevice, () -> Unit.INSTANCE); + } + + public void listDirectory(@Nullable OCFile directory, OCFile file, boolean onlyOnDevice) { + listDirectory(directory, file, onlyOnDevice, () -> Unit.INSTANCE); + } + + public void listDirectory(@Nullable OCFile directory, boolean onlyOnDevice, @NonNull Function0 onComplete) { + listDirectory(directory, null, onlyOnDevice, onComplete); } private OCFile getDirectoryForListDirectory(@Nullable OCFile directory, FileDataStorageManager storageManager) { @@ -1578,7 +1597,10 @@ private OCFile getDirectoryForListDirectory(@Nullable OCFile directory, FileData * * @param directory File to be listed */ - public void listDirectory(@Nullable OCFile directory, OCFile file, boolean onlyOnDevice) { + public void listDirectory(@Nullable OCFile directory, + OCFile file, + boolean onlyOnDevice, + @NonNull Function0 onComplete) { if (!searchFragment) { FileDataStorageManager storageManager = mContainerActivity.getStorageManager(); if (storageManager == null) { @@ -1607,7 +1629,8 @@ public void listDirectory(@Nullable OCFile directory, OCFile file, boolean onlyO directory, storageManager, onlyOnDevice, - mLimitToMimeType); + mLimitToMimeType, + onComplete); OCFile previousDirectory = mFile; mFile = directory;