Repository navigation
Android: going back re-attaches and redraws the whole covered screen (hide instead of remove halves the worst back frame) #5012
enzomanuelmangano
started this conversation in
Ideas
Replies: 0 comments
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
Note
Written by Claude Opus 5.5 on behalf of Enzo (@enzomanuelmangano).
The problem
On Android, going back in a native stack drops frames when the screen underneath is heavy. When a screen is pushed,
ScreenStackremoves the fragment of the screen it covers (transaction.remove,android/.../legacy/ScreenStack.kt). Its views leave the window and Android drops their display lists. Going back adds the fragment again, so the first frame of the pop re-attaches and redraws the whole screen underneath.Measurements
Reproduction: https://github.com/enzomanuelmangano/repro-lab/tree/main/demos/screens-android-back-reattach. The covered screen has ~200 translucent views and a Skia canvas, and the pushed screen is light. Redmi Note 8 Pro, release build, 8 pops per run, two interleaved runs per build:
Before / after
Android's "Profile GPU rendering" bars right after the back. Each bar is one frame, and the green line is 16 ms. On the left, the tall blue/green bars are the covered screen being re-recorded and redrawn during the pop.
Video of the back, 3× slower: https://github.com/enzomanuelmangano/repro-lab/blob/main/media/screens-android-back-reattach.mp4
The idea
Hide the covered fragment (
transaction.hide) instead of removing it, and show it again on the way back. Preloaded (INACTIVE) screens and fragments that were never added are still removed. The change is about 30 lines inScreenStack.kt, plus two lines inScreenFragment/ScreensAnimation. A hidden fragment stays resumed, so those two places treatisHiddenas disappearing.Diff against 4.30.0: enzomanuelmangano/repro-lab@main...fix/screens-android-back-reattach
Trade-offs I know of:
onPause. The appear/disappear events are kept correct by theisHiddenchecks above, but code that relies on fragment lifecycle callbacks would see a difference.We've shipped this as a patch in a production app (v4 stack) for a few days. Given the focus on the v5 stack: is this something you'd consider for v4, maybe behind an option? Or does the v5 Android stack already avoid the re-attach? If it's of interest, I'm happy to open a PR in whatever shape you prefer.
All reactions