-
Notifications
You must be signed in to change notification settings - Fork 24.3k
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
ListView (or perhaps ScrollView) disappears after running in background for several minutes #8607
Comments
I tried to revert the commit 329c716 manually, and now the issue occurs every time, no need for background waiting @nicklockwood will you have any time to check it? I'm trying to solve this issue to summit the new version to App Store, thanks I'll try to revert another commit 1048e5d |
Summary: The `removeClippedSubviews` feature works by umounting views from the hierarchy if they move outside the bounds of their parent. This was previously restricted to clipping views which had `overflow: hidden`, since we cannot efficiently check whether the subviews of a view go outside its bounds, and so clipping a view that has potentially overflowing children becomes an expensive recursive operation. The problem with this is that `overflow: visible` is the default, and it's not well documented nor easy to tell that `removeClippedSubviews` has been set up correctly (i.e. with all children having `overflow: hidden`). When I checked, I found that `removeClippedSubviews` was not working on any of the examples in UIExplorer, nor in several of our internal apps, because the views inside the ListView has `overflow: visible`. This was probably caused by an infra change at some point, but I'm not sure how long it's been broken. It's vanishingly unlikely that anyone would ever deliberately want subviews to overflow their bounds in this scenario, so I've updated the logic to simply ignore the `overflow` property and assume that views should be clipped if you are using the `removeClippedSubviews` property on the parent. Cons / Breaking changes: in some rare circumstances, a view might get clipped prematurely if its parent is outside the scrollview bounds, but it itself is inside. This doesn't occur in practice in any of our products, and could be worked around with additional wrapper views if it did. Pros: removeClippedSubviews is now much easier to use, and much more likely to work as intended, so most list-based apps should see a performance improvement. Reviewed By: javache Differential Revision: D3385316 fbshipit-source-id: 1c0064a4c21340a971ba80d794062a356ae6cfb3
still the save after turn off |
I'm encountering a similar problem after migrating RN from 0.28 to 0.29. I have a ListView off-screen which gets updated (render is called) due to an action occurring in another view. When navigating back to the ListView all items are invisible until I scroll the View up or down. The items seem to re-appear from the top of the screen. Edit: Turning off |
We had a similar problem with a ListView on a inactive route which did not render correctly. |
We have this same problem too. It usually happens when popping navigation back to an existing listview after the app was in the background. Can confirm that the problem started to occur after 0.28, in 0.29 and still in 0.30. |
Are you able to see this issue on simulator, or does it seem like device only? |
@majak The problem exists both in iOS simulator and on real device. It's reliable reproducible. |
BTW, turning off |
Same here, after popping route and going to ListView, it stays empty until you interact with it. |
Which navigator are you using? |
ExNavigator, not sure if I can set up a reproducible example, but I could try to set up screen share and give you the control so you can place breakpoints here and there ;) |
I can confirm i have seen this as well. Also using ExNavigator. |
If I won't manage to fix it, I might swizzle that method (in order to revert Nick changes) as I do really need to ship my app soon. But happy to help in anyway possible |
Oh cool, knowing it happens in environment with |
@grabbou that method doesn't even exist in rn 0.30.0.rc.0 or master anymore. @nicklockwood refactored everything shortly after that commit with 46c02b6, so it's even more obscure to manually revert back the offending changes. Anyone have suggestions on how to fix this in latest? |
@grabbou I have to and already revert Nick's commit 1048e5d to release my app, and it works well as before till now, (BTW I'm using 0.30RC0 will this commit reverted) |
@sjmueller The following is my local version of - (void)mountOrUnmountSubview:(UIView *)view withClipRect:(CGRect)clipRect relativeToView:(UIView *)clipView
{
if (view.clipsToBounds) {
// View has cliping enabled, so we can easily test if it is partially
// or completely within the clipRect, and mount or unmount it accordingly
if (!CGRectIsEmpty(CGRectIntersection(clipRect, view.frame))) {
// View is at least partially visible, so remount it if unmounted
if (view.superview == nil) {
[self remountSubview:view];
}
// Then test its subviews
if (CGRectContainsRect(clipRect, view.frame)) {
[view react_remountAllSubviews];
} else {
[view react_updateClippedSubviewsWithClipRect:clipRect relativeToView:clipView];
}
} else if (view.superview) {
// View is completely outside the clipRect, so unmount it
[view removeFromSuperview];
}
} else {
// View has clipping disabled, so there's no way to tell if it has
// any visible subviews without an expensive recursive test, so we'll
// just add it.
if (view.superview == nil) {
[self remountSubview:view];
}
// Check if subviews need to be mounted/unmounted
[view react_updateClippedSubviewsWithClipRect:clipRect relativeToView:clipView];
}
}
- (void)react_updateClippedSubviewsWithClipRect:(CGRect)clipRect relativeToView:(UIView *)clipView
{
// TODO (#5906496): for scrollviews (the primary use-case) we could
// optimize this by only doing a range check along the scroll axis,
// instead of comparing the whole frame
if (_reactSubviews == nil) {
// Use default behavior if unmounting is disabled
return [super react_updateClippedSubviewsWithClipRect:clipRect relativeToView:clipView];
}
if (_reactSubviews.count == 0) {
// Do nothing if we have no subviews
return;
}
if (CGSizeEqualToSize(self.bounds.size, CGSizeZero)) {
// Do nothing if layout hasn't happened yet
return;
}
// Convert clipping rect to local coordinates
clipRect = [clipView convertRect:clipRect toView:self];
clipView = self;
if (self.clipsToBounds) {
clipRect = CGRectIntersection(clipRect, self.bounds);
}
// Mount / unmount views
for (UIView *view in _reactSubviews) {
[self mountOrUnmountSubview:view withClipRect:clipRect relativeToView:clipView];
}
} |
Thanks for sharing @nihgwu, however I don't think you are on RN 0.30. As you can see below, the 0.30 lines don't match up with yours: Looks like your local version was before the refactor in 46c02b6! |
@sjmueller Sorry I didn't notice there is another commit after 1048e5d, BTW I'm using RN0.30RC0 😊 |
@majak any news here, I'm waiting to upgrade to the latest RN 😄 |
Reviewed By: mmmulani Differential Revision: D4081700 fbshipit-source-id: d4079138dc070565e475831e82651c9b2d5b8d59
Heads up: we've uncovered the linked solution (625c8cb & co.) doesn't work well with modals, so I've reverted the change on master until we come up with a proper fix 😞 |
@majak Bummer, was just going to comment that it works well in our app. Good you caught that case, though 👌 |
Who cares about modal 😔 |
@majak for most of the time, your commit works really well, but sometimes when I ? 2016?11?22??01:53?Martin Kralik <notifications@github.commailto:notifications@github.com> ??? Heads up: we've uncovered the linked solution (625c8cbhttps://github.com/facebook/react-native/commit/625c8cb83c7be01b1d5f646b70f8fb1d4c70a45c & co.) doesn't work well with modals, so I've reverted the change on master until we come up with a proper fix ? You are receiving this because you were mentioned. |
@majak none cares about modal!!! |
@nihgwu I'm still using 0.27 since I saw all these messed up things here. |
|
@majak FYI, I've upgraded to RN0.40RC0 and seems this issue has gone, I thought you reverted all your commits over clip commits, so I'm wrong? I've check the commit history, seems you've reverted all the related commits, then why I don't get this issue now |
@nihgwu yes I did revert everything. Could you bisect to figure out why it's working for you now? |
@majak Perhaps it's because I'm using Native Animated.event to handle scroll, I'll try to turn off native driver to check. UPDATE: not related to Native Animated.event, I switched to NavigationExperimental from Navigator in this version too, but still not sure if this change makes the issue gone, need more developers to report their status after they upgrade to RN0.40 |
Closing as ListView is deprecated in 0.43. Use FlatList. |
I am having the same issue with Anyone else still having the same issue? Still looking for a solution.. UPDATE:
I don't know if it's the most efficient solution, but it's the only one I found. If there is a better way to go about this from a performance stand point, please let us know @sahrens To reproduce the issue:
|
I need sticky Headers so I'm stuck using ListView @hramos. additionally, does setting |
React Native 0.44.0 (latest) has sticky header support for both iOS and Android in SectionList. |
removeClippedSubviews does not affect JavaScript so react rendering is the same and initial load/render time will be unaffected, but disabling it loses the native optimization to pull offscreen views out of the view hierarchy and scroll performance may suffer as a result. |
does this problem fix? i occur this at RN 0.41 with listView and navigator. |
I'm using the ScrollView as a
ViewPager
and placing ListView in it just like the F8 app does, and since I upgrade the RN to 0.29 and now 0.30RC0, I'm persecuted by this problem:navigate to the detail view from the list view ,then press the home button to make the app running in background, and then wait for several minutes to wake up the app, navigate back to the list view, the ListView (or perhaps or outer ScrollView) just disappears until I scroll it vertically or horizontally ( tap has no effect )
I have no idea what happened as it's OK before RN0.29, I've tested on all the 0.29 versions and the newest 0.30RC version they are all the same.
here is the demo:
The text was updated successfully, but these errors were encountered: