Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix/waterfall view bug #4063

Merged
merged 3 commits into from
Oct 15, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@
import com.tencent.mtt.hippy.views.common.HippyNestedScrollComponent.Priority;
import com.tencent.mtt.hippy.views.common.HippyNestedScrollHelper;
import com.tencent.mtt.hippy.views.custom.HippyCustomPropsController;
import com.tencent.mtt.hippy.views.modal.HippyModalHostView;
import com.tencent.mtt.hippy.views.view.HippyViewGroup;
import com.tencent.renderer.NativeRenderContext;
import com.tencent.renderer.Renderer;
Expand Down Expand Up @@ -543,8 +544,12 @@ private boolean checkOverflowVisible(@NonNull View view) {

protected void addView(ViewGroup parentView, View view, int index) {
int realIndex = index;
if (realIndex > parentView.getChildCount()) {
realIndex = parentView.getChildCount();
int childCount = parentView.getChildCount();
if (parentView instanceof HippyModalHostView) {
childCount = ((HippyModalHostView) parentView).getModalChildCount();
}
if (realIndex > childCount) {
realIndex = childCount;
}
try {
parentView.addView(view, realIndex);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@

import android.content.Context;
import android.graphics.Rect;
import android.util.Log;
import android.view.ViewConfiguration;
import android.widget.FrameLayout;
import androidx.annotation.NonNull;
Expand Down Expand Up @@ -49,6 +50,7 @@
public class HippyRecyclerView<ADP extends HippyRecyclerListAdapter> extends HippyRecyclerViewBase
implements IHeaderAttachListener, HippyViewHolderAbandonListener, HippyNestedScrollTarget2 {

private static final String TAG = "HippyRecyclerView";
private static int DEFAULT_ITEM_VIEW_CACHE_SIZE = 4;
private static final int INVALID_POINTER = -1;
protected ADP listAdapter;
Expand Down Expand Up @@ -253,18 +255,27 @@ private void scrollToInitContentOffset() {
* 刷新数据
*/
public void setListData() {
LogUtils.d("HippyRecyclerView", "itemCount =" + listAdapter.getItemCount());
LayoutManager layoutManager = getLayoutManager();
int currentNodeCount = listAdapter.getRenderNodeCount();
if (layoutManager instanceof StaggeredGridLayoutManager) {
listAdapter.notifyItemRangeChanged(renderNodeCount, listAdapter.getRenderNodeCount() - renderNodeCount);
LogUtils.d(TAG, "setListData: lastNodeCount " + renderNodeCount + ", currentNodeCount " + currentNodeCount);
int[] firstVisibleItem = null;
firstVisibleItem = ((HippyStaggeredGridLayoutManager) layoutManager).findFirstVisibleItemPositions(firstVisibleItem);
if (renderNodeCount >= currentNodeCount && firstVisibleItem != null
&& (firstVisibleItem[0] == 0 || firstVisibleItem[0] == 1)) {
LogUtils.d(TAG, "setListData: firstVisibleItem[0] " + firstVisibleItem[0]);
listAdapter.notifyDataSetChanged();
} else if (renderNodeCount < currentNodeCount) {
listAdapter.notifyItemRangeInserted(renderNodeCount, listAdapter.getRenderNodeCount() - renderNodeCount);
}
} else {
listAdapter.notifyDataSetChanged();
}
if (overPullHelper != null) {
overPullHelper.enableOverPullUp(!listAdapter.hasFooter());
overPullHelper.enableOverPullDown(!listAdapter.hasHeader());
}
renderNodeCount = listAdapter.getRenderNodeCount();
renderNodeCount = currentNodeCount;
if (renderNodeCount > 0 && mInitialContentOffset > 0) {
scrollToInitContentOffset();
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@
import androidx.recyclerview.widget.HippyStaggeredGridLayoutManager;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
import androidx.recyclerview.widget.RecyclerView.Adapter;
import androidx.recyclerview.widget.RecyclerView.LayoutManager;
import androidx.recyclerview.widget.RecyclerView.OnScrollListener;

Expand Down Expand Up @@ -56,6 +57,7 @@
public class RecyclerViewEventHelper extends OnScrollListener implements OnLayoutChangeListener,
OnAttachStateChangeListener, HippyOverPullListener {

private static final int WATERFALL_SCROLL_RELAYOUT_THRESHOLD = 4;
protected final HippyRecyclerView hippyRecyclerView;
private boolean scrollBeginDragEventEnable;
private boolean scrollEndDragEventEnable;
Expand Down Expand Up @@ -179,6 +181,21 @@ protected HippyViewEvent getOnScrollDragEndedEvent() {
return onScrollDragEndedEvent;
}

private void relayoutWaterfallIfNeeded() {
LayoutManager layoutManager = hippyRecyclerView.getLayoutManager();
if (layoutManager instanceof HippyStaggeredGridLayoutManager) {
int[] firstVisibleItem = null;
firstVisibleItem = ((HippyStaggeredGridLayoutManager) layoutManager).findFirstVisibleItemPositions(firstVisibleItem);
if (firstVisibleItem != null && (firstVisibleItem[0] <= WATERFALL_SCROLL_RELAYOUT_THRESHOLD)) {
Adapter adapter = hippyRecyclerView.getAdapter();
if (adapter != null) {
adapter.notifyDataSetChanged();
hippyRecyclerView.dispatchLayout();
}
}
}
}

@Override
public void onScrollStateChanged(RecyclerView recyclerView, int newState) {
int oldState = currentState;
Expand All @@ -190,6 +207,9 @@ public void onScrollStateChanged(RecyclerView recyclerView, int newState) {
sendDragEndEvent(oldState, currentState);
sendFlingEvent(newState);
sendFlingEndEvent(oldState, currentState);
if (newState == RecyclerView.SCROLL_STATE_IDLE) {
relayoutWaterfallIfNeeded();
}
}

@Override
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
import android.content.DialogInterface;
import android.view.View;

import android.view.ViewGroup;
import androidx.annotation.NonNull;
import com.tencent.mtt.hippy.annotation.HippyController;
import com.tencent.mtt.hippy.annotation.HippyControllerProps;
Expand Down Expand Up @@ -101,4 +102,13 @@ public void onAfterUpdateProps(@NonNull HippyModalHostView v) {
v.showOrUpdate();
}

@Override
public int getChildCount(HippyModalHostView modalHostView) {
return modalHostView.getModalChildCount();
}

@Override
public View getChildAt(HippyModalHostView modalHostView, int i) {
return modalHostView.getModalChildAt(i);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -126,27 +126,30 @@ public void addView(View child, int index) {
mDialogRootView.addView(child, index);
}

@Override
public int getChildCount() {
return mDialogRootView.getChildCount();
}

@Override
public View getChildAt(int index) {
return mDialogRootView.getChildAt(index);
}

@Override
public void removeView(View child) {
mDialogRootView.removeView(child);
}

@Override
public void removeViewAt(int index) {
View child = getChildAt(index);
View child = getModalChildAt(index);
mDialogRootView.removeView(child);
}

// Do not directly override the getChildCount method of ModalHostView, as it may cause the crash:
// java.lang.IllegalArgumentException: parameter must be a descendant
// Because under Modal, there are actually no child views. When the system traverses internally, it returns the
// number of child views of mDialogRootView, which leads to inconsistent parent values in the internal
// verification process of the system.
public int getModalChildCount() {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nit: consider adding a comment to explain the method

return mDialogRootView.getChildCount();
}

public View getModalChildAt(int index) {
return mDialogRootView.getChildAt(index);
}

@Override
public boolean dispatchPopulateAccessibilityEvent(AccessibilityEvent event) {
return false;
Expand Down Expand Up @@ -243,7 +246,7 @@ protected void setDialogBar(boolean isDarkIcon) {
lp.layoutInDisplayCutoutMode = WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_SHORT_EDGES;
window.setAttributes(lp);
sysUI = sysUI | View.SYSTEM_UI_FLAG_FULLSCREEN
| View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN | View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY;
| View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN | View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY;
} else if (mEnterImmersionStatusBar) {
sysUI = sysUI & ~View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR;
sysUI = sysUI & ~View.SYSTEM_UI_FLAG_LAYOUT_STABLE;
Expand Down
Loading