Enqueue only one instance of PullNotificationWorker. Fixed bugs related to comment single thread mode.

This commit is contained in:
Alex Ning 2019-08-18 09:25:52 +08:00
parent 21c9eb03ed
commit 1984332fdd
3 changed files with 138 additions and 58 deletions

View File

@ -492,7 +492,11 @@ class CommentAndPostRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVie
bundle.putString(ModifyCommentBottomSheetFragment.EXTRA_ACCESS_TOKEN, mAccessToken);
bundle.putString(ModifyCommentBottomSheetFragment.EXTRA_COMMENT_CONTENT, comment.getCommentContent());
bundle.putString(ModifyCommentBottomSheetFragment.EXTRA_COMMENT_FULLNAME, comment.getFullName());
bundle.putInt(ModifyCommentBottomSheetFragment.EXTRA_POSITION, holder.getAdapterPosition() - 1);
if(mIsSingleCommentThreadMode) {
bundle.putInt(ModifyCommentBottomSheetFragment.EXTRA_POSITION, holder.getAdapterPosition() - 2);
} else {
bundle.putInt(ModifyCommentBottomSheetFragment.EXTRA_POSITION, holder.getAdapterPosition() - 1);
}
modifyCommentBottomSheetFragment.setArguments(bundle);
modifyCommentBottomSheetFragment.show(((AppCompatActivity) mActivity).getSupportFragmentManager(), modifyCommentBottomSheetFragment.getTag());
});
@ -519,7 +523,8 @@ class CommentAndPostRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVie
}
} else if(holder instanceof LoadMoreChildCommentsViewHolder) {
CommentData placeholder;
placeholder = mVisibleComments.get(holder.getAdapterPosition() - 1);
placeholder = mIsSingleCommentThreadMode ? mVisibleComments.get(holder.getAdapterPosition() - 2)
: mVisibleComments.get(holder.getAdapterPosition() - 1);
ViewGroup.LayoutParams params = ((LoadMoreChildCommentsViewHolder) holder).verticalBlock.getLayoutParams();
params.width = placeholder.getDepth() * 16;
@ -593,7 +598,11 @@ class CommentAndPostRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVie
children.get(i).setExpanded(false);
}
mVisibleComments.addAll(position + 1, children);
notifyItemRangeInserted(position + 2, children.size());
if(mIsSingleCommentThreadMode) {
notifyItemRangeInserted(position + 3, children.size());
} else {
notifyItemRangeInserted(position + 2, children.size());
}
}
}
}
@ -611,7 +620,11 @@ class CommentAndPostRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVie
}
mVisibleComments.subList(position + 1, position + 1 + allChildrenSize).clear();
notifyItemRangeRemoved(position + 2, allChildrenSize);
if(mIsSingleCommentThreadMode) {
notifyItemRangeRemoved(position + 3, allChildrenSize);
} else {
notifyItemRangeRemoved(position + 2, allChildrenSize);
}
}
void addComments(ArrayList<CommentData> comments, boolean hasMoreComments) {
@ -627,13 +640,25 @@ class CommentAndPostRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVie
int sizeBefore = mVisibleComments.size();
mVisibleComments.addAll(comments);
notifyItemRangeInserted(sizeBefore + 1, comments.size());
if(mIsSingleCommentThreadMode) {
notifyItemRangeInserted(sizeBefore + 2, comments.size());
} else {
notifyItemRangeInserted(sizeBefore + 1, comments.size());
}
if(mHasMoreComments != hasMoreComments) {
if(hasMoreComments) {
notifyItemInserted(mVisibleComments.size() + 1);
if(mIsSingleCommentThreadMode) {
notifyItemInserted(mVisibleComments.size() + 2);
} else {
notifyItemInserted(mVisibleComments.size() + 1);
}
} else {
notifyItemRemoved(mVisibleComments.size() + 1);
if(mIsSingleCommentThreadMode) {
notifyItemRemoved(mVisibleComments.size() + 2);
} else {
notifyItemRemoved(mVisibleComments.size() + 1);
}
}
}
mHasMoreComments = hasMoreComments;
@ -667,10 +692,18 @@ class CommentAndPostRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVie
mVisibleComments.get(parentPosition).setHasReply(true);
if(!mVisibleComments.get(parentPosition).isExpanded()) {
expandChildren(parentPosition);
notifyItemChanged(parentPosition + 1);
if(mIsSingleCommentThreadMode) {
notifyItemChanged(parentPosition + 2);
} else {
notifyItemChanged(parentPosition + 1);
}
} else {
mVisibleComments.add(parentPosition + 1, comment);
notifyItemInserted(parentPosition + 2);
if(mIsSingleCommentThreadMode) {
notifyItemInserted(parentPosition + 3);
} else {
notifyItemInserted(parentPosition + 2);
}
}
}
@ -713,26 +746,38 @@ class CommentAndPostRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVie
void loadMoreCommentsFailed() {
loadMoreCommentsFailed = true;
notifyItemChanged(mVisibleComments.size() + 1);
}
ArrayList<CommentData> getVisibleComments() {
return mVisibleComments;
if(mIsSingleCommentThreadMode) {
notifyItemChanged(mVisibleComments.size() + 2);
} else {
notifyItemChanged(mVisibleComments.size() + 1);
}
}
void editComment(String commentContent, int position) {
mVisibleComments.get(position).setCommentContent(commentContent);
notifyItemChanged(position + 1);
if(mIsSingleCommentThreadMode) {
notifyItemChanged(position + 2);
} else {
notifyItemChanged(position + 1);
}
}
void deleteComment(int position) {
if(mVisibleComments.get(position).hasReply()) {
mVisibleComments.get(position).setAuthor("[deleted]");
mVisibleComments.get(position).setCommentContent("[deleted]");
notifyItemChanged(position + 1);
if(mIsSingleCommentThreadMode) {
notifyItemChanged(position + 2);
} else {
notifyItemChanged(position + 1);
}
} else {
mVisibleComments.remove(position);
notifyItemRemoved(position + 1);
if(mIsSingleCommentThreadMode) {
notifyItemRemoved(position + 2);
} else {
notifyItemRemoved(position + 1);
}
}
}
@ -978,25 +1023,31 @@ class CommentAndPostRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVie
authorTextView.setOnClickListener(view -> {
Intent intent = new Intent(mActivity, ViewUserDetailActivity.class);
intent.putExtra(ViewUserDetailActivity.EXTRA_USER_NAME_KEY, mVisibleComments.get(getAdapterPosition() - 1).getAuthor());
if(mIsSingleCommentThreadMode) {
intent.putExtra(ViewUserDetailActivity.EXTRA_USER_NAME_KEY, mVisibleComments.get(getAdapterPosition() - 2).getAuthor());
} else {
intent.putExtra(ViewUserDetailActivity.EXTRA_USER_NAME_KEY, mVisibleComments.get(getAdapterPosition() - 1).getAuthor());
}
mActivity.startActivity(intent);
});
shareButton.setOnClickListener(view -> {
Intent intent = new Intent(Intent.ACTION_SEND);
intent.setType("text/plain");
String extraText = mVisibleComments.get(getAdapterPosition() - 1).getPermalink();
String extraText = mIsSingleCommentThreadMode ? mVisibleComments.get(getAdapterPosition() - 2).getPermalink()
: mVisibleComments.get(getAdapterPosition() - 1).getPermalink();
intent.putExtra(Intent.EXTRA_TEXT, extraText);
mActivity.startActivity(Intent.createChooser(intent, "Share"));
});
expandButton.setOnClickListener(view -> {
if(mVisibleComments.get(getAdapterPosition() - 1).isExpanded()) {
collapseChildren(getAdapterPosition() - 1);
int commentPosition = mIsSingleCommentThreadMode ? getAdapterPosition() - 2 : getAdapterPosition() - 1;
if(mVisibleComments.get(commentPosition).isExpanded()) {
collapseChildren(commentPosition);
expandButton.setImageResource(R.drawable.ic_expand_more_black_20dp);
} else {
expandChildren(getAdapterPosition() - 1);
mVisibleComments.get(getAdapterPosition() - 1).setExpanded(true);
expandChildren(commentPosition);
mVisibleComments.get(commentPosition).setExpanded(true);
expandButton.setImageResource(R.drawable.ic_expand_less_black_20dp);
}
});
@ -1007,12 +1058,15 @@ class CommentAndPostRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVie
return;
}
CommentData comment = mIsSingleCommentThreadMode ? mVisibleComments.get(getAdapterPosition() - 2) : mVisibleComments.get(getAdapterPosition() - 1);
Intent intent = new Intent(mActivity, CommentActivity.class);
intent.putExtra(CommentActivity.EXTRA_PARENT_DEPTH_KEY, mVisibleComments.get(getAdapterPosition() - 1).getDepth() + 1);
intent.putExtra(CommentActivity.EXTRA_COMMENT_PARENT_TEXT_KEY, mVisibleComments.get(getAdapterPosition() - 1).getCommentContent());
intent.putExtra(CommentActivity.EXTRA_PARENT_FULLNAME_KEY, mVisibleComments.get(getAdapterPosition() - 1).getFullName());
intent.putExtra(CommentActivity.EXTRA_PARENT_DEPTH_KEY, comment.getDepth() + 1);
intent.putExtra(CommentActivity.EXTRA_COMMENT_PARENT_TEXT_KEY, comment.getCommentContent());
intent.putExtra(CommentActivity.EXTRA_PARENT_FULLNAME_KEY, comment.getFullName());
intent.putExtra(CommentActivity.EXTRA_IS_REPLYING_KEY, true);
intent.putExtra(CommentActivity.EXTRA_PARENT_POSITION_KEY, getAdapterPosition() - 1);
int parentPosition = mIsSingleCommentThreadMode ? getAdapterPosition() - 2 : getAdapterPosition() - 1;
intent.putExtra(CommentActivity.EXTRA_PARENT_POSITION_KEY, parentPosition);
mActivity.startActivityForResult(intent, CommentActivity.WRITE_COMMENT_REQUEST_CODE);
});
@ -1022,43 +1076,45 @@ class CommentAndPostRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVie
return;
}
int previousVoteType = mVisibleComments.get(getAdapterPosition() - 1).getVoteType();
int commentPosition = mIsSingleCommentThreadMode ? getAdapterPosition() - 2 : getAdapterPosition() - 1;
int previousVoteType = mVisibleComments.get(commentPosition).getVoteType();
String newVoteType;
downVoteButton.clearColorFilter();
if(previousVoteType != CommentData.VOTE_TYPE_UPVOTE) {
//Not upvoted before
mVisibleComments.get(getAdapterPosition() - 1).setVoteType(CommentData.VOTE_TYPE_UPVOTE);
mVisibleComments.get(commentPosition).setVoteType(CommentData.VOTE_TYPE_UPVOTE);
newVoteType = RedditUtils.DIR_UPVOTE;
upVoteButton.setColorFilter(ContextCompat.getColor(mActivity, R.color.backgroundColorPrimaryDark), android.graphics.PorterDuff.Mode.SRC_IN);
} else {
//Upvoted before
mVisibleComments.get(getAdapterPosition() - 1).setVoteType(CommentData.VOTE_TYPE_NO_VOTE);
mVisibleComments.get(commentPosition).setVoteType(CommentData.VOTE_TYPE_NO_VOTE);
newVoteType = RedditUtils.DIR_UNVOTE;
upVoteButton.clearColorFilter();
}
scoreTextView.setText(Integer.toString(mVisibleComments.get(getAdapterPosition() - 1).getScore() + mVisibleComments.get(getAdapterPosition() - 1).getVoteType()));
scoreTextView.setText(Integer.toString(mVisibleComments.get(commentPosition).getScore() + mVisibleComments.get(commentPosition).getVoteType()));
VoteThing.voteThing(mOauthRetrofit, mAccessToken, new VoteThing.VoteThingListener() {
@Override
public void onVoteThingSuccess(int position) {
if(newVoteType.equals(RedditUtils.DIR_UPVOTE)) {
mVisibleComments.get(getAdapterPosition() - 1).setVoteType(CommentData.VOTE_TYPE_UPVOTE);
mVisibleComments.get(commentPosition).setVoteType(CommentData.VOTE_TYPE_UPVOTE);
upVoteButton.setColorFilter(ContextCompat.getColor(mActivity, R.color.backgroundColorPrimaryDark), android.graphics.PorterDuff.Mode.SRC_IN);
} else {
mVisibleComments.get(getAdapterPosition() - 1).setVoteType(CommentData.VOTE_TYPE_NO_VOTE);
mVisibleComments.get(commentPosition).setVoteType(CommentData.VOTE_TYPE_NO_VOTE);
upVoteButton.clearColorFilter();
}
downVoteButton.clearColorFilter();
scoreTextView.setText(Integer.toString(mVisibleComments.get(getAdapterPosition() - 1).getScore() + mVisibleComments.get(getAdapterPosition() - 1).getVoteType()));
scoreTextView.setText(Integer.toString(mVisibleComments.get(commentPosition).getScore() + mVisibleComments.get(commentPosition).getVoteType()));
}
@Override
public void onVoteThingFail(int position) { }
}, mVisibleComments.get(getAdapterPosition() - 1).getFullName(), newVoteType, getAdapterPosition());
}, mVisibleComments.get(commentPosition).getFullName(), newVoteType, getAdapterPosition());
});
downVoteButton.setOnClickListener(view -> {
@ -1067,43 +1123,45 @@ class CommentAndPostRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVie
return;
}
int previousVoteType = mVisibleComments.get(getAdapterPosition() - 1).getVoteType();
int commentPosition = mIsSingleCommentThreadMode ? getAdapterPosition() - 2 : getAdapterPosition() - 1;
int previousVoteType = mVisibleComments.get(commentPosition).getVoteType();
String newVoteType;
upVoteButton.clearColorFilter();
if(previousVoteType != CommentData.VOTE_TYPE_DOWNVOTE) {
//Not downvoted before
mVisibleComments.get(getAdapterPosition() - 1).setVoteType(CommentData.VOTE_TYPE_DOWNVOTE);
mVisibleComments.get(commentPosition).setVoteType(CommentData.VOTE_TYPE_DOWNVOTE);
newVoteType = RedditUtils.DIR_DOWNVOTE;
downVoteButton.setColorFilter(ContextCompat.getColor(mActivity, R.color.colorAccent), android.graphics.PorterDuff.Mode.SRC_IN);
} else {
//Downvoted before
mVisibleComments.get(getAdapterPosition() - 1).setVoteType(CommentData.VOTE_TYPE_NO_VOTE);
mVisibleComments.get(commentPosition).setVoteType(CommentData.VOTE_TYPE_NO_VOTE);
newVoteType = RedditUtils.DIR_UNVOTE;
downVoteButton.clearColorFilter();
}
scoreTextView.setText(Integer.toString(mVisibleComments.get(getAdapterPosition() - 1).getScore() + mVisibleComments.get(getAdapterPosition() - 1).getVoteType()));
scoreTextView.setText(Integer.toString(mVisibleComments.get(commentPosition).getScore() + mVisibleComments.get(commentPosition).getVoteType()));
VoteThing.voteThing(mOauthRetrofit, mAccessToken, new VoteThing.VoteThingListener() {
@Override
public void onVoteThingSuccess(int position1) {
if(newVoteType.equals(RedditUtils.DIR_DOWNVOTE)) {
mVisibleComments.get(getAdapterPosition() - 1).setVoteType(CommentData.VOTE_TYPE_DOWNVOTE);
mVisibleComments.get(commentPosition).setVoteType(CommentData.VOTE_TYPE_DOWNVOTE);
downVoteButton.setColorFilter(ContextCompat.getColor(mActivity, R.color.colorAccent), android.graphics.PorterDuff.Mode.SRC_IN);
} else {
mVisibleComments.get(getAdapterPosition() - 1).setVoteType(CommentData.VOTE_TYPE_NO_VOTE);
mVisibleComments.get(commentPosition).setVoteType(CommentData.VOTE_TYPE_NO_VOTE);
downVoteButton.clearColorFilter();
}
upVoteButton.clearColorFilter();
scoreTextView.setText(Integer.toString(mVisibleComments.get(getAdapterPosition() - 1).getScore() + mVisibleComments.get(getAdapterPosition() - 1).getVoteType()));
scoreTextView.setText(Integer.toString(mVisibleComments.get(commentPosition).getScore() + mVisibleComments.get(commentPosition).getVoteType()));
}
@Override
public void onVoteThingFail(int position1) { }
}, mVisibleComments.get(getAdapterPosition() - 1).getFullName(), newVoteType, getAdapterPosition());
}, mVisibleComments.get(commentPosition).getFullName(), newVoteType, getAdapterPosition());
});
}
}
@ -1117,11 +1175,12 @@ class CommentAndPostRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVie
ButterKnife.bind(this, itemView);
placeholderTextView.setOnClickListener(view -> {
int parentPosition = getParentPosition(getAdapterPosition() - 1);
int commentPosition = mIsSingleCommentThreadMode ? getAdapterPosition() - 2 : getAdapterPosition() - 1;
int parentPosition = getParentPosition(commentPosition);
CommentData parentComment = mVisibleComments.get(parentPosition);
mVisibleComments.get(getAdapterPosition() - 1).setLoadingMoreChildren(true);
mVisibleComments.get(getAdapterPosition() - 1).setLoadMoreChildrenFailed(false);
mVisibleComments.get(commentPosition).setLoadingMoreChildren(true);
mVisibleComments.get(commentPosition).setLoadMoreChildrenFailed(false);
placeholderTextView.setText(R.string.loading);
FetchComment.fetchMoreComment(mRetrofit, parentComment.getMoreChildrenFullnames(),
@ -1140,8 +1199,8 @@ class CommentAndPostRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVie
mVisibleComments.get(parentPosition).getChildren().get(mVisibleComments.get(parentPosition).getChildren().size() - 1)
.setLoadMoreChildrenFailed(false);
int placeholderPosition = getAdapterPosition() - 1;
if(mVisibleComments.get(getAdapterPosition() - 1).getFullName().equals(parentComment.getFullName())) {
int placeholderPosition = commentPosition;
if(mVisibleComments.get(commentPosition).getFullName().equals(parentComment.getFullName())) {
for(int i = parentPosition + 1; i < mVisibleComments.size(); i++) {
if(mVisibleComments.get(i).getFullName().equals(parentComment.getFullName())) {
placeholderPosition = i;
@ -1155,14 +1214,18 @@ class CommentAndPostRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVie
placeholderTextView.setText(R.string.comment_load_more_comments);
mVisibleComments.addAll(placeholderPosition, expandedComments);
notifyItemRangeInserted(placeholderPosition + 1, expandedComments.size());
if(mIsSingleCommentThreadMode) {
notifyItemRangeInserted(placeholderPosition + 2, expandedComments.size());
} else {
notifyItemRangeInserted(placeholderPosition + 1, expandedComments.size());
}
} else {
mVisibleComments.get(parentPosition).getChildren()
.remove(mVisibleComments.get(parentPosition).getChildren().size() - 1);
mVisibleComments.get(parentPosition).removeMoreChildrenFullnames();
int placeholderPosition = getAdapterPosition() - 1;
if(mVisibleComments.get(getAdapterPosition() - 1).getFullName().equals(parentComment.getFullName())) {
int placeholderPosition = commentPosition;
if(mVisibleComments.get(commentPosition).getFullName().equals(parentComment.getFullName())) {
for(int i = parentPosition + 1; i < mVisibleComments.size(); i++) {
if(mVisibleComments.get(i).getFullName().equals(parentComment.getFullName())) {
placeholderPosition = i;
@ -1172,10 +1235,18 @@ class CommentAndPostRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVie
}
mVisibleComments.remove(placeholderPosition);
notifyItemRemoved(placeholderPosition + 1);
if(mIsSingleCommentThreadMode) {
notifyItemRemoved(placeholderPosition + 2);
} else {
notifyItemRemoved(placeholderPosition + 1);
}
mVisibleComments.addAll(placeholderPosition, expandedComments);
notifyItemRangeInserted(placeholderPosition + 1, expandedComments.size());
if(mIsSingleCommentThreadMode) {
notifyItemRangeInserted(placeholderPosition + 2, expandedComments.size());
} else {
notifyItemRangeInserted(placeholderPosition + 1, expandedComments.size());
}
}
} else {
if(mVisibleComments.get(parentPosition).hasReply() && mVisibleComments.get(parentPosition).getChildren().size() <= childrenStartingIndex) {
@ -1206,7 +1277,11 @@ class CommentAndPostRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVie
placeholderTextView.setText(R.string.comment_load_more_comments);
mVisibleComments.addAll(placeholderPosition, expandedComments);
notifyItemRangeInserted(placeholderPosition + 1, expandedComments.size());
if(mIsSingleCommentThreadMode) {
notifyItemRangeInserted(placeholderPosition + 2, expandedComments.size());
} else {
notifyItemRangeInserted(placeholderPosition + 1, expandedComments.size());
}
}
mVisibleComments.get(i).getChildren().get(mVisibleComments.get(i).getChildren().size() - 1)
@ -1226,8 +1301,9 @@ class CommentAndPostRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVie
if(parentPosition < mVisibleComments.size()
&& parentComment.getFullName().equals(mVisibleComments.get(parentPosition).getFullName())) {
if(mVisibleComments.get(parentPosition).isExpanded()) {
int placeholderPosition = getAdapterPosition() - 1;
if(!mVisibleComments.get(getAdapterPosition() - 1).getFullName().equals(parentComment.getFullName())) {
int commentPosition = mIsSingleCommentThreadMode ? getAdapterPosition() - 2 : getAdapterPosition() - 1;
int placeholderPosition = commentPosition;
if(!mVisibleComments.get(commentPosition).getFullName().equals(parentComment.getFullName())) {
for(int i = parentPosition + 1; i < mVisibleComments.size(); i++) {
if(mVisibleComments.get(i).getFullName().equals(parentComment.getFullName())) {
placeholderPosition = i;

View File

@ -31,6 +31,7 @@ import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
import androidx.viewpager.widget.ViewPager;
import androidx.work.Constraints;
import androidx.work.ExistingPeriodicWorkPolicy;
import androidx.work.NetworkType;
import androidx.work.PeriodicWorkRequest;
import androidx.work.WorkManager;
@ -246,11 +247,12 @@ public class MainActivity extends AppCompatActivity implements SortTypeBottomShe
.build();
PeriodicWorkRequest pullNotificationRequest =
new PeriodicWorkRequest.Builder(PullNotificationWorker.class, 15, TimeUnit.MINUTES)
new PeriodicWorkRequest.Builder(PullNotificationWorker.class, 1, TimeUnit.HOURS)
.setConstraints(constraints)
.build();
WorkManager.getInstance(this).enqueue(pullNotificationRequest);
WorkManager.getInstance(this).enqueueUniquePeriodicWork(PullNotificationWorker.WORKER_TAG,
ExistingPeriodicWorkPolicy.KEEP, pullNotificationRequest);
}
bindView();
}).execute();

View File

@ -23,6 +23,8 @@ import retrofit2.Response;
import retrofit2.Retrofit;
public class PullNotificationWorker extends Worker {
static final String WORKER_TAG = "PNWT";
private Context context;
@Inject