Closed oferRounds closed 4 years ago
@zmnv I saw this issue, but I don‘t think it’s the same... This relates to a native tab bar, the issue you refer to relate to a non-native tab bar
@oferRounds what is a 'native tab bar'?
You mean bottom navigation bar in android?
Yes, but only on iOS
On iOS it’s called TabBar
, and as react-native-navigation
is based on the native iOS’ TabBar
and Android‘s BottomNavigationBar
, then it’s a different story compared to react-navigation
JS solution
No matter iOS or Android. TabBar or BottomNavigationBar always inside <Navigation />
.
You just need to place your bottom sheet ABOVE <Navigation />
component. Outside of Navigation Stack like in https://github.com/brentvatne/bottom-sheet-example/blob/master/App.tsx#L201
Well react-native-navigation
works a bit differently, there’s no
@zmnv seems like there’s no good way to integrate your react-native-reanimated-bottom-sheet
with react-native-navigation
(see here: https://github.com/wix/react-native-navigation/issues/5789)
Perhaps we can change react-native-reanimated-bottom-sheet
in the way that it will always (by default) present the sheet on the front? i.e., on its native implementation (on iOS, perhaps setting the windowLevel
to Alert
)
It doesn't matter which navigation you use...
react-native-reanimated-bottom-sheet
is just view component
I see now that there is no native side... It does in the sense that it get presented bellow the tab bar... Perhaps it should use React Native‘s Modal
component?
was manage to solve the issue by wrapping the component in a Modal
component... Could be that this should be included in the component...
Hi, thank you for digging into this issue. Your problem seems to be caused entirely by react native navigation and that's why it has to be wrapped in a Modal component. Please use react navigation next time instead. I think that sums it up.
You can handle 'back' button on Android to close bottom sheet
AndroidBackHandler.tsx
import React, { PureComponent } from 'react';
import { BackHandler } from 'react-native';
import { NavigationEvents } from 'react-navigation';
type Props = {
onBackPress: () => void,
};
export class AndroidBackHandler extends PureComponent<Props> {
enabled = true;
backHandler: any;
componentDidMount() {
this.backHandler = BackHandler.addEventListener('hardwareBackPress', this.handleBackPress);
}
componentWillUnmount() {
this.backHandler.remove();
}
handleBackPress = () => {
if (this.enabled && this.props.onBackPress) {
this.props.onBackPress();
return true;
}
return false;
}
handleWillBlur = () => {
this.enabled = false;
}
handleWillFocus = () => {
this.enabled = true;
}
render() {
return (
<NavigationEvents
onWillFocus={this.handleWillFocus}
onWillBlur={this.handleWillBlur}
/>
);
}
}
@BrtqKr react-native-navigation is a popular library... Anyhow, wrap it in a modal solves the issue
@zmnv your last answer might be related to a different issue?
@oferRounds yes, it's good to put
So, when bottom sheet is opened hardware back button will hide it. You can put tab slider and handle 'routing' (not actually navigation, but still...) inside bottom sheet.
ps: <FadeInOut />
don't mount children if visible = false.
@oferRounds indeed it is, but when you use react native navigation your bottomsheet is going to be rendered with a different hierarchy and is going to be displayed as you described.
@oferRounds Do you mean modal like https://reactnavigation.org/docs/en/modal.html ? With transparent background.
@zmnv thanks – no, I mean https://github.com/react-native-community/react-native-modal
Care to share the boilerplate code used to achieve this @oferRounds ? I'm pretty sure there are other people facing this issue!
@mstaicu sorry missed your comment! Here it is:
<Modal
useNativeDriver = { true }
style = { styles.modal }
isVisible = { this.state.isPresentingReactionsPickerBottomsheet }
onBackButtonPress = { this.onReactionsPickerBottomSheetClose }
onBackdropPress = { this.onReactionsPickerBottomSheetClose }
>
<BottomSheet
ref = { this.onGetReactionsPickerBottomSheetRef }
snapPoints = { [USERS_REACTIONS_BOTTOM_SHEET_INITIAL_HEIGHT, USERS_REACTIONS_BOTTOM_SHEET_INITIAL_HEIGHT / 2, 0] }
initialSnap = { 1 }
overdragResistanceFactor = { 8 }
renderContent = { this.renderReactionsPickerContent }
renderHeader = { this.reactionsPickerBottomSheetHeader }
enabledInnerScrolling = { true }
// listening to both events, as `closeStart` not called when half-way opened (called only when completely open),
// but we do want start the transition as early as possible
onCloseStart = { this.onReactionsPickerBottomSheetClose }
onCloseEnd = { this.onReactionsPickerBottomSheetClose }
/>
</Modal>
The sheet can be opened by setting isPresentingReactionsPickerBottomsheet
to true, while closing it be listening the Modal’s callbacks: onBackButtonPress
and onBackdropPress
and running the same logic, but with false:
private onReactionsPickerBottomSheetClose = () => {
this.setState({ isPresentingReactionsPickerBottomsheet: false })
}
@mstaicu sorry missed your comment! Here it is:
<Modal useNativeDriver = { true } style = { styles.modal } isVisible = { this.state.isPresentingReactionsPickerBottomsheet } onBackButtonPress = { this.onReactionsPickerBottomSheetClose } onBackdropPress = { this.onReactionsPickerBottomSheetClose } > <BottomSheet ref = { this.onGetReactionsPickerBottomSheetRef } snapPoints = { [USERS_REACTIONS_BOTTOM_SHEET_INITIAL_HEIGHT, USERS_REACTIONS_BOTTOM_SHEET_INITIAL_HEIGHT / 2, 0] } initialSnap = { 1 } overdragResistanceFactor = { 8 } renderContent = { this.renderReactionsPickerContent } renderHeader = { this.reactionsPickerBottomSheetHeader } enabledInnerScrolling = { true } // listening to both events, as `closeStart` not called when half-way opened (called only when completely open), // but we do want start the transition as early as possible onCloseStart = { this.onReactionsPickerBottomSheetClose } onCloseEnd = { this.onReactionsPickerBottomSheetClose } /> </Modal>
The sheet can be opened by setting
isPresentingReactionsPickerBottomsheet
to true, while closing it be listening the Modal’s callbacks:onBackButtonPress
andonBackdropPress
and running the same logic, but with false:private onReactionsPickerBottomSheetClose = () => { this.setState({ isPresentingReactionsPickerBottomsheet: false }) }
Is it swipable with modal? I'm using react-native-modal with react-native-reanimated-bottom-sheet and its not!
@Abdulaev, as far as I know, react-native-modal
is a wrapper around the Modal
component exposed by react-native
, which seeks to add missing functionality. It does not solve any of the existing issues regarding the usage of the bottom sheet in the modal. The main issue, for me at least, is the fact that the fix introduced in this pull request does not work when the bottom sheet is used inside a modal which is then rendered on a screen that is rendering lots of times. The result is that it auto dismisses the modal that contains the bottom sheet. I will respond to this thread if I have any updates regarding fixes or workarounds
I migrated to: https://github.com/jeremybarbet/react-native-modalize
@zmnv thanks – no, I mean https://github.com/react-native-community/react-native-modal
by wrapping BottomSheet by Modal - react-native-reanimated-bottom-sheet gesture is not working like dragging and droping.
react-native-portalize the key guys!!!! Just wrap the tabnavigation in the Host component and after any place in the application wrap your bottomsheet component in a Portal component. Works like hell!!!!
react-native-portalize the key guys!!!! Just wrap the tabnavigation in the Host component and after any place in the application wrap your bottomsheet component in a Portal component. Works like hell!!!!
Works beautifully. Thank you!
Hi, I’m using
react native navigation
– everything works great, except for the fact the bottom sheet is presented beneath the tab bar. Is there a way to make it show above it?Thank you!