Fix modals freezing on close with Nodes
Summary: Modals were doing nothing (and sometimes crashing) when they were being closed. The reason for this was due to the fact that the parent being removed was not necessarily the view's parent. Consequently, trying to inform said parent that its child was removed failed, because said parent wasn't a view, and therefore had no record in mViewsToTags. Reviewed By: sriramramani Differential Revision: D3928850
This commit is contained in:
parent
a61766dbac
commit
fc10d0d3bf
|
@ -342,9 +342,7 @@ public class FlatUIImplementation extends UIImplementation {
|
|||
--moveFromIndex;
|
||||
moveFromChildIndex = (moveFromIndex == -1) ? -1 : mMoveProxy.getMoveFrom(moveFromIndex);
|
||||
} else if (removeFromChildIndex > moveFromChildIndex) {
|
||||
removeChild(
|
||||
removeChildAt(parentNode, removeFromChildIndex, prevIndex),
|
||||
parentNode.getReactTag());
|
||||
removeChild(removeChildAt(parentNode, removeFromChildIndex, prevIndex), parentNode);
|
||||
prevIndex = removeFromChildIndex;
|
||||
|
||||
--removeFromIndex;
|
||||
|
@ -361,19 +359,38 @@ public class FlatUIImplementation extends UIImplementation {
|
|||
* Unregisters given element and all of its children from ShadowNodeRegistry,
|
||||
* and drops all Views used by it and its children.
|
||||
*/
|
||||
private void removeChild(ReactShadowNode child, int parentReactTag) {
|
||||
private void removeChild(ReactShadowNode child, ReactShadowNode parentNode) {
|
||||
if (child instanceof FlatShadowNode) {
|
||||
FlatShadowNode node = (FlatShadowNode) child;
|
||||
if (node.mountsToView() && node.isBackingViewCreated()) {
|
||||
int tag = -1;
|
||||
|
||||
// this tag is used to remove the reference to this dropping view if it it's clipped.
|
||||
// we need to figure out the correct "view parent" tag to do this. note that this is
|
||||
// not necessarily getParent().getReactTag(), since getParent() may represent something
|
||||
// that's not a View - we need to find the first View (what would represent
|
||||
// view.getParent() on the ui thread), which is what this code is finding.
|
||||
ReactShadowNode tmpNode = parentNode;
|
||||
while (tmpNode != null) {
|
||||
if (tmpNode instanceof FlatShadowNode) {
|
||||
FlatShadowNode flatTmpNode = (FlatShadowNode) tmpNode;
|
||||
if (flatTmpNode.mountsToView() && flatTmpNode.isBackingViewCreated()) {
|
||||
tag = flatTmpNode.getReactTag();
|
||||
break;
|
||||
}
|
||||
}
|
||||
tmpNode = tmpNode.getParent();
|
||||
}
|
||||
|
||||
// this will recursively drop all subviews
|
||||
mStateBuilder.dropView(node, parentReactTag);
|
||||
mStateBuilder.dropView(node, tag);
|
||||
removeShadowNode(node);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
for (int i = 0, childCount = child.getChildCount(); i != childCount; ++i) {
|
||||
removeChild(child.getChildAt(i), child.getReactTag());
|
||||
removeChild(child.getChildAt(i), child);
|
||||
}
|
||||
|
||||
removeShadowNode(child);
|
||||
|
|
|
@ -11,6 +11,8 @@ package com.facebook.react.flat;
|
|||
|
||||
import javax.annotation.Nullable;
|
||||
|
||||
import java.util.ArrayList;
|
||||
|
||||
import android.util.SparseIntArray;
|
||||
import android.view.View;
|
||||
import android.view.ViewGroup;
|
||||
|
@ -207,8 +209,12 @@ import com.facebook.react.uimanager.UIViewOperationQueue;
|
|||
|
||||
private final SparseIntArray mViewsToDrop;
|
||||
|
||||
private DropViews(SparseIntArray viewsToDrop) {
|
||||
mViewsToDrop = viewsToDrop;
|
||||
private DropViews(ArrayList<Integer> viewsToDrop, ArrayList<Integer> parentsForViewsToDrop) {
|
||||
SparseIntArray sparseIntArray = new SparseIntArray();
|
||||
for (int i = 0, count = viewsToDrop.size(); i < count; i++) {
|
||||
sparseIntArray.put(viewsToDrop.get(i), parentsForViewsToDrop.get(i));
|
||||
}
|
||||
mViewsToDrop = sparseIntArray;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -478,8 +484,10 @@ import com.facebook.react.uimanager.UIViewOperationQueue;
|
|||
new SetPadding(reactTag, paddingLeft, paddingTop, paddingRight, paddingBottom));
|
||||
}
|
||||
|
||||
public void enqueueDropViews(SparseIntArray viewsToDrop) {
|
||||
enqueueUIOperation(new DropViews(viewsToDrop));
|
||||
public void enqueueDropViews(
|
||||
ArrayList<Integer> viewsToDrop,
|
||||
ArrayList<Integer> parentsOfViewsToDrop) {
|
||||
enqueueUIOperation(new DropViews(viewsToDrop, parentsOfViewsToDrop));
|
||||
}
|
||||
|
||||
public void enqueueMeasureVirtualView(
|
||||
|
|
|
@ -51,7 +51,8 @@ import com.facebook.react.uimanager.events.EventDispatcher;
|
|||
|
||||
private final ArrayList<FlatShadowNode> mViewsToDetachAllChildrenFrom = new ArrayList<>();
|
||||
private final ArrayList<FlatShadowNode> mViewsToDetach = new ArrayList<>();
|
||||
private final SparseIntArray mViewsToDrop = new SparseIntArray();
|
||||
private final ArrayList<Integer> mViewsToDrop = new ArrayList<>();
|
||||
private final ArrayList<Integer> mParentsForViewsToDrop = new ArrayList<>();
|
||||
private final ArrayList<OnLayoutEvent> mOnLayoutEvents = new ArrayList<>();
|
||||
private final ArrayList<UIViewOperationQueue.UIOperation> mUpdateViewBoundsOperations =
|
||||
new ArrayList<>();
|
||||
|
@ -132,8 +133,9 @@ import com.facebook.react.uimanager.events.EventDispatcher;
|
|||
mOnLayoutEvents.clear();
|
||||
|
||||
if (mViewsToDrop.size() > 0) {
|
||||
mOperationsQueue.enqueueDropViews(mViewsToDrop);
|
||||
mOperationsQueue.enqueueDropViews(mViewsToDrop, mParentsForViewsToDrop);
|
||||
mViewsToDrop.clear();
|
||||
mParentsForViewsToDrop.clear();
|
||||
}
|
||||
|
||||
mOperationsQueue.enqueueProcessLayoutRequests();
|
||||
|
@ -141,7 +143,8 @@ import com.facebook.react.uimanager.events.EventDispatcher;
|
|||
|
||||
/* package */ void removeRootView(int rootViewTag) {
|
||||
// Note root view tags with a negative value.
|
||||
mViewsToDrop.put(-rootViewTag, -1);
|
||||
mViewsToDrop.add(-rootViewTag);
|
||||
mParentsForViewsToDrop.add(-1);
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -229,7 +232,8 @@ import com.facebook.react.uimanager.events.EventDispatcher;
|
|||
* @param node The node to drop the backing view for.
|
||||
*/
|
||||
/* package */ void dropView(FlatShadowNode node, int parentReactTag) {
|
||||
mViewsToDrop.put(node.getReactTag(), parentReactTag);
|
||||
mViewsToDrop.add(node.getReactTag());
|
||||
mParentsForViewsToDrop.add(parentReactTag);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
Loading…
Reference in New Issue