[Android] [PATCH v2] Keep search filter on screen rotation
Romain Vimont
rom1v at videolabs.io
Thu Apr 12 11:00:29 CEST 2018
Save and restore the search query state along with the activity.
Fixes #404
---
Changes from v1:
- store the saved query in the view model
- apply the filter on restore (in case the view model has been recreated)
- filter only if the query changes (so that it does nothing on restore if the
view model was kept)
- move the "ignore small query check" to the view model, to prevent
unnecessary restore when the query changes but still have less than 3
chars
.../org/videolan/vlc/gui/ContentActivity.java | 42 ++++++++++++++++++-
.../org/videolan/vlc/util/FilterDelegate.kt | 4 ++
.../org/videolan/vlc/viewmodels/BaseModel.kt | 15 ++++---
3 files changed, 54 insertions(+), 7 deletions(-)
diff --git a/vlc-android/src/org/videolan/vlc/gui/ContentActivity.java b/vlc-android/src/org/videolan/vlc/gui/ContentActivity.java
index 2da5bca3b..c577b72e1 100644
--- a/vlc-android/src/org/videolan/vlc/gui/ContentActivity.java
+++ b/vlc-android/src/org/videolan/vlc/gui/ContentActivity.java
@@ -48,6 +48,7 @@ import org.videolan.vlc.gui.video.VideoGridFragment;
import org.videolan.vlc.interfaces.Filterable;
import org.videolan.vlc.util.AndroidDevices;
import org.videolan.vlc.util.Util;
+import org.videolan.vlc.viewmodels.BaseModel;
import java.util.List;
@@ -55,9 +56,37 @@ import java.util.List;
public class ContentActivity extends AudioPlayerContainerActivity implements SearchView.OnQueryTextListener, MenuItem.OnActionExpandListener {
public static final String TAG = "VLC/ContentActivity";
+ private static final String KEY_SEARCH_QUERY = "org.videolan.vlc.SEARCH_QUERY";
+
private SearchView mSearchView;
private boolean showRenderers = !AndroidDevices.isChromeBook && !Util.isListEmpty(RendererDelegate.INSTANCE.getRenderers().getValue());
+ @Override
+ protected void onSaveInstanceState(Bundle outState) {
+ super.onSaveInstanceState(outState);
+ if (mSearchView != null) {
+ outState.putString(KEY_SEARCH_QUERY, mSearchView.getQuery().toString());
+ }
+ }
+
+ @Override
+ protected void onRestoreInstanceState(Bundle savedInstanceState) {
+ super.onRestoreInstanceState(savedInstanceState);
+ String query = savedInstanceState.getString(KEY_SEARCH_QUERY);
+ BaseModel<?> viewModel = getViewModel();
+ if (viewModel != null) {
+ viewModel.filter(query);
+ }
+ }
+
+ protected BaseModel<?> getViewModel() {
+ Fragment fragment = getCurrentFragment();
+ if (fragment instanceof MediaBrowserFragment) {
+ return ((MediaBrowserFragment)fragment).getProvider();
+ }
+ return null;
+ }
+
@Override
protected void initAudioPlayerContainerActivity() {
super.initAudioPlayerContainerActivity();
@@ -101,6 +130,16 @@ public class ContentActivity extends AudioPlayerContainerActivity implements Sea
final MenuItem searchItem = menu.findItem(R.id.ml_menu_filter);
mSearchView = (SearchView) searchItem.getActionView();
mSearchView.setQueryHint(getString(R.string.search_list_hint));
+ BaseModel<?> viewModel = getViewModel();
+ if (viewModel != null) {
+ // restore the current filter text, if any
+ String filterQuery = viewModel.getFilterQuery();
+ if (filterQuery != null) {
+ searchItem.expandActionView();
+ mSearchView.setQuery(filterQuery, false);
+ setSearchVisibility(true);
+ }
+ }
mSearchView.setOnQueryTextListener(this);
searchItem.setOnActionExpandListener(this);
}
@@ -141,8 +180,7 @@ public class ContentActivity extends AudioPlayerContainerActivity implements Sea
public boolean onQueryTextChange(String filterQueryString) {
final Fragment current = getCurrentFragment();
if (current instanceof Filterable) {
- if (filterQueryString.length() < 3) ((Filterable) current).restoreList();
- else ((Filterable) current).filter(filterQueryString);
+ ((Filterable) current).filter(filterQueryString);
return true;
}
return false;
diff --git a/vlc-android/src/org/videolan/vlc/util/FilterDelegate.kt b/vlc-android/src/org/videolan/vlc/util/FilterDelegate.kt
index c1778a305..d234e772f 100644
--- a/vlc-android/src/org/videolan/vlc/util/FilterDelegate.kt
+++ b/vlc-android/src/org/videolan/vlc/util/FilterDelegate.kt
@@ -43,6 +43,10 @@ open class FilterDelegate<T : MediaLibraryItem>(protected val dataset: MutableLi
}
}
}
+
+ companion object {
+ fun getEffectiveFilter(query: String?) = if (query?.length ?: 0 > 2) query else null
+ }
}
class PlaylistFilterDelegate(dataset: MutableLiveData<out List<MediaWrapper>>) : FilterDelegate<MediaWrapper>(dataset) {
diff --git a/vlc-android/src/org/videolan/vlc/viewmodels/BaseModel.kt b/vlc-android/src/org/videolan/vlc/viewmodels/BaseModel.kt
index d93c862d9..533205b3b 100644
--- a/vlc-android/src/org/videolan/vlc/viewmodels/BaseModel.kt
+++ b/vlc-android/src/org/videolan/vlc/viewmodels/BaseModel.kt
@@ -38,7 +38,8 @@ abstract class BaseModel<T : MediaLibraryItem> : ViewModel(), RefreshModel {
var sort = Medialibrary.SORT_ALPHA
var desc = false
- private var filtering = false
+ var filterQuery: String? = null
+ private set
protected open val sortKey = this.javaClass.simpleName!!
open fun canSortByName() = true
@@ -105,13 +106,17 @@ abstract class BaseModel<T : MediaLibraryItem> : ViewModel(), RefreshModel {
fun remove(mw: T) = updateActor.offer(Remove(mw))
fun filter(query: String?) {
- filtering = true
- updateActor.offer(Filter(query))
+ var effectiveFilter = FilterDelegate.getEffectiveFilter(query)
+ if (effectiveFilter != FilterDelegate.getEffectiveFilter(filterQuery))
+ updateActor.offer(Filter(effectiveFilter))
+ filterQuery = query
}
fun restore() {
- if (filtering) updateActor.offer(Filter(null))
- filtering = false
+ if (filterQuery != null) {
+ updateActor.offer(Filter(null))
+ filterQuery = null
+ }
}
protected open fun removeMedia(media: T) = dataset.remove(media)
--
2.17.0
More information about the Android
mailing list