1
0
mirror of https://github.com/TwidereProject/Twidere-Android synced 2025-01-28 15:39:32 +01:00
This commit is contained in:
Mariotaku Lee 2016-02-25 21:11:35 +08:00
parent b5e8f98f18
commit 1e8c6233d3
5 changed files with 83 additions and 17 deletions

View File

@ -259,7 +259,7 @@ public abstract class AbsActivitiesFragment<Data> extends AbsContentListRecycler
final AbsActivitiesAdapter<Data> adapter = getAdapter();
final boolean rememberPosition = mPreferences.getBoolean(KEY_REMEMBER_POSITION, false);
final boolean readFromBottom = mPreferences.getBoolean(KEY_READ_FROM_BOTTOM, false);
final long lastReadId;
long lastReadId;
final int lastVisiblePos, lastVisibleTop;
final String tag = getCurrentReadPositionTag();
final LinearLayoutManager layoutManager = getLayoutManager();
@ -283,14 +283,25 @@ public abstract class AbsActivitiesFragment<Data> extends AbsContentListRecycler
lastVisibleTop = 0;
}
adapter.setData(data);
setRefreshEnabled(true);
final int activityStartIndex = adapter.getActivityStartIndex();
final int activityEndIndex = activityStartIndex + adapter.getActivityCount();
// The last activity is activityEndExclusiveIndex - 1
final int activityEndExclusiveIndex = activityStartIndex + adapter.getActivityCount();
if (activityEndExclusiveIndex >= 0) {
final long lastItemId = adapter.getTimestamp(activityEndExclusiveIndex);
// Activity corresponds to last read timestamp was deleted, use last item timestamp
// instead
if (lastItemId > 0 && lastReadId < lastItemId) {
lastReadId = lastItemId;
}
}
setRefreshEnabled(true);
if (!(loader instanceof IExtendedLoader) || ((IExtendedLoader) loader).isFromUser()) {
adapter.setLoadMoreSupportedPosition(hasMoreData(data) ? IndicatorPosition.END : IndicatorPosition.NONE);
int pos = -1;
for (int i = activityStartIndex; i < activityEndIndex; i++) {
if (lastReadId != -1 && lastReadId == adapter.getTimestamp(i)) {
for (int i = activityStartIndex; i < activityEndExclusiveIndex; i++) {
if (lastReadId != -1 && adapter.getTimestamp(i) <= lastReadId) {
pos = i;
break;
}

View File

@ -248,7 +248,7 @@ public abstract class AbsContentRecyclerViewFragment<A extends LoadMoreSupportAd
setupRecyclerView(context, compact);
mRecyclerView.setAdapter(mAdapter);
mScrollListener = new ContentListScrollListener(this);
mScrollListener = new ContentListScrollListener(this, new ContentListScrollListener.RecyclerViewCallback(mRecyclerView));
mRecyclerView.setOnTouchListener(mScrollListener.getOnTouchListener());
mScrollListener.setTouchSlop(ViewConfiguration.get(context).getScaledTouchSlop());
}

View File

@ -246,7 +246,7 @@ public abstract class AbsStatusesFragment<Data> extends AbsContentListRecyclerVi
final AbsStatusesAdapter<Data> adapter = getAdapter();
final boolean rememberPosition = mPreferences.getBoolean(KEY_REMEMBER_POSITION, false);
final boolean readFromBottom = mPreferences.getBoolean(KEY_READ_FROM_BOTTOM, false);
final long lastReadId;
long lastReadId;
final int lastVisiblePos, lastVisibleTop;
final String tag = getCurrentReadPositionTag();
final LinearLayoutManager layoutManager = getLayoutManager();
@ -270,14 +270,24 @@ public abstract class AbsStatusesFragment<Data> extends AbsContentListRecyclerVi
lastVisibleTop = 0;
}
adapter.setData(data);
setRefreshEnabled(true);
final int statusStartIndex = adapter.getStatusStartIndex();
final int statusEndIndex = statusStartIndex + adapter.getStatusCount();
// The last status is statusEndExclusiveIndex - 1
final int statusEndExclusiveIndex = statusStartIndex + adapter.getStatusCount();
if (statusEndExclusiveIndex >= 0) {
final long lastItemId = adapter.getStatusId(statusEndExclusiveIndex - 1);
// Status corresponds to last read id was deleted, use last item id instead
if (lastItemId > 0 && lastReadId < lastItemId) {
lastReadId = lastItemId;
}
}
setRefreshEnabled(true);
if (!(loader instanceof IExtendedLoader) || ((IExtendedLoader) loader).isFromUser()) {
adapter.setLoadMoreSupportedPosition(hasMoreData(data) ? IndicatorPosition.END : IndicatorPosition.NONE);
int pos = -1;
for (int i = statusStartIndex; i < statusEndIndex; i++) {
if (lastReadId != -1 && lastReadId == adapter.getStatusId(i)) {
for (int i = statusStartIndex; i < statusEndExclusiveIndex; i++) {
// Assume statuses are descend sorted by id, so break at first status with id
// lesser equals than read position
if (lastReadId != -1 && adapter.getStatusId(i) <= lastReadId) {
pos = i;
break;
}

View File

@ -364,7 +364,7 @@ public class StatusFragment extends BaseSupportFragment implements LoaderCallbac
mRecyclerView.setAdapter(mStatusAdapter);
registerForContextMenu(mRecyclerView);
mScrollListener = new ContentListScrollListener(this);
mScrollListener = new ContentListScrollListener(this, new ContentListScrollListener.RecyclerViewCallback(mRecyclerView));
mScrollListener.setTouchSlop(ViewConfiguration.get(context).getScaledTouchSlop());
mNavigationHelper = new RecyclerViewNavigationHelper(mRecyclerView, mLayoutManager,

View File

@ -20,6 +20,7 @@
package org.mariotaku.twidere.util;
import android.support.annotation.NonNull;
import android.support.annotation.Nullable;
import android.support.v7.widget.RecyclerView;
import android.support.v7.widget.RecyclerView.OnScrollListener;
import android.view.MotionEvent;
@ -33,23 +34,26 @@ import org.mariotaku.twidere.adapter.iface.ILoadMoreSupportAdapter.IndicatorPosi
*/
public class ContentListScrollListener extends OnScrollListener {
private final ContentListSupport mContentListSupport;
private final ViewCallback mViewCallback;
private final TouchListener mTouchListener;
private int mScrollState;
private int mScrollSum;
private int mTouchSlop;
private final ContentListSupport mContentListSupport;
private final TouchListener mTouchListener;
private int mScrollDirection;
public ContentListScrollListener(@NonNull ContentListSupport contentListSupport) {
public ContentListScrollListener(@NonNull ContentListSupport contentListSupport, @Nullable ViewCallback viewCallback) {
mContentListSupport = contentListSupport;
mViewCallback = viewCallback;
mTouchListener = new TouchListener(this);
}
@Override
public void onScrollStateChanged(RecyclerView recyclerView, int newState) {
if (mScrollState != RecyclerView.SCROLL_STATE_IDLE) {
notifyScrollStateChanged();
postNotifyScrollStateChanged();
}
mScrollState = newState;
}
@ -66,7 +70,7 @@ public class ContentListScrollListener extends OnScrollListener {
mScrollSum = 0;
}
if (recyclerView.getScrollState() == RecyclerView.SCROLL_STATE_IDLE) {
notifyScrollStateChanged();
postNotifyScrollStateChanged();
}
}
@ -74,6 +78,23 @@ public class ContentListScrollListener extends OnScrollListener {
mTouchSlop = touchSlop;
}
private void postNotifyScrollStateChanged() {
if (mViewCallback != null) {
mViewCallback.post(new Runnable() {
@Override
public void run() {
if (mViewCallback.isComputingLayout()) {
mViewCallback.post(this);
} else {
notifyScrollStateChanged();
}
}
});
} else {
notifyScrollStateChanged();
}
}
private void notifyScrollStateChanged() {
final Object adapter = mContentListSupport.getAdapter();
if (!(adapter instanceof ILoadMoreSupportAdapter)) return;
@ -135,6 +156,12 @@ public class ContentListScrollListener extends OnScrollListener {
mScrollDirection = 0;
}
public interface ViewCallback {
boolean isComputingLayout();
void post(Runnable runnable);
}
public interface ContentListSupport {
Object getAdapter();
@ -150,4 +177,22 @@ public class ContentListScrollListener extends OnScrollListener {
boolean isReachingEnd();
}
public static class RecyclerViewCallback implements ViewCallback {
private final RecyclerView recyclerView;
public RecyclerViewCallback(RecyclerView recyclerView) {
this.recyclerView = recyclerView;
}
@Override
public boolean isComputingLayout() {
return recyclerView.isComputingLayout();
}
@Override
public void post(Runnable action) {
recyclerView.post(action);
}
}
}