Skip to content

Commit 76bcbd3

Browse files
authored
v3 (#49)
* extract overflow handlers and e2e.js * add some docs * revamp example * further improvements to docs and types * fix some flow types * remove useless stateFromProps * remove confusing disabled prop
1 parent 7ba48f3 commit 76bcbd3

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

42 files changed

+6481
-4954
lines changed

README.md

+27-19
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,7 @@ Please see also [how to integrate in your project](#how-to-integrate-in-your-pro
1616

1717
```js
1818
import Icon from 'react-native-vector-icons/Ionicons';
19-
import HeaderButtons, { HeaderButton, Item } from 'react-navigation-header-buttons';
19+
import { HeaderButtons, HeaderButton, Item } from 'react-navigation-header-buttons';
2020

2121
const IoniconsHeaderButton = passMeFurther => (
2222
// the `passMeFurther` variable here contains props from <Item .../> as well as <HeaderButtons ... />
@@ -31,6 +31,7 @@ static navigationOptions = {
3131
<HeaderButtons HeaderButtonComponent={IoniconsHeaderButton}>
3232
<Item title="search" iconName="ios-search" onPress={() => alert('search')} />
3333
<Item title="select" onPress={() => alert('select')} />
34+
<HiddenItem title="hidden in overflow menu" onPress={() => alert('hidden in overflow')} />
3435
</HeaderButtons>
3536
),
3637
};
@@ -40,26 +41,29 @@ static navigationOptions = {
4041

4142
`HeaderButtons` accepts:
4243

43-
| prop and type | description | note |
44-
| ---------------------------------------------------------------------------------------------------- | ------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
45-
| left: boolean | whether the `HeaderButtons` are on the left from header title | false by default |
46-
| HeaderButtonComponent: React.ComponentType<\*> | component that renders the buttons | Typically, you'll want to provide a component that wraps `HeaderButton` provided by this package, as seen in the [quick example](#quick-example). However, you're free to use your own component (see `HeaderButton` for reference). |
47-
| OverflowIcon?: React.Element<\*> | React element for the overflow icon | you need to provide this only if you need an overflow icon |
48-
| overflowButtonWrapperStyle?: ViewStyleProp | optional styles for overflow button | there are some default styles set, as seen in `OverflowButton.js` |
49-
| onOverflowMenuPress?: ({ hiddenButtons: Array<React.Element<\*>>, overflowButtonRef: ?View }) => any | function that is called when overflow menu is pressed. | This will override the default handler. Use this prop if you want to customize your overflow button behavior - I will likely not merge PRs that add props for the overflow menu since I prefer these customizations to happen in userland. |
44+
| prop and type | description | note |
45+
| ---------------------------------------------------------------------------------------------------- | ------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
46+
| left: boolean | whether the `HeaderButtons` are on the left from header title | false by default |
47+
| HeaderButtonComponent: React.ComponentType<any> | component that renders the buttons | Typically, you'll want to provide a component that wraps `HeaderButton` provided by this package, as seen in the [quick example](#quick-example). However, you're free to use your own component (see `HeaderButton` for reference). |
48+
| OverflowIcon?: React.Element<any> | React element for the overflow icon | you need to provide this only if you need an overflow icon |
49+
| overflowButtonWrapperStyle?: ViewStyleProp | optional styles for overflow button | there are some default styles set, as seen in `OverflowButton.js` |
50+
| onOverflowMenuPress?: ({ hiddenButtons: Array<React.Element<any>>, overflowButtonRef: View }) => any | function that is called when overflow menu is pressed. | This will override the default handler. Note the default handler offers (limited) customization. See more below. |
51+
| overflowButtonTestID?: string | testID to locate the overflow button in e2e tests | the default is available under `import { OVERFLOW_BUTTON_TEST_ID } from 'react-navigation-header-buttons/e2e'` |
5052

5153
`Item` accepts:
5254

53-
| prop and type | description | note |
54-
| ---------------------------------- | --------------------------------------------------------------------------------- | --------------------------------------------------------------------------------- |
55-
| onPress: ?() => any | function to call on press | if this is a falsy value, the button won't react to touches (will be disabled) |
56-
| title: string | title for the button, required | |
57-
| show: "always" or "never" | string specifying if the icon should be shown or hidden in overflow menu | "always" by default |
58-
| ButtonElement?: React.Node | optional React element to show as button. Use this for completely custom buttons. | if neither `IconComponent` nor this is defined, will render text with the `title` |
59-
| iconName?: string | icon name, used together with the `IconComponent` prop | |
60-
| buttonStyle?: ViewStyleProp | style to apply to the button | applies to both icon and text |
61-
| buttonWrapperStyle?: ViewStyleProp | style to apply to the touchable element that wraps the button | |
62-
| testID?: string | ID to locate the view in e2e tests | testID of the overflow button is exported under `OVERFLOW_BUTTON_TEST_ID` |
55+
| prop and type | description | note |
56+
| ---------------------------------- | --------------------------------------------------------------------------------- | ---------------------------------------------------------------------------------------------- |
57+
| onPress: ?() => any | function to call on press | if this is a falsy value, the button won't react to touches (will be disabled) |
58+
| title: string | title for the button, required | |
59+
| show: "always" or "never" | string specifying if the icon should be shown or hidden in overflow menu | the strings are accessible under `Item.SHOW_ALWAYS` and `Item.SHOW_NEVER`. "always" by default |
60+
| ButtonElement?: React.Node | optional React element to show as button. Use this for completely custom buttons. | if neither `IconComponent` nor `ButtonElement` is defined, will render text with the `title` |
61+
| iconName?: string | icon name, used together with the `IconComponent` prop | |
62+
| buttonStyle?: ViewStyleProp | style to apply to the button | applies to both icon and text |
63+
| buttonWrapperStyle?: ViewStyleProp | style to apply to the touchable element that wraps the button | |
64+
| testID?: string | ID to locate the view in e2e tests | |
65+
66+
Note - as an alternative to `<Item title="edit" show={Item.SHOW_NEVER} onPress={...} />` you can also use `<HiddenItem title="edit" onPress={...} />`
6367

6468
`HeaderButton` accepts:
6569

@@ -73,6 +77,10 @@ You may also pass other props that will be passed to the underlying `react-nativ
7377

7478
Please note that `HeaderButton` also requires other props to function correctly. Some of these props are passed from `<Item .. />` (such as `iconName`) and also `<HeaderButtons ... />`. When wrapping `HeaderButton` it is thus important to not forget to pass down all props the wrapping component receives (this is easy using the spread operator), as documented in the [quick example](#quick-example).
7579

80+
#### Customize the cancel button label of overflow menu on iOS
81+
82+
The default handler for overflow menu is exported as `defaultOnOverflowMenuPress`. On iOS, it uses `ActionSheetIOS` and on Android, it uses `UIManager.showPopupMenu`. One of the usual things you may want to do is override the cancel button label on iOS - see [example](example/screens/UsageWithOverflow.tsx).
83+
7684
#### How to integrate in your project
7785

7886
This sections covers how you should use the library in your project. Please note that there are numerous [example screens](https://github.com/vonovak/react-navigation-header-buttons/tree/master/example/navbar-buttons-demo/screens).
@@ -100,7 +108,7 @@ export const MaterialHeaderButtons = props => {
100108
/>
101109
);
102110
};
103-
export const Item = HeaderButtons.Item;
111+
export { Item } from 'react-navigation-header-buttons';
104112
```
105113

106114
2 . Import header buttons from the file defined previously.

example/.expo/packager-info.json

+10
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
{
2+
"devToolsPort": 19002,
3+
"expoServerPort": null,
4+
"packagerPort": null,
5+
"packagerPid": null,
6+
"expoServerNgrokUrl": null,
7+
"packagerNgrokUrl": null,
8+
"ngrokPid": null,
9+
"webpackServerPort": null
10+
}

example/.expo/settings.json

+7
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
{
2+
"hostType": "lan",
3+
"lanType": "ip",
4+
"dev": true,
5+
"minify": false,
6+
"urlRandomness": "rh-h82"
7+
}

example/.gitignore

+10
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
node_modules/**/*
2+
.expo/*
3+
npm-debug.*
4+
*.jks
5+
*.p12
6+
*.key
7+
*.mobileprovision
8+
*.orig.*
9+
web-build/
10+
web-report/
File renamed without changes.

example/App.tsx

+38
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
import {
2+
UsageCustom,
3+
UsageWithIcons,
4+
UsageWithOverflow,
5+
UsageLeft,
6+
UsageDisabled,
7+
UsageCustomRipple,
8+
UsageDifferentFontFamilies,
9+
HomeScreen,
10+
UsageWithCustomOverflow,
11+
UsageWithCustomOverflow2,
12+
} from './screens';
13+
import { createStackNavigator, createAppContainer } from 'react-navigation';
14+
import React from 'react';
15+
16+
// just for custom overflow menu onPress action
17+
import { ActionSheetProvider } from '@expo/react-native-action-sheet';
18+
19+
const RootStack = createStackNavigator({
20+
HomeScreen,
21+
UsageWithIcons,
22+
UsageLeft,
23+
UsageCustom,
24+
UsageDisabled,
25+
UsageCustomRipple,
26+
UsageWithOverflow,
27+
UsageDifferentFontFamilies,
28+
UsageWithCustomOverflow,
29+
UsageWithCustomOverflow2,
30+
});
31+
32+
const AppContainer = createAppContainer(RootStack);
33+
const App = () => (
34+
<ActionSheetProvider>
35+
<AppContainer />
36+
</ActionSheetProvider>
37+
);
38+
export default App;

example/navbar-buttons-demo/app.json example/app.json

+6-6
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,13 @@
11
{
22
"expo": {
33
"name": "navbar-buttons-demo",
4-
"description": "This project is really great.",
54
"slug": "navbar-buttons-demo",
65
"privacy": "public",
7-
"sdkVersion": "29.0.0",
8-
"platforms": ["ios", "android"],
6+
"sdkVersion": "33.0.0",
7+
"packagerOpts": {
8+
"config": "./metro.config.js"
9+
},
10+
"platforms": ["ios", "android", "web"],
911
"version": "1.0.0",
1012
"orientation": "portrait",
1113
"icon": "./assets/icon.png",
@@ -17,9 +19,7 @@
1719
"updates": {
1820
"fallbackToCacheTimeout": 0
1921
},
20-
"assetBundlePatterns": [
21-
"**/*"
22-
],
22+
"assetBundlePatterns": ["**/*"],
2323
"ios": {
2424
"supportsTablet": true
2525
}

example/assets/icon.png

1.07 KB
Loading
File renamed without changes.

example/babel.config.js

+6
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
module.exports = function(api) {
2+
api.cache(true);
3+
return {
4+
presets: ['babel-preset-expo'],
5+
};
6+
};

example/metro.config.js

+21
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
const path = require('path');
2+
3+
module.exports = {
4+
watchFolders: [path.resolve(__dirname, 'node_modules'), path.resolve(__dirname, '..')],
5+
transformer: {
6+
getTransformOptions: async () => ({
7+
transform: {
8+
experimentalImportSupport: false,
9+
inlineRequires: false,
10+
},
11+
}),
12+
},
13+
resolver: {
14+
providesModuleNodeModules: [
15+
'react-native',
16+
'react',
17+
'react-native-platform-touchable',
18+
'@babel/runtime',
19+
],
20+
},
21+
};

example/navbar-buttons-demo/.babelrc

-8
This file was deleted.

example/navbar-buttons-demo/.flowconfig

-55
This file was deleted.

example/navbar-buttons-demo/.gitignore

-3
This file was deleted.

example/navbar-buttons-demo/App.js

-54
This file was deleted.

example/navbar-buttons-demo/README.md

-4
This file was deleted.
-2.91 KB
Binary file not shown.

example/navbar-buttons-demo/package.json

-23
This file was deleted.

0 commit comments

Comments
 (0)