From a725f7eb3a11b45b21bc02f182564e5db9b1714c Mon Sep 17 00:00:00 2001 From: Alex Ning Date: Mon, 6 Sep 2021 22:59:05 +0800 Subject: Use withLoadStateFooter to show load state. --- .../adapters/Paging3LoadingStateAdapter.java | 72 ++++++++++++++++++++++ .../infinityforreddit/fragments/PostFragment.java | 31 +++++++++- .../main/res/layout/item_paging_3_load_state.xml | 45 ++++++++++++++ 3 files changed, 146 insertions(+), 2 deletions(-) create mode 100644 app/src/main/java/ml/docilealligator/infinityforreddit/adapters/Paging3LoadingStateAdapter.java create mode 100644 app/src/main/res/layout/item_paging_3_load_state.xml diff --git a/app/src/main/java/ml/docilealligator/infinityforreddit/adapters/Paging3LoadingStateAdapter.java b/app/src/main/java/ml/docilealligator/infinityforreddit/adapters/Paging3LoadingStateAdapter.java new file mode 100644 index 00000000..e23dc4dd --- /dev/null +++ b/app/src/main/java/ml/docilealligator/infinityforreddit/adapters/Paging3LoadingStateAdapter.java @@ -0,0 +1,72 @@ +package ml.docilealligator.infinityforreddit.adapters; + +import android.util.Log; +import android.view.LayoutInflater; +import android.view.View; +import android.view.ViewGroup; +import android.widget.Button; +import android.widget.ProgressBar; +import android.widget.RelativeLayout; +import android.widget.TextView; + +import androidx.annotation.NonNull; +import androidx.paging.LoadState; +import androidx.paging.LoadStateAdapter; +import androidx.recyclerview.widget.RecyclerView; + +import ml.docilealligator.infinityforreddit.R; +import ml.docilealligator.infinityforreddit.customtheme.CustomThemeWrapper; + +public class Paging3LoadingStateAdapter extends LoadStateAdapter { + private CustomThemeWrapper mCustomThemeWrapper; + private int mErrorStringId; + private View.OnClickListener mRetryCallback; + + public Paging3LoadingStateAdapter(CustomThemeWrapper customThemeWrapper, int errorStringId, View.OnClickListener retryCallback) { + this.mCustomThemeWrapper = customThemeWrapper; + this.mErrorStringId = errorStringId; + this.mRetryCallback = retryCallback; + } + + @Override + public void onBindViewHolder(@NonNull LoadStateViewHolder loadStateViewHolder, @NonNull LoadState loadState) { + loadStateViewHolder.bind(loadState); + } + + @NonNull + @Override + public LoadStateViewHolder onCreateViewHolder(@NonNull ViewGroup viewGroup, @NonNull LoadState loadState) { + return new LoadStateViewHolder(LayoutInflater.from(viewGroup.getContext()).inflate(R.layout.item_paging_3_load_state, viewGroup, false), mRetryCallback); + } + + class LoadStateViewHolder extends RecyclerView.ViewHolder { + private ProgressBar mProgressBar; + private RelativeLayout mErrorView; + private TextView mErrorMsg; + private Button mRetry; + + LoadStateViewHolder(@NonNull View itemView, @NonNull View.OnClickListener retryCallback) { + super(itemView); + + mProgressBar = itemView.findViewById(R.id.progress_bar_item_paging_3_load_state); + mErrorView = itemView.findViewById(R.id.error_view_relative_layout_item_paging_3_load_state); + mErrorMsg = itemView.findViewById(R.id.error_text_view_item_paging_3_load_state); + mRetry = itemView.findViewById(R.id.retry_button_item_paging_3_load_state); + + mErrorMsg.setText(mErrorStringId); + mErrorMsg.setTextColor(mCustomThemeWrapper.getPrimaryTextColor()); + mRetry.setOnClickListener(retryCallback); + mErrorView.setOnClickListener(retryCallback); + + Log.i("asfasdf", "asdf "); + } + + public void bind(LoadState loadState) { + Log.i("asfasdf", "asdf bind"); + mProgressBar.setVisibility(loadState instanceof LoadState.Loading + ? View.VISIBLE : View.GONE); + mErrorView.setVisibility(loadState instanceof LoadState.Error + ? View.VISIBLE : View.GONE); + } + } +} diff --git a/app/src/main/java/ml/docilealligator/infinityforreddit/fragments/PostFragment.java b/app/src/main/java/ml/docilealligator/infinityforreddit/fragments/PostFragment.java index f4ed088a..48a39e41 100644 --- a/app/src/main/java/ml/docilealligator/infinityforreddit/fragments/PostFragment.java +++ b/app/src/main/java/ml/docilealligator/infinityforreddit/fragments/PostFragment.java @@ -37,6 +37,7 @@ import androidx.appcompat.app.AppCompatActivity; import androidx.core.content.res.ResourcesCompat; import androidx.fragment.app.Fragment; import androidx.lifecycle.ViewModelProvider; +import androidx.paging.LoadState; import androidx.recyclerview.widget.ItemTouchHelper; import androidx.recyclerview.widget.LinearSmoothScroller; import androidx.recyclerview.widget.RecyclerView; @@ -78,6 +79,7 @@ import ml.docilealligator.infinityforreddit.SortType; import ml.docilealligator.infinityforreddit.activities.BaseActivity; import ml.docilealligator.infinityforreddit.activities.FilteredPostsActivity; import ml.docilealligator.infinityforreddit.activities.ViewSubredditDetailActivity; +import ml.docilealligator.infinityforreddit.adapters.Paging3LoadingStateAdapter; import ml.docilealligator.infinityforreddit.adapters.PostRecyclerViewAdapter; import ml.docilealligator.infinityforreddit.asynctasks.LoadSubredditIcon; import ml.docilealligator.infinityforreddit.asynctasks.LoadUserData; @@ -214,6 +216,7 @@ public class PostFragment extends Fragment implements FragmentCommunicator { private boolean isLazyModePaused = false; private boolean hasPost = false; private boolean isShown = false; + private boolean isInitialRefreshingStarted = false; private boolean savePostFeedScrolledPosition; private boolean rememberMutingOptionInPostFeed; private Boolean masterMutingOption; @@ -257,8 +260,8 @@ public class PostFragment extends Fragment implements FragmentCommunicator { public void onResume() { super.onResume(); isShown = true; - if (mPostRecyclerView.getAdapter() != null) { - ((PostRecyclerViewAdapter) mPostRecyclerView.getAdapter()).setCanStartActivity(true); + if (mAdapter != null) { + mAdapter.setCanStartActivity(true); } if (isInLazyMode) { resumeLazyMode(false); @@ -1179,6 +1182,30 @@ public class PostFragment extends Fragment implements FragmentCommunicator { private void bindPostViewModel() { mPostViewModel.getPosts().observe(getViewLifecycleOwner(), posts -> mAdapter.submitData(getViewLifecycleOwner().getLifecycle(), posts)); + mAdapter.addLoadStateListener(combinedLoadStates -> { + LoadState refreshLoadState = combinedLoadStates.getRefresh(); + LoadState appendLoadState = combinedLoadStates.getAppend(); + + mSwipeRefreshLayout.setRefreshing(refreshLoadState instanceof LoadState.Loading); + if (refreshLoadState instanceof LoadState.NotLoading) { + if (refreshLoadState.getEndOfPaginationReached() && mAdapter.getItemCount() < 1) { + if (isInLazyMode) { + stopLazyMode(); + } + + mFetchPostInfoLinearLayout.setOnClickListener(null); + showErrorView(R.string.no_posts); + } + } else if (refreshLoadState instanceof LoadState.Error) { + mFetchPostInfoLinearLayout.setOnClickListener(view -> refresh()); + showErrorView(R.string.load_posts_error); + } + return null; + }); + + mPostRecyclerView.setAdapter(mAdapter.withLoadStateFooter(new Paging3LoadingStateAdapter(mCustomThemeWrapper, R.string.load_more_posts_error, + view -> mAdapter.retry()))); + /*mPostViewModel.hasPost().observe(getViewLifecycleOwner(), hasPost -> { this.hasPost = hasPost; mSwipeRefreshLayout.setRefreshing(false); diff --git a/app/src/main/res/layout/item_paging_3_load_state.xml b/app/src/main/res/layout/item_paging_3_load_state.xml new file mode 100644 index 00000000..321b8e14 --- /dev/null +++ b/app/src/main/res/layout/item_paging_3_load_state.xml @@ -0,0 +1,45 @@ + + + + + + + + + +