Skip to content
This repository has been archived by the owner on Jan 15, 2024. It is now read-only.

Commit

Permalink
Fixes #126: Option to Save Selected Tag Filters (#147)
Browse files Browse the repository at this point in the history
* New option in Settings to toggle filter saving

* Some English strings updated

* Improved code legibility in a few places
  • Loading branch information
bobheadxi committed Sep 6, 2017
1 parent 226295e commit 602e4f1
Show file tree
Hide file tree
Showing 8 changed files with 158 additions and 41 deletions.
Original file line number Diff line number Diff line change
@@ -1,8 +1,10 @@
package subreddit.android.appstore.screens.list;

import java.util.Collection;
import java.util.List;

import subreddit.android.appstore.backend.data.AppInfo;
import subreddit.android.appstore.backend.data.AppTags;
import subreddit.android.appstore.util.mvp.BasePresenter;
import subreddit.android.appstore.util.mvp.BaseView;

Expand All @@ -17,6 +19,10 @@ interface View extends BaseView {
void updateTagCount(TagMap tagMap);

void showError();

void restoreSelectedTags(Collection<AppTags> appTags);

Collection<AppTags> getSelectedTags();
}

interface Presenter extends BasePresenter<View> {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;

import java.util.ArrayList;
import java.util.Collection;
import java.util.List;

Expand Down Expand Up @@ -64,7 +65,7 @@ public class AppListFragment extends BasePresenterFragment<AppListContract.Prese
Unbinder unbinder;
AppListAdapter appListAdapter;
FilterListAdapter filterListAdapter;
Collection<AppTags> appTags;
Collection<AppTags> appTags = new ArrayList<>();

private BaseActivity.OnBackKeyPressedListener closeDrawerOnBackKeyListener;

Expand Down Expand Up @@ -229,10 +230,6 @@ public boolean onItemClick(View view, int position, long itemId) {
return true;
}

private boolean isTagFilterDrawerOpen() {
return drawerLayout.isDrawerOpen(GravityCompat.END);
}

private void toggleTagFilterDrawer() {
if (drawerLayout.isDrawerOpen(GravityCompat.END)) {
drawerLayout.closeDrawer(GravityCompat.END);
Expand All @@ -247,4 +244,13 @@ public void onNewFilterTags(Collection<AppTags> appTagses) {
appListAdapter.getFilter().setFilterAppTagses(appTagses);
appListAdapter.getFilter().filter(appListAdapter.getFilter().getFilterString());
}

@Override
public void restoreSelectedTags(Collection<AppTags> appTags) {
filterListAdapter.setSelectedItems(appTags);
}

public Collection<AppTags> getSelectedTags() {
return appTags;
}
}
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package subreddit.android.appstore.screens.list;

import android.content.SharedPreferences;
import android.os.Bundle;

import dagger.Module;
Expand All @@ -26,11 +27,15 @@ public CategoryFilter provideCategories() {

@Provides
@FragmentScope
public PresenterFactory<AppListContract.Presenter> providePresenterFactory(final WikiRepository wikiRepository, final CategoryFilter categoryFilter) {
public PresenterFactory<AppListContract.Presenter> providePresenterFactory(
final WikiRepository wikiRepository,
final CategoryFilter categoryFilter,
SharedPreferences preferences
) {
return new PresenterFactory<AppListContract.Presenter>() {
@Override
public AppListContract.Presenter create() {
return new AppListPresenter(wikiRepository, categoryFilter);
return new AppListPresenter(wikiRepository, categoryFilter, preferences);
}

@Override
Expand Down
Original file line number Diff line number Diff line change
@@ -1,8 +1,10 @@
package subreddit.android.appstore.screens.list;

import android.content.SharedPreferences;
import android.os.Bundle;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;
import java.util.List;
Expand All @@ -16,19 +18,22 @@
import subreddit.android.appstore.backend.data.AppTags;
import subreddit.android.appstore.backend.reddit.wiki.WikiRepository;
import subreddit.android.appstore.screens.navigation.CategoryFilter;
import subreddit.android.appstore.screens.settings.SettingsActivity;
import timber.log.Timber;


public class AppListPresenter implements AppListContract.Presenter {
final WikiRepository repository;
final CategoryFilter categoryFilter;
private SharedPreferences sharedPreferences;
private Disposable listUpdater;
private Disposable tagUpdater;
AppListContract.View view;

public AppListPresenter(WikiRepository repository, CategoryFilter categoryFilter) {
public AppListPresenter(WikiRepository repository, CategoryFilter categoryFilter, SharedPreferences preferences) {
this.repository = repository;
this.categoryFilter = categoryFilter;
this.sharedPreferences = preferences;
}

@Override
Expand Down Expand Up @@ -66,6 +71,11 @@ public void onAttachView(final AppListContract.View view) {
.subscribe(appInfos -> {
Timber.d("showAppList(%s items)", appInfos.size());
AppListPresenter.this.view.showAppList(appInfos);

if (saveTagFiltersSelected()) {
AppListPresenter.this.view.restoreSelectedTags(getSavedTagFilters());
}

});

tagUpdater = filteredData
Expand Down Expand Up @@ -93,6 +103,9 @@ public TagMap apply(Collection<AppInfo> appInfos) throws Exception {

@Override
public void onDetachView() {
if (saveTagFiltersSelected()) {
saveSelectedTags(AppListPresenter.this.view.getSelectedTags());
}
listUpdater.dispose();
tagUpdater.dispose();
view = null;
Expand All @@ -114,4 +127,34 @@ public void refreshData() {
view.showLoadingScreen();
repository.refresh();
}

private boolean saveTagFiltersSelected() {
return sharedPreferences.getBoolean(SettingsActivity.PREF_KEY_SAVE_TAG_FILTERS, false);
}

private Collection<AppTags> getSavedTagFilters() {
List<AppTags> data = Arrays.asList(AppTags.values());
Collection<AppTags> appTags = new ArrayList<>();

for (int i = 0; i < data.size(); i++) {
if (sharedPreferences.getBoolean("savedTags_" + i, false)) {
appTags.add(data.get(i));
}
}

return appTags;
}

public void saveSelectedTags(Collection<AppTags> appTags) {
List<AppTags> data = Arrays.asList(AppTags.values());
SharedPreferences.Editor editor = sharedPreferences.edit();

for (int i = 0; i < data.size(); i++) {
if (appTags.contains(data.get(i))) {
editor.putBoolean("savedTags_" + i, true);
}
}

editor.commit();
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -22,43 +22,29 @@

public class FilterListAdapter extends BaseAdapter<FilterListAdapter.ViewHolder> {
final List<AppTags> data = Arrays.asList(AppTags.values());
final SparseBooleanArray selectedItems = new SparseBooleanArray(AppTags.values().length);
final FilterListener filterListener;
private SparseBooleanArray selectedItems = new SparseBooleanArray(AppTags.values().length);;
TagMap tagMap = new TagMap();

interface FilterListener {
void onNewFilterTags(Collection<AppTags> appTagses);
}

public FilterListAdapter(final FilterListener filterListener) {
public FilterListAdapter(FilterListener filterListener) {
this.filterListener = filterListener;

setItemClickListener((view, position, itemId) -> {
//If selected tag is FREE, make sure paid is removed from selectedItems before it is added

if (data.get(position) == AppTags.FREE) {
//Find 'PAID' in selectedItems and remove it
for (int i = 0; i < selectedItems.size(); i++) {
int key = selectedItems.keyAt(i);
if (data.get(key) == AppTags.PAID) {
selectedItems.delete(key);
notifyDataSetChanged();
}
}
deselectTag(AppTags.PAID);
} else if (data.get(position) == AppTags.PAID) {
//Find 'FREE' in selectedItems and remove it
for (int i = 0; i < selectedItems.size(); i++) {
int key = selectedItems.keyAt(i);
if (data.get(key) == AppTags.FREE) {
selectedItems.delete(key);
notifyDataSetChanged();
}
}
deselectTag(AppTags.FREE);
}

selectedItems.put(position, !selectedItems.get(position));
notifyItemChanged(position);
Collection<AppTags> activeAppTagses = new ArrayList<>();
for (int i = 0; i < selectedItems.size(); i++) {
int key = selectedItems.keyAt(i);
if (selectedItems.get(key)) activeAppTagses.add(data.get(key));
}
filterListener.onNewFilterTags(activeAppTagses);

filterListener.onNewFilterTags(getActiveAppTags());
return false;
});
}
Expand Down Expand Up @@ -88,6 +74,21 @@ public int getItemCount() {
return data.size();
}

public void setSelectedItems(Collection<AppTags> appTags) {
boolean changed = false;
for (int i = 0; i < AppTags.values().length; i++) {
if (appTags.contains(data.get(i))) {
selectedItems.put(i, true);
changed = true;
}
}

if (changed) {
notifyDataSetChanged();
filterListener.onNewFilterTags(getActiveAppTags());
}
}

static class ViewHolder extends BaseViewHolder {
@BindView(R.id.tagname) TextView tagName;
@BindView(R.id.tagcount) TextView tagCount;
Expand All @@ -104,4 +105,26 @@ public void bind(AppTags item, boolean checked, int tagNumber) {
checkBox.setChecked(checked);
}
}

private void deselectTag(AppTags tag) {
for (int i = 0; i < selectedItems.size(); i++) {
int key = selectedItems.keyAt(i);
if (data.get(key) == tag) {
selectedItems.delete(key);
notifyDataSetChanged();
}
}
}

private Collection<AppTags> getActiveAppTags() {
Collection<AppTags> activeAppTagses = new ArrayList<>();

for (int i = 0; i < selectedItems.size(); i++) {
int key = selectedItems.keyAt(i);
if (selectedItems.get(key)) activeAppTagses.add(data.get(key));
}

return activeAppTagses;
}

}
Original file line number Diff line number Diff line change
@@ -1,8 +1,10 @@
package subreddit.android.appstore.screens.settings;

import android.content.Intent;
import android.content.SharedPreferences;
import android.net.Uri;
import android.os.Bundle;
import android.preference.PreferenceManager;
import android.support.customtabs.CustomTabsIntent;
import android.support.v4.content.ContextCompat;
import android.support.v7.app.AlertDialog;
Expand All @@ -15,10 +17,13 @@
import butterknife.ButterKnife;
import subreddit.android.appstore.AppStoreApp;
import subreddit.android.appstore.R;
import subreddit.android.appstore.backend.data.AppTags;
import subreddit.android.appstore.util.ui.BaseActivity;
import timber.log.Timber;

public class SettingsActivity extends BaseActivity implements View.OnClickListener {
public static final String PREF_KEY_LOAD_MEDIA = "core.data.loadmedia";
public static final String PREF_KEY_LOAD_MEDIA = "core.options.loadmedia";
public static final String PREF_KEY_SAVE_TAG_FILTERS = "core.options.savetagfilters";
protected static final String SUBMIT_APP_URL = "https://androidflair.github.io/wikiapps/";
@BindView(R.id.settings_toolbar) Toolbar mToolbar;

Expand Down Expand Up @@ -50,6 +55,7 @@ public void onCreatePreferences(Bundle savedInstanceState, String rootKey) {
findPreference("about").setOnPreferenceClickListener(this);
findPreference("submitapp").setOnPreferenceClickListener(this);
findPreference("theme").setOnPreferenceChangeListener(this);
findPreference("core.options.savetagfilters").setOnPreferenceChangeListener(this);
}

@Override
Expand All @@ -59,6 +65,14 @@ public void onViewCreated(View view, Bundle savedInstanceState) {

@Override
public boolean onPreferenceChange(Preference preference, Object o) {
if (preference.getKey().equals("core.options.savetagfilters")) {
if (!((Boolean) o)) {
deleteSavedTagFilters();
Timber.d("Save selected tags is now " + o);
}
return true;
}

new AlertDialog.Builder(getActivity())
.setMessage(R.string.restart)
.setNegativeButton(R.string.later, null)
Expand All @@ -84,6 +98,18 @@ else if (preference.getKey().equals("submitapp")) {
return true;
}

private void deleteSavedTagFilters() {
SharedPreferences prefs =
PreferenceManager.getDefaultSharedPreferences(getContext());
SharedPreferences.Editor editor = prefs.edit();

editor.remove("savedTags_size");
for(int i = 0; i < AppTags.values().length; i++) {
editor.remove("savedTags_" + i);
}

editor.commit();
}

}
}
8 changes: 5 additions & 3 deletions app/src/main/res/values/strings.xml
Original file line number Diff line number Diff line change
Expand Up @@ -30,10 +30,12 @@
<string name="app_category_new">New</string>
<string name="view_update">View</string>
<string name="error">Error fetching repository</string>
<string name="data_options">Data options</string>
<string name="options">Options</string>
<string name="screenshots">Screenshots</string>
<string name="data_option_loadmedia_title"><![CDATA[Icons & screenshots]]></string>
<string name="data_option_loadmedia_summary">Load app icons and screenshots</string>
<string name="options_loadmedia_title"><![CDATA[Icons & screenshots]]></string>
<string name="options_loadmedia_summary">Load app icons and screenshots</string>
<string name="options_savetagfilters_title">Save selected Tag filters</string>
<string name="options_savetagfilters_summary">Filter by the same selected Tags every time</string>
<string name="update">Update available</string>
<string name="update_error">Error checking for updates</string>
<string name="update_confirm">Update</string>
Expand Down
14 changes: 10 additions & 4 deletions app/src/main/res/xml/preferences.xml
Original file line number Diff line number Diff line change
Expand Up @@ -11,13 +11,19 @@
android:key="theme"/>
</android.support.v7.preference.PreferenceCategory>
<android.support.v7.preference.PreferenceCategory
android:title="@string/data_options">
android:title="@string/options">
<android.support.v7.preference.CheckBoxPreference
android:key="core.data.loadmedia"
android:title="@string/data_option_loadmedia_title"
android:key="core.options.loadmedia"
android:title="@string/options_loadmedia_title"
android:checked="true"
android:defaultValue="true"
android:summary="@string/data_option_loadmedia_summary"/>
android:summary="@string/options_loadmedia_summary"/>
<android.support.v7.preference.CheckBoxPreference
android:key="core.options.savetagfilters"
android:title="@string/options_savetagfilters_title"
android:checked="false"
android:defaultValue="false"
android:summary="@string/options_savetagfilters_summary"/>
</android.support.v7.preference.PreferenceCategory>
<android.support.v7.preference.PreferenceCategory
android:title="@string/more" >
Expand Down

0 comments on commit 602e4f1

Please sign in to comment.