aboutsummaryrefslogtreecommitdiff
path: root/app/src/main/java/ml/docilealligator/infinityforreddit
diff options
context:
space:
mode:
authorDocile-Alligator <25734209+Docile-Alligator@users.noreply.github.com>2024-04-24 02:38:12 +0000
committerDocile-Alligator <25734209+Docile-Alligator@users.noreply.github.com>2024-04-24 02:38:12 +0000
commit1bd50ef7651f8455e8703e2cd08bc4a315bed28b (patch)
tree13aedca7d8c1cb7cc03fc59405e193d68eae18e8 /app/src/main/java/ml/docilealligator/infinityforreddit
parentb598da636053154670642ec326b104c9a11914d2 (diff)
downloadinfinity-for-reddit-1bd50ef7651f8455e8703e2cd08bc4a315bed28b.tar
infinity-for-reddit-1bd50ef7651f8455e8703e2cd08bc4a315bed28b.tar.gz
infinity-for-reddit-1bd50ef7651f8455e8703e2cd08bc4a315bed28b.tar.bz2
infinity-for-reddit-1bd50ef7651f8455e8703e2cd08bc4a315bed28b.tar.lz
infinity-for-reddit-1bd50ef7651f8455e8703e2cd08bc4a315bed28b.tar.xz
infinity-for-reddit-1bd50ef7651f8455e8703e2cd08bc4a315bed28b.tar.zst
infinity-for-reddit-1bd50ef7651f8455e8703e2cd08bc4a315bed28b.zip
Show online themes from local server.
Diffstat (limited to 'app/src/main/java/ml/docilealligator/infinityforreddit')
-rw-r--r--app/src/main/java/ml/docilealligator/infinityforreddit/NetworkModule.java9
-rw-r--r--app/src/main/java/ml/docilealligator/infinityforreddit/activities/CustomThemeListingActivity.java3
-rw-r--r--app/src/main/java/ml/docilealligator/infinityforreddit/adapters/CustomThemeListingRecyclerViewAdapter.java2
-rw-r--r--app/src/main/java/ml/docilealligator/infinityforreddit/adapters/OnlineCustomThemeListingRecyclerViewAdapter.java121
-rw-r--r--app/src/main/java/ml/docilealligator/infinityforreddit/adapters/PostRecyclerViewAdapter.java2
-rw-r--r--app/src/main/java/ml/docilealligator/infinityforreddit/apis/OnlineCustomThemeAPI.java12
-rw-r--r--app/src/main/java/ml/docilealligator/infinityforreddit/customtheme/CustomThemeViewModel.java56
-rw-r--r--app/src/main/java/ml/docilealligator/infinityforreddit/customtheme/LocalCustomThemeRepository.java (renamed from app/src/main/java/ml/docilealligator/infinityforreddit/customtheme/CustomThemeRepository.java)4
-rw-r--r--app/src/main/java/ml/docilealligator/infinityforreddit/customtheme/OnlineCustomThemeFilter.java4
-rw-r--r--app/src/main/java/ml/docilealligator/infinityforreddit/customtheme/OnlineCustomThemePagingSource.java86
-rw-r--r--app/src/main/java/ml/docilealligator/infinityforreddit/customtheme/OnlineCustomThemeRepository.java40
-rw-r--r--app/src/main/java/ml/docilealligator/infinityforreddit/fragments/CustomThemeListingFragment.java38
-rw-r--r--app/src/main/java/ml/docilealligator/infinityforreddit/utils/JSONUtils.java1
13 files changed, 353 insertions, 25 deletions
diff --git a/app/src/main/java/ml/docilealligator/infinityforreddit/NetworkModule.java b/app/src/main/java/ml/docilealligator/infinityforreddit/NetworkModule.java
index 2c231682..7bbc2443 100644
--- a/app/src/main/java/ml/docilealligator/infinityforreddit/NetworkModule.java
+++ b/app/src/main/java/ml/docilealligator/infinityforreddit/NetworkModule.java
@@ -192,6 +192,15 @@ abstract class NetworkModule {
}
@Provides
+ @Named("online_custom_themes")
+ @Singleton
+ static Retrofit provideOnlineCustomThemesRetrofit(@Named("base") Retrofit retrofit) {
+ return retrofit.newBuilder()
+ .baseUrl(APIUtils.ONLINE_CUSTOM_THEMES_API_BASE_URI)
+ .build();
+ }
+
+ @Provides
@Singleton
static StreamableAPI provideStreamableApi(@Named("streamable") Retrofit streamableRetrofit) {
return streamableRetrofit.create(StreamableAPI.class);
diff --git a/app/src/main/java/ml/docilealligator/infinityforreddit/activities/CustomThemeListingActivity.java b/app/src/main/java/ml/docilealligator/infinityforreddit/activities/CustomThemeListingActivity.java
index f2421ac6..9ddbeffb 100644
--- a/app/src/main/java/ml/docilealligator/infinityforreddit/activities/CustomThemeListingActivity.java
+++ b/app/src/main/java/ml/docilealligator/infinityforreddit/activities/CustomThemeListingActivity.java
@@ -366,6 +366,9 @@ public class CustomThemeListingActivity extends BaseActivity implements
return fragment;
}
CustomThemeListingFragment fragment = new CustomThemeListingFragment();
+ Bundle bundle = new Bundle();
+ bundle.putBoolean(CustomThemeListingFragment.EXTRA_IS_ONLINE, true);
+ fragment.setArguments(bundle);
return fragment;
}
diff --git a/app/src/main/java/ml/docilealligator/infinityforreddit/adapters/CustomThemeListingRecyclerViewAdapter.java b/app/src/main/java/ml/docilealligator/infinityforreddit/adapters/CustomThemeListingRecyclerViewAdapter.java
index e0f460a3..cee53dd6 100644
--- a/app/src/main/java/ml/docilealligator/infinityforreddit/adapters/CustomThemeListingRecyclerViewAdapter.java
+++ b/app/src/main/java/ml/docilealligator/infinityforreddit/adapters/CustomThemeListingRecyclerViewAdapter.java
@@ -74,7 +74,7 @@ public class CustomThemeListingRecyclerViewAdapter extends RecyclerView.Adapter<
CustomTheme customTheme = predefinedCustomThemes.get(position - 1);
((PredefinedCustomThemeViewHolder) holder).colorPrimaryView.setBackgroundTintList(ColorStateList.valueOf(customTheme.colorPrimary));
((PredefinedCustomThemeViewHolder) holder).nameTextView.setText(customTheme.name);
- ((PredefinedCustomThemeViewHolder) holder).itemView.setOnClickListener(view -> {
+ holder.itemView.setOnClickListener(view -> {
Intent intent = new Intent(activity, CustomizeThemeActivity.class);
intent.putExtra(CustomizeThemeActivity.EXTRA_THEME_NAME, customTheme.name);
intent.putExtra(CustomizeThemeActivity.EXTRA_IS_PREDEFIINED_THEME, true);
diff --git a/app/src/main/java/ml/docilealligator/infinityforreddit/adapters/OnlineCustomThemeListingRecyclerViewAdapter.java b/app/src/main/java/ml/docilealligator/infinityforreddit/adapters/OnlineCustomThemeListingRecyclerViewAdapter.java
new file mode 100644
index 00000000..038d26ca
--- /dev/null
+++ b/app/src/main/java/ml/docilealligator/infinityforreddit/adapters/OnlineCustomThemeListingRecyclerViewAdapter.java
@@ -0,0 +1,121 @@
+package ml.docilealligator.infinityforreddit.adapters;
+
+import android.content.Intent;
+import android.content.res.ColorStateList;
+import android.os.Bundle;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.ImageView;
+import android.widget.TextView;
+
+import androidx.annotation.NonNull;
+import androidx.paging.PagingDataAdapter;
+import androidx.recyclerview.widget.DiffUtil;
+import androidx.recyclerview.widget.RecyclerView;
+
+import butterknife.BindView;
+import butterknife.ButterKnife;
+import ml.docilealligator.infinityforreddit.R;
+import ml.docilealligator.infinityforreddit.activities.BaseActivity;
+import ml.docilealligator.infinityforreddit.activities.CustomThemeListingActivity;
+import ml.docilealligator.infinityforreddit.activities.CustomizeThemeActivity;
+import ml.docilealligator.infinityforreddit.bottomsheetfragments.CustomThemeOptionsBottomSheetFragment;
+import ml.docilealligator.infinityforreddit.customtheme.CustomTheme;
+
+public class OnlineCustomThemeListingRecyclerViewAdapter extends PagingDataAdapter<CustomTheme, RecyclerView.ViewHolder> {
+ private static final int VIEW_TYPE_USER_THEME = 1;
+ private static final int VIEW_TYPE_USER_THEME_DIVIDER = 2;
+
+ private final BaseActivity activity;
+
+ public OnlineCustomThemeListingRecyclerViewAdapter(BaseActivity activity) {
+ super(new DiffUtil.ItemCallback<>() {
+ @Override
+ public boolean areItemsTheSame(@NonNull CustomTheme oldItem, @NonNull CustomTheme newItem) {
+ return oldItem.name.equals(newItem.name);
+ }
+
+ @Override
+ public boolean areContentsTheSame(@NonNull CustomTheme oldItem, @NonNull CustomTheme newItem) {
+ return false;
+ }
+ });
+ this.activity = activity;
+ }
+
+ @Override
+ public int getItemViewType(int position) {
+ return VIEW_TYPE_USER_THEME;
+ }
+
+ @NonNull
+ @Override
+ public RecyclerView.ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
+ switch (viewType) {
+ case VIEW_TYPE_USER_THEME_DIVIDER:
+ return new OnlineCustomThemeDividerViewHolder(LayoutInflater.from(parent.getContext()).inflate(R.layout.item_theme_type_divider, parent, false));
+ default:
+ return new OnlineCustomThemeViewHolder(LayoutInflater.from(parent.getContext()).inflate(R.layout.item_user_custom_theme, parent, false));
+ }
+ }
+
+ @Override
+ public void onBindViewHolder(@NonNull RecyclerView.ViewHolder holder, int position) {
+ if (holder instanceof OnlineCustomThemeViewHolder) {
+ CustomTheme customTheme = getItem(position);
+ ((OnlineCustomThemeViewHolder) holder).colorPrimaryView.setBackgroundTintList(ColorStateList.valueOf(customTheme.colorPrimary));
+ ((OnlineCustomThemeViewHolder) holder).nameTextView.setText(customTheme.name);
+ ((OnlineCustomThemeViewHolder) holder).createThemeImageView.setOnClickListener(view -> {
+ Intent intent = new Intent(activity, CustomizeThemeActivity.class);
+ intent.putExtra(CustomizeThemeActivity.EXTRA_THEME_NAME, customTheme.name);
+ intent.putExtra(CustomizeThemeActivity.EXTRA_CREATE_THEME, true);
+ activity.startActivity(intent);
+ });
+ ((OnlineCustomThemeViewHolder) holder).shareImageView.setOnClickListener(view -> {
+ ((CustomThemeListingActivity) activity).shareTheme(customTheme);
+ });
+ holder.itemView.setOnClickListener(view -> {
+ CustomThemeOptionsBottomSheetFragment customThemeOptionsBottomSheetFragment = new CustomThemeOptionsBottomSheetFragment();
+ Bundle bundle = new Bundle();
+ bundle.putString(CustomThemeOptionsBottomSheetFragment.EXTRA_THEME_NAME, customTheme.name);
+ customThemeOptionsBottomSheetFragment.setArguments(bundle);
+ customThemeOptionsBottomSheetFragment.show(activity.getSupportFragmentManager(), customThemeOptionsBottomSheetFragment.getTag());
+ });
+ holder.itemView.setOnLongClickListener(view -> {
+ holder.itemView.performClick();
+ return true;
+ });
+ }
+ }
+
+ class OnlineCustomThemeViewHolder extends RecyclerView.ViewHolder {
+
+ @BindView(R.id.color_primary_item_user_custom_theme)
+ View colorPrimaryView;
+ @BindView(R.id.name_text_view_item_user_custom_theme)
+ TextView nameTextView;
+ @BindView(R.id.add_image_view_item_user_custom_theme)
+ ImageView createThemeImageView;
+ @BindView(R.id.share_image_view_item_user_custom_theme)
+ ImageView shareImageView;
+
+ OnlineCustomThemeViewHolder(@NonNull View itemView) {
+ super(itemView);
+ ButterKnife.bind(this, itemView);
+ if (activity.typeface != null) {
+ nameTextView.setTypeface(activity.typeface);
+ }
+ }
+ }
+
+ class OnlineCustomThemeDividerViewHolder extends RecyclerView.ViewHolder {
+
+ OnlineCustomThemeDividerViewHolder(@NonNull View itemView) {
+ super(itemView);
+ if (activity.typeface != null) {
+ ((TextView) itemView).setTypeface(activity.typeface);
+ }
+ }
+ }
+}
diff --git a/app/src/main/java/ml/docilealligator/infinityforreddit/adapters/PostRecyclerViewAdapter.java b/app/src/main/java/ml/docilealligator/infinityforreddit/adapters/PostRecyclerViewAdapter.java
index 14859bba..40b263da 100644
--- a/app/src/main/java/ml/docilealligator/infinityforreddit/adapters/PostRecyclerViewAdapter.java
+++ b/app/src/main/java/ml/docilealligator/infinityforreddit/adapters/PostRecyclerViewAdapter.java
@@ -147,7 +147,7 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
private static final int VIEW_TYPE_POST_CARD_3_GALLERY_TYPE = 14;
private static final int VIEW_TYPE_POST_CARD_3_TEXT_TYPE = 15;
- private static final DiffUtil.ItemCallback<Post> DIFF_CALLBACK = new DiffUtil.ItemCallback<Post>() {
+ private static final DiffUtil.ItemCallback<Post> DIFF_CALLBACK = new DiffUtil.ItemCallback<>() {
@Override
public boolean areItemsTheSame(@NonNull Post post, @NonNull Post t1) {
return post.getId().equals(t1.getId());
diff --git a/app/src/main/java/ml/docilealligator/infinityforreddit/apis/OnlineCustomThemeAPI.java b/app/src/main/java/ml/docilealligator/infinityforreddit/apis/OnlineCustomThemeAPI.java
new file mode 100644
index 00000000..de2e46e2
--- /dev/null
+++ b/app/src/main/java/ml/docilealligator/infinityforreddit/apis/OnlineCustomThemeAPI.java
@@ -0,0 +1,12 @@
+package ml.docilealligator.infinityforreddit.apis;
+
+import com.google.common.util.concurrent.ListenableFuture;
+
+import retrofit2.Response;
+import retrofit2.http.GET;
+import retrofit2.http.Query;
+
+public interface OnlineCustomThemeAPI {
+ @GET("/themes/")
+ ListenableFuture<Response<String>> getCustomThemesListenableFuture(@Query("page") String page);
+}
diff --git a/app/src/main/java/ml/docilealligator/infinityforreddit/customtheme/CustomThemeViewModel.java b/app/src/main/java/ml/docilealligator/infinityforreddit/customtheme/CustomThemeViewModel.java
index c8a6f930..b953cee2 100644
--- a/app/src/main/java/ml/docilealligator/infinityforreddit/customtheme/CustomThemeViewModel.java
+++ b/app/src/main/java/ml/docilealligator/infinityforreddit/customtheme/CustomThemeViewModel.java
@@ -1,55 +1,83 @@
package ml.docilealligator.infinityforreddit.customtheme;
import androidx.annotation.NonNull;
+import androidx.annotation.Nullable;
import androidx.lifecycle.LiveData;
import androidx.lifecycle.ViewModel;
+import androidx.lifecycle.ViewModelKt;
import androidx.lifecycle.ViewModelProvider;
+import androidx.paging.PagingData;
import java.util.List;
+import java.util.concurrent.Executor;
import ml.docilealligator.infinityforreddit.RedditDataRoomDatabase;
+import retrofit2.Retrofit;
public class CustomThemeViewModel extends ViewModel {
- private final LiveData<List<CustomTheme>> mAllCustomThemes;
- private final LiveData<CustomTheme> mCurrentLightTheme;
- private final LiveData<CustomTheme> mCurrentDarkTheme;
- private final LiveData<CustomTheme> mCurrentAmoledTheme;
+ @Nullable
+ private LocalCustomThemeRepository localCustomThemeRepository;
+ @Nullable
+ private OnlineCustomThemeRepository onlineCustomThemeRepository;
public CustomThemeViewModel(RedditDataRoomDatabase redditDataRoomDatabase) {
- CustomThemeRepository customThemeRepository = new CustomThemeRepository(redditDataRoomDatabase);
- mAllCustomThemes = customThemeRepository.getAllCustomThemes();
- mCurrentLightTheme = customThemeRepository.getCurrentLightCustomTheme();
- mCurrentDarkTheme = customThemeRepository.getCurrentDarkCustomTheme();
- mCurrentAmoledTheme = customThemeRepository.getCurrentAmoledCustomTheme();
+ localCustomThemeRepository = new LocalCustomThemeRepository(redditDataRoomDatabase);
}
+ public CustomThemeViewModel(Executor executor, Retrofit retrofit,
+ RedditDataRoomDatabase redditDataRoomDatabase) {
+ onlineCustomThemeRepository = new OnlineCustomThemeRepository(executor, retrofit, redditDataRoomDatabase,
+ ViewModelKt.getViewModelScope(this));
+ }
+
+ @Nullable
public LiveData<List<CustomTheme>> getAllCustomThemes() {
- return mAllCustomThemes;
+ return localCustomThemeRepository.getAllCustomThemes();
}
public LiveData<CustomTheme> getCurrentLightThemeLiveData() {
- return mCurrentLightTheme;
+ return localCustomThemeRepository.getCurrentLightCustomTheme();
}
public LiveData<CustomTheme> getCurrentDarkThemeLiveData() {
- return mCurrentDarkTheme;
+ return localCustomThemeRepository.getCurrentDarkCustomTheme();
}
+ @Nullable
public LiveData<CustomTheme> getCurrentAmoledThemeLiveData() {
- return mCurrentAmoledTheme;
+ return localCustomThemeRepository.getCurrentAmoledCustomTheme();
+ }
+
+ public LiveData<PagingData<CustomTheme>> getOnlineCustomThemes() {
+ return onlineCustomThemeRepository.getOnlineCustomThemes();
}
public static class Factory extends ViewModelProvider.NewInstanceFactory {
+ private Executor executor;
+ private Retrofit retrofit;
private final RedditDataRoomDatabase mRedditDataRoomDatabase;
+ private final boolean isOnline;
public Factory(RedditDataRoomDatabase redditDataRoomDatabase) {
mRedditDataRoomDatabase = redditDataRoomDatabase;
+ isOnline = false;
+ }
+
+ public Factory(Executor executor, Retrofit retrofit, RedditDataRoomDatabase redditDataRoomDatabase) {
+ this.executor = executor;
+ this.retrofit = retrofit;
+ mRedditDataRoomDatabase = redditDataRoomDatabase;
+ isOnline = true;
}
@NonNull
@Override
public <T extends ViewModel> T create(@NonNull Class<T> modelClass) {
- return (T) new CustomThemeViewModel(mRedditDataRoomDatabase);
+ if (isOnline) {
+ return (T) new CustomThemeViewModel(executor, retrofit, mRedditDataRoomDatabase);
+ } else {
+ return (T) new CustomThemeViewModel(mRedditDataRoomDatabase);
+ }
}
}
}
diff --git a/app/src/main/java/ml/docilealligator/infinityforreddit/customtheme/CustomThemeRepository.java b/app/src/main/java/ml/docilealligator/infinityforreddit/customtheme/LocalCustomThemeRepository.java
index 9cee3de9..3a610ec9 100644
--- a/app/src/main/java/ml/docilealligator/infinityforreddit/customtheme/CustomThemeRepository.java
+++ b/app/src/main/java/ml/docilealligator/infinityforreddit/customtheme/LocalCustomThemeRepository.java
@@ -6,13 +6,13 @@ import java.util.List;
import ml.docilealligator.infinityforreddit.RedditDataRoomDatabase;
-public class CustomThemeRepository {
+public class LocalCustomThemeRepository {
private final LiveData<List<CustomTheme>> mAllCustomThemes;
private final LiveData<CustomTheme> mCurrentLightCustomTheme;
private final LiveData<CustomTheme> mCurrentDarkCustomTheme;
private final LiveData<CustomTheme> mCurrentAmoledCustomTheme;
- CustomThemeRepository(RedditDataRoomDatabase redditDataRoomDatabase) {
+ LocalCustomThemeRepository(RedditDataRoomDatabase redditDataRoomDatabase) {
mAllCustomThemes = redditDataRoomDatabase.customThemeDao().getAllCustomThemes();
mCurrentLightCustomTheme = redditDataRoomDatabase.customThemeDao().getLightCustomThemeLiveData();
mCurrentDarkCustomTheme = redditDataRoomDatabase.customThemeDao().getDarkCustomThemeLiveData();
diff --git a/app/src/main/java/ml/docilealligator/infinityforreddit/customtheme/OnlineCustomThemeFilter.java b/app/src/main/java/ml/docilealligator/infinityforreddit/customtheme/OnlineCustomThemeFilter.java
new file mode 100644
index 00000000..f44aaf6d
--- /dev/null
+++ b/app/src/main/java/ml/docilealligator/infinityforreddit/customtheme/OnlineCustomThemeFilter.java
@@ -0,0 +1,4 @@
+package ml.docilealligator.infinityforreddit.customtheme;
+
+public class OnlineCustomThemeFilter {
+}
diff --git a/app/src/main/java/ml/docilealligator/infinityforreddit/customtheme/OnlineCustomThemePagingSource.java b/app/src/main/java/ml/docilealligator/infinityforreddit/customtheme/OnlineCustomThemePagingSource.java
new file mode 100644
index 00000000..5bcfd175
--- /dev/null
+++ b/app/src/main/java/ml/docilealligator/infinityforreddit/customtheme/OnlineCustomThemePagingSource.java
@@ -0,0 +1,86 @@
+package ml.docilealligator.infinityforreddit.customtheme;
+
+import androidx.annotation.NonNull;
+import androidx.annotation.Nullable;
+import androidx.paging.ListenableFuturePagingSource;
+import androidx.paging.PagingState;
+
+import com.google.common.util.concurrent.Futures;
+import com.google.common.util.concurrent.ListenableFuture;
+
+import org.json.JSONArray;
+import org.json.JSONException;
+import org.json.JSONObject;
+
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.concurrent.Executor;
+
+import ml.docilealligator.infinityforreddit.RedditDataRoomDatabase;
+import ml.docilealligator.infinityforreddit.apis.OnlineCustomThemeAPI;
+import ml.docilealligator.infinityforreddit.utils.JSONUtils;
+import retrofit2.HttpException;
+import retrofit2.Response;
+import retrofit2.Retrofit;
+
+public class OnlineCustomThemePagingSource extends ListenableFuturePagingSource<String, CustomTheme> {
+ private final Executor executor;
+ private final OnlineCustomThemeAPI api;
+ private final RedditDataRoomDatabase redditDataRoomDatabase;
+
+ public OnlineCustomThemePagingSource(Executor executor, Retrofit onlineCustomThemesRetrofit, RedditDataRoomDatabase redditDataRoomDatabase) {
+ this.executor = executor;
+ this.redditDataRoomDatabase = redditDataRoomDatabase;
+ api = onlineCustomThemesRetrofit.create(OnlineCustomThemeAPI.class);
+ }
+
+ @Nullable
+ @Override
+ public String getRefreshKey(@NonNull PagingState<String, CustomTheme> pagingState) {
+ return null;
+ }
+
+ @NonNull
+ @Override
+ public ListenableFuture<LoadResult<String, CustomTheme>> loadFuture(@NonNull LoadParams<String> loadParams) {
+ ListenableFuture<Response<String>> customThemes;
+ customThemes = api.getCustomThemesListenableFuture(loadParams.getKey());
+
+ ListenableFuture<LoadResult<String, CustomTheme>> pageFuture = Futures.transform(customThemes, this::transformData, executor);
+
+ ListenableFuture<LoadResult<String, CustomTheme>> partialLoadResultFuture =
+ Futures.catching(pageFuture, HttpException.class,
+ LoadResult.Error::new, executor);
+
+ return Futures.catching(partialLoadResultFuture,
+ IOException.class, LoadResult.Error::new, executor);
+ }
+
+ public LoadResult<String, CustomTheme> transformData(Response<String> response) {
+ if (response.isSuccessful()) {
+ List<CustomTheme> themes = new ArrayList<>();
+ try {
+ String responseString = response.body();
+ JSONObject data = new JSONObject(responseString);
+ int page = data.getInt(JSONUtils.PAGE_KEY);
+ JSONArray themesArray = data.getJSONArray(JSONUtils.DATA_KEY);
+ for (int i = 0; i < themesArray.length(); i++) {
+ try {
+ themes.add(CustomTheme.fromJson(themesArray.getJSONObject(i).getString(JSONUtils.DATA_KEY)));
+ } catch (JSONException ignore) {}
+ }
+
+ if (themes.isEmpty()) {
+ return new LoadResult.Page<>(themes, null, null);
+ } else {
+ return new LoadResult.Page<>(themes, null, Integer.toString(page + 1));
+ }
+ } catch (JSONException e) {
+ return new LoadResult.Error<>(new Exception("Response failed"));
+ }
+ } else {
+ return new LoadResult.Error<>(new Exception("Response failed"));
+ }
+ }
+}
diff --git a/app/src/main/java/ml/docilealligator/infinityforreddit/customtheme/OnlineCustomThemeRepository.java b/app/src/main/java/ml/docilealligator/infinityforreddit/customtheme/OnlineCustomThemeRepository.java
new file mode 100644
index 00000000..7a978e7a
--- /dev/null
+++ b/app/src/main/java/ml/docilealligator/infinityforreddit/customtheme/OnlineCustomThemeRepository.java
@@ -0,0 +1,40 @@
+package ml.docilealligator.infinityforreddit.customtheme;
+
+import androidx.lifecycle.LiveData;
+import androidx.lifecycle.MutableLiveData;
+import androidx.lifecycle.Transformations;
+import androidx.paging.Pager;
+import androidx.paging.PagingConfig;
+import androidx.paging.PagingData;
+import androidx.paging.PagingLiveData;
+
+import java.util.concurrent.Executor;
+
+import kotlinx.coroutines.CoroutineScope;
+import ml.docilealligator.infinityforreddit.RedditDataRoomDatabase;
+import retrofit2.Retrofit;
+
+public class OnlineCustomThemeRepository {
+ private final LiveData<PagingData<CustomTheme>> customThemes;
+ private MutableLiveData<OnlineCustomThemeFilter> onlineCustomThemeFilterMutableLiveData;
+
+ public OnlineCustomThemeRepository(Executor executor, Retrofit retrofit,
+ RedditDataRoomDatabase redditDataRoomDatabase, CoroutineScope viewModelScope) {
+ onlineCustomThemeFilterMutableLiveData = new MutableLiveData<>(new OnlineCustomThemeFilter());
+
+ Pager<String, CustomTheme> pager = new Pager<>(new PagingConfig(25, 4, false, 10),
+ () -> new OnlineCustomThemePagingSource(executor, retrofit, redditDataRoomDatabase));
+
+ customThemes = PagingLiveData.cachedIn(Transformations.switchMap(onlineCustomThemeFilterMutableLiveData,
+ customThemeFilter -> PagingLiveData.getLiveData(pager)), viewModelScope);
+ }
+
+ public LiveData<PagingData<CustomTheme>> getOnlineCustomThemes() {
+ return customThemes;
+ }
+
+ public void changeOnlineCustomThemeFilter(OnlineCustomThemeFilter onlineCustomThemeFilter) {
+ onlineCustomThemeFilterMutableLiveData.postValue(onlineCustomThemeFilter);
+ }
+
+}
diff --git a/app/src/main/java/ml/docilealligator/infinityforreddit/fragments/CustomThemeListingFragment.java b/app/src/main/java/ml/docilealligator/infinityforreddit/fragments/CustomThemeListingFragment.java
index c10bee15..ddb3d11d 100644
--- a/app/src/main/java/ml/docilealligator/infinityforreddit/fragments/CustomThemeListingFragment.java
+++ b/app/src/main/java/ml/docilealligator/infinityforreddit/fragments/CustomThemeListingFragment.java
@@ -22,12 +22,19 @@ import ml.docilealligator.infinityforreddit.RecyclerViewContentScrollingInterfac
import ml.docilealligator.infinityforreddit.RedditDataRoomDatabase;
import ml.docilealligator.infinityforreddit.activities.BaseActivity;
import ml.docilealligator.infinityforreddit.adapters.CustomThemeListingRecyclerViewAdapter;
+import ml.docilealligator.infinityforreddit.adapters.OnlineCustomThemeListingRecyclerViewAdapter;
import ml.docilealligator.infinityforreddit.customtheme.CustomThemeViewModel;
import ml.docilealligator.infinityforreddit.customtheme.CustomThemeWrapper;
import ml.docilealligator.infinityforreddit.databinding.FragmentCustomThemeListingBinding;
+import retrofit2.Retrofit;
public class CustomThemeListingFragment extends Fragment {
+ public static final String EXTRA_IS_ONLINE = "EIO";
+
+ @Inject
+ @Named("online_custom_themes")
+ Retrofit onlineCustomThemesRetrofit;
@Inject
@Named("default")
SharedPreferences sharedPreferences;
@@ -52,6 +59,7 @@ public class CustomThemeListingFragment extends Fragment {
public CustomThemeViewModel customThemeViewModel;
private BaseActivity activity;
private FragmentCustomThemeListingBinding binding;
+ private boolean isOnline;
public CustomThemeListingFragment() {
// Required empty public constructor
@@ -65,9 +73,10 @@ public class CustomThemeListingFragment extends Fragment {
// Inflate the layout for this fragment
binding = FragmentCustomThemeListingBinding.inflate(inflater, container, false);
- CustomThemeListingRecyclerViewAdapter adapter = new CustomThemeListingRecyclerViewAdapter(activity,
- CustomThemeWrapper.getPredefinedThemes(activity));
- binding.recyclerViewCustomizeThemeListingActivity.setAdapter(adapter);
+ if (getArguments() != null) {
+ isOnline = getArguments().getBoolean(EXTRA_IS_ONLINE);
+ }
+
binding.recyclerViewCustomizeThemeListingActivity.addOnScrollListener(new RecyclerView.OnScrollListener() {
@Override
public void onScrolled(@NonNull RecyclerView recyclerView, int dx, int dy) {
@@ -79,10 +88,25 @@ public class CustomThemeListingFragment extends Fragment {
}
});
- customThemeViewModel = new ViewModelProvider(this,
- new CustomThemeViewModel.Factory(redditDataRoomDatabase))
- .get(CustomThemeViewModel.class);
- customThemeViewModel.getAllCustomThemes().observe(getViewLifecycleOwner(), adapter::setUserThemes);
+ if (isOnline) {
+ OnlineCustomThemeListingRecyclerViewAdapter adapter = new OnlineCustomThemeListingRecyclerViewAdapter(activity);
+ binding.recyclerViewCustomizeThemeListingActivity.setAdapter(adapter);
+
+ customThemeViewModel = new ViewModelProvider(this,
+ new CustomThemeViewModel.Factory(executor, onlineCustomThemesRetrofit, redditDataRoomDatabase))
+ .get(CustomThemeViewModel.class);
+ customThemeViewModel.getOnlineCustomThemes().observe(getViewLifecycleOwner(),
+ customThemePagingData -> adapter.submitData(getViewLifecycleOwner().getLifecycle(), customThemePagingData));
+ } else {
+ CustomThemeListingRecyclerViewAdapter adapter = new CustomThemeListingRecyclerViewAdapter(activity,
+ CustomThemeWrapper.getPredefinedThemes(activity));
+ binding.recyclerViewCustomizeThemeListingActivity.setAdapter(adapter);
+
+ customThemeViewModel = new ViewModelProvider(this,
+ new CustomThemeViewModel.Factory(redditDataRoomDatabase))
+ .get(CustomThemeViewModel.class);
+ customThemeViewModel.getAllCustomThemes().observe(getViewLifecycleOwner(), adapter::setUserThemes);
+ }
return binding.getRoot();
}
diff --git a/app/src/main/java/ml/docilealligator/infinityforreddit/utils/JSONUtils.java b/app/src/main/java/ml/docilealligator/infinityforreddit/utils/JSONUtils.java
index 800e6d45..32b8a245 100644
--- a/app/src/main/java/ml/docilealligator/infinityforreddit/utils/JSONUtils.java
+++ b/app/src/main/java/ml/docilealligator/infinityforreddit/utils/JSONUtils.java
@@ -195,6 +195,7 @@ public class JSONUtils {
public static final String SUGGESTED_SORT_KEY = "suggested_sort";
public static final String P_KEY = "p";
public static final String VARIANTS_KEY = "variants";
+ public static final String PAGE_KEY = "page";
@Nullable
public static Map<String, MediaMetadata> parseMediaMetadata(JSONObject data) {