Fix unresponsive UI bug due to sloppy swizzling

Summary:
If you're going to swizzle, you have to be very careful to call the original version of the swizzled method!

The blame diff for this regression is D21285438.

In this case we would fail to call `swizzle_removeFromSuperview` if the view being removed was a child of a window. Thus the view would never be removed.

In practice, this manifested as `UITransitionView` instances being left around. These would block taps, leading to developer reports of unresponsive UI.

Reviewed By: priteshrnandgaonkar

Differential Revision: D21509692

fbshipit-source-id: e400c55232c44e9cd3f478eb2b456222c0bc6576
This commit is contained in:
Adam Ernst
2020-05-11 16:15:17 -07:00
committed by Facebook GitHub Bot
parent 2dcb73aba5
commit 029122ce7a

View File

@@ -63,17 +63,20 @@ static auto shouldInvalidateRootNode(UIView* view) -> bool {
}
- (void)swizzle_removeFromSuperview {
UIView* oldSuperview = self.superview;
// Be careful that we always call the swizzled implementation
// before any early returns or mischief below!
[self swizzle_removeFromSuperview];
id<SKInvalidationDelegate> delegate =
[SKInvalidation sharedInstance].delegate;
if (delegate != nil && self.superview != nil) {
if (shouldInvalidateRootNode(self.superview)) {
if (delegate != nil && oldSuperview != nil) {
if (shouldInvalidateRootNode(oldSuperview)) {
[delegate invalidateRootNode];
return;
}
[delegate invalidateNode:self.superview];
[delegate invalidateNode:oldSuperview];
}
[self swizzle_removeFromSuperview];
}
@end