I'm using a NavigatorIOS for the routing of my app. I would like to display just the back button without any title or bar even translucent.
Is it possible ?
Or I must use another module ?
Currently, I have this :
<NavigatorIOS
ref='nav'
tintColor="white"
style={{flex: 1}}
initialRoute={{
title: 'Splash',
navigationBarHidden: true,
component: SplashScene
}}/>
Thanks a lot for your help,
Margot
You can pass translucent prop to NavigatorIOS's route, like so:
<NavigatorIOS
ref='nav'
tintColor="white"
style={{flex: 1}}
initialRoute={{
title: 'Splash',
navigationBarHidden: true,
translucent: true,
component: SplashScene
}}
/>
Related
The title is very confusing, but the explanation that I will give will be more clear.
I am creating one StackNavigator for my app, and I am defining one icon to be displayed on the header of one of my screens like so:
const navigator= createStackNavigator(
{
Initial: {
screen: Posts,
navigationOptions: {
title: "All Posts",
headerRight: () => {
return (
<TouchableOpacity style={{ padding: 5 }}>
<Feather name={"plus"} size={30} />
</TouchableOpacity>
);
},
},
},
Details: Details,
Create: Create,
},
{
initialRouteName: "Initial",
}
);
const App = createAppContainer(navigator);
export default () => {
return (
<Provider>
<App />
</Provider>
);
};
The problem is that I want to navigate the user to the Create screen when the user presses the icon that I am rendering on the right side of the header, but I do not know how to have access to the navigation.navigate() function that the navigator generates for all the screens. I know that I can define the header on the Posts' screen file, so I have access to the navigation.navigate() function, but I want to know if there is some way to do it on the App.js file.
EDIT
Reading the documentation I saw that the way that I am was creating the navigator is not what the official documentation recommends. I learned to make it like this by one old course, using React Navigation 4.x, and now with React Navigation 6.x I perceived the difference in the creation and changed the way that I was doing it on my app. You can check the documentation for the problem that I was having here
You can prepare your navigation option this way by sending props
options={(props) => ({
headerRight: () => <TouchableOpacity
onPress={()=>props.navigation.navigate('Screen')} style={{ padding: 5 }}>
<Feather name={"plus"} size={30} />
</TouchableOpacity>
})}
I had recently upgraded my react native project from ~0.28 to the most recent version (0.43.2) and for some reason my navigation bar no longer hides for me.
Here is the code (it is sitting in a TabBarIOS component):
<TabBarIOS.Item
selected={this.state.selectedTab === 'home'}
title='Home'
icon={require ('./Icons/IconImages/HomeTabIcon.png')}
onPress={
() => this._tabPressed('home')
}>
<NavigatorIOS
style={styles.container}
ref="nav"
interactivePopGestureEnabled={false}
initialRoute={{
title: 'Home',
component: HomeNavigationController,
navigationBarHidden: true, //this does nothing now
showTabBar: false, //this is to hide the bottom tabBar
passProps: {
...
},
}}/>
</TabBarIOS.Item>
Adding it outside initialRoute also does not work:
<NavigatorIOS
style={styles.container}
ref="nav"
interactivePopGestureEnabled={false}
initialRoute={{
title: 'Home',
component: HomeNavigationController,
showTabBar: false,
passProps: {...},
}}
navigationBarHidden={true} // does not work
/>
So, after trying to isolate the problem by stripping out everything and reducing it to its most basic form, I realized that it the problem wasn't in any code that I could find.
I initialized a new project from scratch and then re-added all my components and now it works just fine.
I have a TabBar with multiple TabBar.Item components. Each TabBar.Item component has it's own NavigatorIOS.
Here's an example of my code for my TabBar.js
<TabBarIOS>
<TabBarIOS.Item
selected={this.state.selectedTab === "profile"}
systemIcon={"most-viewed"}
onPress={() => this.setTab("profile")}
>
<NavigationBar title="Profile" component={Profile} passProps={{ showFilter: this.state.showFilter }} />
</TabBarIOS.Item>
</TabBarIOS>
Within my NavigationBar.js, I simply render out a NavigatorIOS
<NavigatorIOS
ref="nav"
initialRoute={{ ...this.props }}
style={{
flex: 1
}}
/>
When a User clicks the Filter button, this.state.showFilter is updated in TabBar. It's then passed down into NavigatonBar correctly, the render() function inside of NavigationBar is executed however,
At this point, my component won't re-render the component listed in initialRoute (Profile)
Is there any way to achieve this? When clicking the Filter I need to set an optional variable inside of Profile to hide and show the Filter Modal
I'm not sure whether there is a more elegant solution to this, but I have one that works.
I added the following code inside of NavigationBar:
shouldComponentUpdate(nextProps, nextState) {
this.refs.nav.replace({...nextProps})
return true;
}
This will force a reload of the initialRoute component.
I am using TabBarIOS.Item which has three options that each lead to a NavigatorIOS, I want to use the TabBar's so that when you click them it takes you to the first page of the NavigatorIOS as apposed to the last one before the user changed tabs, is that possible?
Thanks, Adam
So the answer is, is that TabBARIOS.item is an object and navigatorIOS is also an object, so you can give them both a ref. so they look like this.
<TabBarIOS.Item
title="partners"
selected={this.state.selectedTab === "Partners"}
icon={require("./App/assets/partnersIcon.png")}
onPress={this.partnersHandleChange.bind(this)} >
<View style={styles.main}>
<NavigatePartners ref="partners"></NavigatePartners>
</View>
</TabBarIOS.Item>
And the navigator looks like this
turn (
<NavigatorIOS
ref="navigator"
style={styles.mainContainer}
initialRoute={{
title: 'Partners',
component: Partners,
backButtonTitle: 'Back',
}}/>
Then you change the onclick to look like this
partnersHandleChange(){
if (this.state.selectedTab == "Partners")
{
this.refs.partners.refs.navigator.popToTop();
}
this.setState({
selectedTab: 'Partners',
})
};
I have created an app which uses the Navigator component, I'm wondering is there a way I can implement a header and footer component outside of the scene?
A screenshot of what I have currently:
http://i.stack.imgur.com/XHDKC.png
This first attempt was accomplished by making the header and footer a single component with absolute styles.
//index.js
<Navigator initialRoute={{id: 'home', title: window.title}}
renderScene={renderScene}
navigationBar={<DefaultHeader toggleSideMenu={this.toggleSideMenu}
route={route.id} />}/>
//DefaultHeader.js
<View style={styles.navContainer}>
<View style={styles.header}>
</View>
<View style={styles.footer} shouldUpdate={false}>
</View>
</View>
Although appeared to work, I was unable to click around anything within the scene due to the render order in React's Navigator component.
I decided to re-think my approach and fully separated navigation bars from the Navigator component. This relies on you passing down a routing function and any other route info.
routeTo: function (route) {
if (route.to == "back") {
this.refs.navigator.pop();
} else {
this.refs.navigator.push(route);
}
},
canGoBack: function () {
return this.refs.navigator && this.refs.navigator.getCurrentRoutes().length > 1
},
getDefaultRoute: function () {
return {id: 'home', title: window.title};
},
getCurrentRoute: function () {
if (this.refs.navigator) {
return _.last(this.props.navigator.getCurrentRoutes());
}
return this.getDefaultRoute();
},
render() {
return (
<View style={styles.container}>
<DefaultHeader routeTo={this.routeTo} route={this.getCurrentRoute()}
toggleSideMenu={this.toggleSideMenu}/>
<Navigator
ref="navigator"
initialRoute={this.getDefaultRoute()}
renderScene={renderScene}
/>
<DefaultFooter routeTo={this.routeTo} route={this.getCurrentRoute()}/>
</View>
)
}
Although it is pretty "hacky" - why don't you add a third view (expanding fully) between the header and footer and set onStartShouldSetResponder and onMoveShouldSetResponder to return false for both: the middle view and the navContainer view). See https://facebook.github.io/react-native/docs/gesture-responder-system.html. I am not sure if it will work but it might be worth trying.
The best way, however, would be to modify the Navigator component and add footer props and displaying there. It's pure javascript, so it should be fairly easy to do.
I am using RN 0.36 and I was able to workaround this by using the navigator height to margin the footer:
<View style={{flex: 1}}>
<ScrollView>
...
</ScrollView>
<View style={{
height: 40,
borderTopWidth: 1,
borderTopColor: colors.grey,
flex: 0,
marginBottom: Navigator.NavigationBar.Styles.General.TotalNavHeight
}}>
<Text>Footer</Text>
</View>
</View>
where my index files (ie index.ios.js) looks like
<NavigatorIOS
style={{flex: 1}}
initialRoute={{
title: ' ',
component: Main
}}
...
Check NavigatorIOS and Navigator