wix / wix/react-native-navigation
Android Hardware Back Button causes Blank Screen
Nobody has claimed this yet.
- Dominant language
- MDX
- Stars
- 13.2k
- Forks
- 2.6k
- Avg merge
- 6d 2h
- Merged PRs (30d)
- 1
Description
🐛 Bug Report
Only on Android, when the user uses the Hardware Back Button and they are at the landing screen, the Activity closes. Then when the application is started again I see a blank screen. This happens only if I use the hardware back. If I minimize the application using the hardware home button, then there are no issues.
I read somewhere that I should use the events().registerAppLaunchedListener but that doesn't get invoked.
Have you read the Contributing Guidelines on issues?
Yes, I have read them.
To Reproduce
- Create a blank application using the React Native CLI
- Install the latest version of the navigation library
- Create a Bottom Navigation
- As the first tab create a Stack Navigator
- Press the hardware back button on the phone
- Enter the application again
ERROR: Blank screen.
NOTES: I am using a legacy project that somebody else wrote and I am trying to maintain/update it.
The way the bottom tab bar is created is very weird to me. I found that this code causes the tab bar to appear, however, without this code the tab bar is missing:
// hide the tab bar when navigating to screens that are not in tabBarScreens
Navigation.events().registerCommandListener((name, params) => {
let componentNames = params &&
params.layout &&
params.layout.data && [params.layout.data.name]
componentNames =
componentNames ||
(params &&
params.layout &&
Array.isArray(params.layout) &&
params.layout
.map((layout) => layout.data && layout.data.name)
.filter((c) => c !== undefined))
if (componentNames && componentNames.length === 0) {
componentNames = undefined
}
componentNames =
componentNames ||
(params &&
params.layout &&
params.layout.children &&
params.layout.children
.map((child) => child.data && child.data.name)
.filter((c) => c !== undefined))
if (componentNames && componentNames.length === 0) {
componentNames = undefined
}
componentNames =
componentNames ||
(params &&
params.layout &&
params.layout.root &&
params.layout.root.children &&
params.layout.root.children
.map((child) => child.data && child.data.name)
.filter((c) => c !== undefined))
console.log({ name, params })
switch (name) {
case 'push':
case 'showModal':
if (componentNames && componentNames.length > 0) {
if (
getTabBarScreen(componentNames[componentNames.length - 1]) ===
undefined
) {
store.dispatch(setShouldBeVisible(false))
screenStack.push({
componentName: componentNames[componentNames.length - 1],
tabBarVisible: false,
})
} else {
screenStack.push({
componentName: componentNames[componentNames.length - 1],
})
}
}
break
case 'pop':
case 'dismissModal':
if (screenStack.length > 1) {
screenStack.pop()
}
break
case 'popToRoot':
screenStack = [screenStack[0]]
break
case 'setRoot':
case 'setStackRoot':
if (componentNames && componentNames.length > 0) {
screenStack = componentNames.map((c) => {
return { componentName: c }
})
}
break
}
})
The stack navigation is created as follows:
// This code is executed in the index.js file
let navStack = [
{
screenName: MainScreen.screenName(),
passProps: {
initial: true,
navigateToRunning: true,
},
},
]
const createNavigationStack = (screenList) => {
return screenList.map((item) => {
return {
component: {
name: item.screenName,
passProps: item.passProps,
options: {
animations: {
setStackRoot: {
enabled: false,
},
},
popGesture: false,
hardwareBackButton: {
dismissModalOnPress: true,
popStackOnPress: true,
bottomTabsOnPress: 'previous',
},
},
},
}
})
}
Navigation.setRoot(createNavigationStack(navStack))
I have no idea why things are done this way. The only workaround to my problem was to override the Native Back Handler and just disable it:
BackHandler.addEventListener('hardwareBackPress', () => true);
Expected behavior
I expect that the application will return to the last screen that was displayed when it is relaunched.
Actual Behavior
A Blank screen is shown
Your Environment
- React Native Navigation version: 7.30.2
- React Native version: 0.70.5
- Platform(s) (iOS, Android, or both?): Android 11
- Device info (Simulator/Device? OS version? Debug/Release?): Simulator + Samsung Galaxy S20 FE, both Debug and Release
Reproducible Demo
N/A, the code is proprietry.
Are you willing to resolve this issue by submitting a Pull Request?
- ✖️ Yes, I have the time, and I know how to start.
- ✖️ Yes, I have the time, but I don't know how to start. I would need guidance.
- ✅ No, I don’t have the time and I’m okay to wait for the community / maintainers to resolve this issue.
Contributor guide
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
Research direction
Start with the navigation setup in index.js and the Android hardwareBackButton options, then follow the listed reproduction steps on the reported React Native and Android versions. Compare the relaunch behavior with the Native Back Handler workaround; done means relaunching after the hardware Back Button does not show a blank screen.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- android, javascript, react-native
- Domain
- mobile-dev
- Issue type
- Bug
- Difficulty
- 4/5
- Estimated time
- 3-5 days
- Activity status
- Stale
- Clarity
- Needs clarification
- Newbie friendliness
- 25/100