benevbright / react-navigation-collapsible Goto Github PK
View Code? Open in Web Editor NEWAn extension of react-navigation that makes your header collapsible.
License: MIT License
An extension of react-navigation that makes your header collapsible.
License: MIT License
I wanna call a class instead of a const (like you used in your examples)
When I change ExtraHeader from a const to a class, nothing happens, nothing is displayed, and there is no error message. I am gonna need my class for sure. Would you help me ?
const collapsibleParams = {
extraHeader: ExtraHeader,
extraHeaderStyle: {
height: 50,
backgroundColor: "#061"
}
};
export default withCollapsible(SearchEngine, collapsibleParams);
In example if default show screen withCollapsible not MenuScreen (my app show withCollapsible in first screen) will get error below:
const routeConfig = {
S0_DefaultHeader: { screen: S0_DefaultHeader },
S1_ExtraHeader: { screen: S1_ExtraHeader },
S2_DefaultHeaderForTab: { screen: S2_DefaultHeaderForTab },
S3_ExtraHeaderForTab: { screen: S3_ExtraHeaderForTab },
DetailScreen: { screen: ContextScreen },
};
thank you!
how can i do fix problem with performace?
when i use two tabs scroable the application is slow, not so much, but has a little problem.
Hello,
first of all, @benevbright congratulations for the great work done so far!
My issue is not about problem or bug, but it is a possible enhancement.
I want to reduce the scroll amount and then reduce the time I wait for collapse extra header.
I tried to find a way to achieve this looking at the file index.js
and I found this at line 35:
const safeBounceHeight = Platform.select({ios: 300, android: 100, web: 200});
For example, if I set safeBounceHeight = 0
I get the desired result, also because in my AnimatedFlatList
I put bounces={false}
.
It could be an idea to have a param to set up in collapsibleParams
for a custom safeBounceHeight
value or any other param that help to reduce scroll amount and quickly collapse custom extra header.
I have a theme object with a bunch of colors passed through the screenProps of my navigator.
I'm having a trouble thinking of a way of changing the collapsibleBackgroundStyle based on this? I can access the screenProps from the collapsibleComponent itself but how would I access it within withCollapsible
so for example
withCollapsible(Screen, {
collapsibleComponent: ExtendedHeader,
collapsibleBackgroundStyle: {
height: 60,
backgroundColor: '#fff' // I'd like to use the user theme here
}
});
hi @benevbright , thanks for your great work.
i try to use it with rnw, but looks not good.
this lib give me a warning
Animated: `useNativeDriver` is not supported
and some error
inputRange must be monotonically increasing ,NaN
i will try to update to use hooks and react reanimated.
=)
I'm playing around with the Material Tab Screen example but I noticed it works slightly different than what I've seen in other apps using a similar approach.
Let me explain myself. Go to that screen and collapse the header in the first tab, then navigate to the second tab, the header will reappear. Go back an forth from tab 1 to tab 2 and back to reproduce.
Is there a way to disable that behavior? I expect the header's height/position to not depend on the selected tab at all, if it's collapsed for one tab it should remain collapsed for all of them.
I am trying to change the default class state with setState from the const ExtraHeader but this is impossible.
Warning: Can't call setState on a component that is not yet mounted. This is a no-op, but it might indicate a bug in your application. Instead, assign to this.state
directly or define a state = {};
class property with the desired state in the SearchEngine component.
I even put the const inside my default class just to be sure, nothing works
In your example you define the const ExtraHeader like this below
const ExtraHeader = (/*{navigation}*/) => (
<View style={{width: '100%', height: '100%', paddingHorizontal: 20, paddingVertical: 10}}>
<View style={{backgroundColor: 'white', flex: 1, borderRadius: 15, justifyContent: 'center', alignItems: 'center'}}>
<Text style={{color: 'gray'}}>Search Here</Text>
</View>
</View>
);
Have you ever tried to put an onPress in the Text balise.
<Text
style={{color: 'gray'}}
onPress={() => {
this.setState({ searchState: "coucou" });
}}>
Search Here
</Text>
This won't work. Do you have an alternative ?
The collapsible header works fine when using the default header component by react navigation. However when I try to implement my own custom header component the collapsible animation of the header didn't workout.
Here is my full custom header component below:
import React from 'react'
import { StyleSheet, Text, View, TouchableOpacity } from 'react-native'
import { Icon } from 'react-native-elements'
import PropTypes from 'prop-types'
import { Header } from 'react-navigation';
import { COLOR } from '../config/styles'
const styles = StyleSheet.create({
centerRow: {
alignItems: 'center',
backgroundColor: 'transparent',
flex: 2,
flexDirection: 'row',
justifyContent: 'center',
},
container: {
flexDirection: 'row',
height: Header.HEIGHT,
justifyContent: 'center',
marginLeft: 10,
marginRight: 10
},
icon: {
justifyContent: 'flex-start',
marginTop: 2.8,
},
iconContainer: {
alignSelf: 'center',
},
leftRow: {
backgroundColor: 'transparent',
flex: 1,
flexDirection: 'row',
justifyContent: 'flex-start',
},
logoutText: {
color: COLOR.blue,
fontSize: 18,
fontWeight: '400',
},
rightRow: {
alignItems: 'center',
backgroundColor: 'transparent',
flex: 1,
flexDirection: 'row',
justifyContent: 'flex-end',
},
titleText: {
color: 'black',
fontSize: 18,
fontWeight: '400',
},
})
const Nav = ({ title, navigation, leftIcon, onPressRight, rightName }) => (
<View style={{ backgroundColor: 'white' }}>
<View style={styles.container}>
<View style={styles.leftRow}>
{/* <Icon
size={34}
type="ionicon"
name="ios-arrow-back"
underlayColor="transparent"
underlineColorAndroid="transparent"
hitSlop={{ top: 15, bottom: 15, left: 15, right: 15 }}
color={COLOR.blue}
iconStyle={styles.icon}
containerStyle={styles.iconContainer}
onPress={() => navigation.goBack(null)}
{...leftIcon}
/> */}
</View>
<View style={styles.centerRow}>
<Text style={styles.titleText} numberOfLines={1}>
{title}
</Text>
</View>
<TouchableOpacity
style={styles.rightRow}
backgroundColor="transparent"
onPress={() => onPressRight()}
>
<Text style={styles.logoutText}>{rightName}</Text>
</TouchableOpacity>
</View>
</View>
)
Nav.propTypes = {
title: PropTypes.string.isRequired,
navigation: PropTypes.object.isRequired,
leftIcon: PropTypes.object,
rightName: PropTypes.string,
onPressRight: PropTypes.func
}
Nav.defaultProps = {
leftIcon: {},
}
export default Nav
and in my Screen.js
class Settings extends Component {
static navigationOptions = ({ navigation }) => {
const { params = {} } = navigation.state;
return {
header: ( // This didn't workout
<Nav
title="Settings"
navigation={navigation}
onPressRight={params.handleLogout}
rightName="Log out"
leftIcon={{
type: 'ionicon',
name: 'md-list',
size: 26,
}}
/>
)
}
}
...
am I missing some configuration or implementation? Thanks
Hi,
Great job, this collapsible feature works well.
I have an issue though when inserting a drawer navigator in between StackNavigator and MaterialTabNavigator, just like this :
https://readybytes.in/blog/how-to-integrate-tabs-navigation-drawer-navigation-and-stack-navigation-together-in-react-navigation-v2
When making MaterialTabNavigator collapsible, there is an extra space between header and tabs (see screenshot).
If I remove collapsible options, it works well (but no collapsing of course)
Thanks
Hello,
Great library btw. So on iOS this works perfectly for my use case, but on android the header is misaligned and opacity is wrong for default.
I was able to reproduce this issue in this snack - https://snack.expo.io/@benevbright/react-navigation-collapsible - with the following changes
const ExtraHeader = ({navigation}) => {
const { searchText } = navigation.state.params ? navigation.state.params : {};
return (
<View style={{width: '100%', height: '100%', paddingHorizontal: 20, paddingVertical: 10}}>
<View style={{backgroundColor: 'white', flex: 1, borderRadius: 15, justifyContent: 'center'}}>
<Text>TESTT</Text>
</View>
</View>
);
}
const collapsibleParams = {
extraHeader: ExtraHeader,
extraHeaderStyle: {
height: 150,
backgroundColor: '#061'
}
}
How to reproduce:
Collapsible header works fine, but when I do pull to refresh on AnimatedList, it hides back and does not show until I normally scroll down the list and come back up. Anyone else facing this issue? Please help me with this.
This component woks very good, but i have one problme, my tabs is slow, i dont kwnow if other componnent is imcompatible withe this.. i would like help.
my package.json
{
"name": "AppChat",
"version": "0.1.0",
"private": true,
"devDependencies": {
"babel-preset-react-native-stage-0": "^1.0.1",
"jest": "^23.5.0",
"jest-react-native": "^18.0.0",
"react-devtools": "^3.2.3",
"react-test-renderer": "16.3.1",
"remote-redux-devtools": "^0.5.13",
"remotedev-server": "^0.2.5"
},
"scripts": {
"start": "react-native start",
"keystore-release": "keytool -genkey -v -keystore my-release-key.keystore -alias my-key-alias -keyalg RSA -keysize 2048 -validity 10000",
"bundle-release-android": "react-native bundle --platform android --dev false --entry-file index.js --bundle-output android/app/src/main/assets/index.android.bundle --assets-dest android/app/src/main/res/",
"bundle-release2-android": "react-native bundle --platform android --dev false --entry-file index.js --bundle-output android/app/build/intermediates/assets/release/index.android.bundle --assets-dest /android/app/build/intermediates/res/merged/release",
"bundle-debug-android": "react-native bundle --platform android --dev true --entry-file index.js --bundle-output android/app/src/main/assets/index.android.bundle --assets-dest android/app/src/main/res/",
"build-release-android": "cd android && gradlew assembleRelease",
"build-debug-android": "cd android && gradlew assembleDebug",
"android": "react-native run-android",
"ios": "react-native run-ios",
"test": "jest",
"reset": "watchman watch-del-all && react-native start --reset-cache",
"react-devtool": "react-devtools",
"redux-devtool": "remotedev --hostname=localhost --port=8000 --injectserver=reactnative",
"redux-devtool-revert": "remotedev --revert=reactnative"
},
"jest": {
"preset": "react-native"
},
"dependencies": {
"axios": "^0.18.0",
"native-base": "^2.7.2",
"react": "16.3.1",
"react-native": "^0.55.4",
"react-native-elements": "^1.0.0-beta5",
"react-native-fbsdk": "^0.7.0",
"react-native-firebase": "^4.3.8",
"react-native-google-signin": "^1.0.0-rc3",
"react-native-material-ui": "^1.30.1",
"react-native-vector-icons": "^5.0.0",
"react-navigation": "^2.11.2",
"react-navigation-collapsible": "^0.2.12",
"react-navigation-redux-helpers": "^2.0.5",
"react-redux": "^5.0.7",
"redux": "^4.0.0",
"redux-thunk": "^2.3.0"
}
}
My extruture of navigation:
StackNavigator->DrawerNavigator->StackNavigator(Collapsible)->MaterialTopTabNavigator
Hi, My navigation configuration is deeply nested which is maybe causing trouble to implement collapsible headers.
react-navigation version:1.5.11
react-navigation-collapsible:0.2.18
Does the library work with react-navigation v1 ?
Can provide with the configs if it is intended to work with react-navigation v1
Thanks for creating this. Very useful!
Please help how can we use this for WebView
Many popular apps have been using this behavior.
Transition between big header and regular header
Hi,
First let me say that this is an amazing package, something that should have been part of the original React Navigation. It is a very common pattern to hide navigation elements in long scrolls to maximize screen real estate for the content.
This is more of a question, do you plan to introduce support for the tabbar along with the header, usually in apps the structure is header, content, tabs (IOS mostly) and while scrolling the both header and tabbar hides out of view at the same time?
react-navigation v5 will come with TS.
It's time.
I followed your example and I want to try something out, I want to call an event in the TopTabNavigator navigation options,
headerLeft: <Icon name='navicon' size={35} color='white' style={{padding: 10}} onPress={()=> this.props.go()}/>
buh i get this error Cannot read property 'go' of undefined.
const collapsibleParams = {
collapsibleComponent: A, //A is a Component
collapsibleBackgroundStyle: {
height: 150,
backgroundColor: '#333743'
}
}
export default connect(mapStateToProps, mapDispatchToProps)(withCollapsibleForTab(TopTabNavigator, collapsibleParams));
I am using this in a MaterialTopTabNavigator with a SectionList. The SectionList sticky headers do not seem to stick. It looks like they might actually be sticking, but are hidden from view underneath the tabs.
I'm trying to build something similar to Extra Header (Search Bar)
example but I want to hide my header and leave the search bar visible
I can't get to work collapsible header, if stack navigator it located inside bottom tab navigator.
New iPhone came out and with current code of this module and react-navigation, it won't work correctly.
It looks like the PR for it is ready to merge on react-navigation. I will do the same thing after it's merged.
Steps for reproduction:
<StackNavigator key='navigator'/>,
to <StackNavigator key='navigator' persistenceKey="navigator" />,
Application launched on previously opened screen, but header is not collapsible.
P.S. Thank you for this awesome library :)
🚨 You need to enable Continuous Integration on all branches of this repository. 🚨
To enable Greenkeeper, you need to make sure that a commit status is reported on all branches. This is required by Greenkeeper because it uses your CI build statuses to figure out when to notify you about breaking changes.
Since we didn’t receive a CI status on the greenkeeper/initial
branch, it’s possible that you don’t have CI set up yet. We recommend using Travis CI, but Greenkeeper will work with every other CI service as well.
If you have already set up a CI for this repository, you might need to check how it’s configured. Make sure it is set to run on all new branches. If you don’t want it to run on absolutely every branch, you can whitelist branches starting with greenkeeper/
.
Once you have installed and configured CI on this repository correctly, you’ll need to re-trigger Greenkeeper’s initial pull request. To do this, please delete the greenkeeper/initial
branch in this repository, and then remove and re-add this repository to the Greenkeeper App’s white list on Github. You'll find this list on your repo or organization’s settings page, under Installed GitHub Apps.
Hi, thank you for this library! I love it,
How could i prevent from immediately collapsing the header if the scroll is not yet at the top part of a particular tab?
Let say, I'm swiping-up to close-collapse the header, then after reaching the bottom part, i swipe-down go to the top part of the current tab but I dont want the header to open-collapse yet NOT UNTILL the scroll reached the top part of that tab.
similar to this....
https://imgur.com/a/Nuf46xP
(on the second time he swipe to the lowest part of the current tab then he swipe bottom to scroll up the tab but the header remain closed until the scroll reaches the upper part of the tab, that's the only time the collapsing of header will take effect, how to achieve that using your library?)
I'm testing the latest changes and so far everything work as expected, really nice job! A few questions here so I can further tweak this lib for my app.
Is there a workaround for the flickering bug in Android (reported in #62)? Have you used this lib on production already with this bug? It's pretty annoying and it looks like it won't be fixed anytime soon by the RN team (the bug was reported back in 2017).
It would be nice to have a prop to disable the header opacity animation (ie, remove the opacity in line 89)
More importantly, why is the content below the header hidden immediately after you start scrolling? I expect it to remain visible until the header is fully collapsed/hidden or at least to have a prop to enable that. Any way to disable this? I'm trying to change this behavior myself but I'm not yet sure what changes are needed or what lines are really responsible for this.
We need to support react-navigation v3.
But it's just released and it does not seem to be stable.
pre-release on npm: react-navigation-collapsible@next
Is it currently possible in the library to have a variable height for the collapsable header?
BIGGER PICTURE: What I'm trying to achieve is essentially an instagram profile layout with a header at the top of the page containing the user's information and then a set of tabs which contain FlatLists of a users' uploaded images WITH an infinite scroll...
(Just random image off the internet)
There is an issue with having a FlatList inside a ScrollView: facebook/react-native#22008
I've tried several approaches but now what I'm thinking is to have a createMaterialTopTabNavigator
with the FlatLists in their separate screens. Then when you scroll on either screen, the header at the top scrolls up...
PROBLEM 1. - The height of the user details at the top may be variable based? This is because if you are looking at your own profile or the profile of someone else, then the height may change. (One solution would be of course to redesign so that they are not... But I'm not looking for that at the moment).
PROBLEM 2. - I'd like to pull to refresh on the whole page and reload the data inside the top panel AND the data inside the Animated.FlatList.
I appreciate that this seems like a lot of issues in one - but I think a lot of people will be wanting this same solution.
Hello friend. At first I must say an awesome job you are doing ! I am trying to create this : https://i.stack.imgur.com/tW209.gif , I tried to do the same as material tab and have few issues. First one is that if I am on TAB1 and scroll, and switch to TAB2 with swipe header return down with some not smooth effect. But if I am on TAB1 and press TAB2 without swipping it works like charm and I can not see padding top ( that is issue nr 2) . Anyway if you have time to give some advice what would be best way to achieve it it would be great!
I am confused about the extra height for ios devices. If I use react-navigation-collapsible for an I-Phone-X Emulator, my header is bigger than it should be. I looked into the code and found this function
const getStatusBarHeight = isLandscape => {
if (Platform.OS === 'ios') {
if (isLandscape) return 0;
return IS_IPHONE_X ? 44 : 20;
} else if (Platform.OS === 'android') return androidStatusBarHeight;
else return 0;
The function is called to set the height of the header. Why does an ios-device gets extra height especially iphoneX, if there is no landscape mode?
I'd like to use a box shadow on the header much like how the default react-navigation header looks on android. Is there a way I can do this? styling the collapsiblecomponent doesn't help because while it looks fine when expanded, you lose the shadow when collapsed
Hi!
Loved your component. I use it in Expo. But there are questions:
Is it possible to customize titles, for example, to add icons? I started trying to do it through a function, but an error occurred.
Is it possible to make TabBar above a photo? Then if you make a translucent background for the panel, it can be beautifully. I thought to do it through a negative marginTop, but the panel shifted under the photo.
For Extra Header With Tab (e.g. Facebook Group), if the list below is short, for example, 4-8 items, then it does not scroll. For small lists, ScrollView doesn't work here either. setSafeBounceHeight did not help. Maybe I did not use it correctly?
I think it will be useful to others.
Thank
Just change line 14 import { Constants } from 'expo';
for import Constants from 'expo-constants';
It does not detect the end of scroll and make final action.
At the result, when we scroll to make it half collapsed, it stays there.
So we detect onScrollEndDrag
of ScrollView and execute final animation.
reference:
https://medium.com/appandflow/react-native-collapsible-navbar-e51a049b560a
Does this library support createBottomTabNavigation to show collapsible child tab toolbar?
I want to use the local module on Example, like using npm install ./..
But the packger gave me error
error: bundling failed: Error: Unable to resolve module `react` from `/Users/bright/Dev/react-navigation-collapsible/index.js`: Module `react` does not exist in the Haste module map
This might be related to https://github.com/facebook/react-native/issues/4968
To resolve try the following:
1. Clear watchman watches: `watchman watch-del-all`.
2. Delete the `node_modules` folder: `rm -rf node_modules && npm install`.
3. Reset Metro Bundler cache: `rm -rf /tmp/metro-bundler-cache-*` or `npm start -- --reset-cache`. 4. Remove haste cache: `rm -rf /tmp/haste-map-react-native-packager-*`.
at ModuleResolver.resolveDependency (/Users/bright/Dev/react-navigation-collapsible/example/node_modules/metro/src/node-haste/DependencyGraph/ModuleResolution.js:167:1306)
at ResolutionRequest.resolveDependency (/Users/bright/Dev/react-navigation-collapsible/example/node_modules/metro/src/node-haste/DependencyGraph/ResolutionRequest.js:80:16)
at DependencyGraph.resolveDependency (/Users/bright/Dev/react-navigation-collapsible/example/node_modules/metro/src/node-haste/DependencyGraph.js:237:485)
at Object.resolve (/Users/bright/Dev/react-navigation-collapsible/example/node_modules/metro/src/lib/transformHelpers.js:116:25)
at dependencies.map.result (/Users/bright/Dev/react-navigation-collapsible/example/node_modules/metro/src/DeltaBundler/traverseDependencies.js:298:29)
at Array.map (<anonymous>)
at resolveDependencies (/Users/bright/Dev/react-navigation-collapsible/example/node_modules/metro/src/DeltaBundler/traverseDependencies.js:294:16)
at /Users/bright/Dev/react-navigation-collapsible/example/node_modules/metro/src/DeltaBundler/traverseDependencies.js:159:33
at Generator.next (<anonymous>)
at step (/Users/bright/Dev/react-navigation-collapsible/example/node_modules/metro/src/DeltaBundler/traverseDependencies.js:239:307)
react-navigation/react-navigation#2749
Many people want the iOS11 style header.
But when you look at carefully, you will notice its transition is complicated.
And scroll action that hiding and showing search bar and the header is working so naturally.
I used this library in my app for collapsible effect with top tab navigation.For that I referred Extra header for tab example .After which I could get a view with header and 3 top tabs ,but the header is not working as collapsible. I'm using redux in my app ,does that affect the collapsible behavior?
const MyProfileTopTab = createMaterialTopTabNavigator(
{
All: {screen: AllTransactions},
Pending: {screen: PendingTransaction},
History: {screen: HistoryTransactions},
},
);
const GroupImageHeader = ({navigation, collapsible}) => {
const {translateY, translateOpacity, translateProgress} = collapsible;
return (
<View
style={{
flex: 1,
justifyContent: 'center',
}}>
<ProfileHeader navigation={navigation} />
</View>
);
};
const collapsibleParams = {
collapsibleComponent: GroupImageHeader,
collapsibleBackgroundStyle: {
height: 200,
backgroundColor: 'white',
disableFadeoutInnerComponent: true,
},
collapsibleForegroundStyle: {
height: 100,
},
};
export default withCollapsibleForTab(MyProfileTopTab, collapsibleParams);
Hey
Thanks for the library
I can't find an example using StackNavigator
My code looks like this:
const MainNavigator = StackNavigator(
{
SCREENA: {
screen: FeedPage,
navigationOptions: ({navigation}) => {
...
},
},
How can I wrap the HOC here?
They is no example for Android devices, on collapse the header becomes transparent and my header title shows.
i noticed in your example you used iOSCollapsedColor, what do we use for android??
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.