UNPKG

10.6 kBMarkdownView Raw
1# Storybook for React Native
2
3With Storybook for React Native you can design and develop individual React Native components without running your app.
4
5For more information visit: [storybook.js.org](https://storybook.js.org)
6
7> NOTE: `@storybook/react-native` and `@storybook/react-native-server` are now on a different release cycle from the Storybook Core packages (`@storybook/react`, `@storybook/vue`, etc.). The last stable version of `@storybook/react-native` is `5.3.25` and it should be used with `5.3` versions of Storybook Core.
8
9_To re-iterate storybook dependencies with a version 6.0 and higher are not supported by react native storybook yet._
10
11# Table of contents
12
13- 🚀 [Getting Started](#getting-started)
14- 📒 [Making stories](#making-stories)
15- 🔌 [On device Addons](#ondevice-addons)
16- 📱 [Other ways to render storybook](#other-ways-to-render-storybook)
17- 🔧 [getStorybookUI Options](#getstorybookui-options)
18- 🤝 [Contributing](#contributing)
19
20# Getting Started
21
22To get started run this command from within the root of your react native app:
23
24```
25npx -p @storybook/cli sb init --type react_native
26```
27
28You'll be prompted asking if you want to install @storybook/react-native-server, you can safely choose not to install this now since you can add it later and its not required.
29
30This command will setup most things for you, now you just need to add the following to your entrypoint (usually App.js or index.js).
31
32```
33export {default} from "./storybook";
34```
35
36The above steps use the storybook cli to install the most useful addons and creates a few example stories in a folder called `storybook`.
37
38All the config for storybook and the entrypoint also live in the `storybook` folder by default.
39
40If you prefer to set things up yourself you can follow the [manual setup](https://github.com/storybookjs/react-native/blob/master/app/react-native/docs/manual-setup.md)
41
42If you're struggling check out this [snack](https://snack.expo.io/@dannyhw/expo-storybook-example) with a working example
43
44# OndeviceUI and React native Server
45
46The react native storybook is designed to be flexible so that you can navigate all your stories and use addons within the device ui, you also have the option to use the web ui via `@storybook/react-native-server` if thats what you prefer.
47
48The UI that allows you to navigate stories on the device is what we will call the "OnDeviceUI". When referring to features specific to this UI this term is used to distinguish it from the server ui.
49
50# Making stories
51
52The simplest type of story could look something like this
53
54```
55
56 import React from 'react';
57 import { storiesOf } from '@storybook/react-native';
58
59 // I import the component I want to display here
60 import CustomButton from './CustomButton';
61
62 // here I define that I want to create stories with the label "Buttons",
63 // this will be the name in the storybook navigation
64
65 const buttonStories = storiesOf('Buttons', module);
66
67 // then I add a story with the name default view, I can add multiple stories to button stories
68 buttonStories.add('default view', () => (<CustomButton onPress={() => null} />));
69```
70
71You can then include addons such as action and knobs to make it more interactive.
72
73# Ondevice Addons
74
75The cli will install some basic addons for you such as knobs and actions.
76Ondevice addons are addons that can render with the device ui that you see on the phone.
77
78Currently the addons available are:
79
80- @storybook/addon-ondevice-knobs: adjust your components props in realtime
81- @storybook/addon-ondevice-actions: mock onPress calls with actions that will log information in the actions tab
82- @storybook/addon-ondevice-notes: Add some markdown to your stories to help document their usage
83- @storybook/addon-ondevice-backgrounds: change the background of storybook to compare the look of your component against different backgrounds
84
85Add each one you want to use to the rn-addons.js file in the `storybook` folder:
86
87```
88import '@storybook/addon-ondevice-actions/register';
89```
90
91Make sure to import the rn-addons.js file in the storybook entrypoint (index.js in the storybook folder by default):
92
93```
94import './rn-addons';
95```
96
97### Using the addons in your story
98
99Based on the previous example heres how you could extend it to use addons.
100
101```
102import React from 'react';
103import { storiesOf } from '@storybook/react-native';
104import CustomButton from './CustomButton';
105import { View } from 'react-native';
106
107// the action function has one argument which is the name of the action,
108// this will be displayed in the actions tab in the addons panel
109// action("name here")
110import { action } from '@storybook/addon-actions';
111
112// the boolean knob renders a switch which lets you toggle a value between true or false
113// you call it like boolean("name here", default_value)
114import { boolean, withKnobs } from '@storybook/addon-knobs';
115
116const buttonStories = storiesOf('CustomButton', module);
117
118// lets storybook know to show the knobs addon for this story
119buttonStories.addDecorator(withKnobs);
120
121// I use to boolean knob to set the disabled prop based on the knob state
122// I use the action function to log every time the button gets called
123buttonStories.add('default view', () => (
124 <View style={{ flex: 1, alignItems: 'center', justifyContent: 'center' }}>
125 <CustomButton onPress={action('Button Press!')} disabled={boolean('Disabled', false)} />
126 </View>
127));
128```
129
130# Other ways to render storybook
131
132In the getting started guide we suggest that you override you change the default export to be the storybook UI, this might not be what you want depending on how you are using storybook.
133
134There are a few options on how you can make the storybook render in your app so it's up to you to decide which works best for your project.
135
136## Run storybook as a separate app/component library
137
138Using the approach from the getting started setup you can make an app that just displays your storybook and then you could use this app to share your component library. Then you can export all your components from somewhere within the project and use the project as a component library/package.
139
140## Optionally run storybook or your app
141
142You could do something like this if you want to run storybook in dev mode and your app in release mode.
143
144```js
145import StorybookUI from './storybook';
146
147import App from './app';
148
149module.exports = __DEV__ ? StorybookUI : App;
150```
151
152Or you could use some kind of setting/environment variable to define what renders.
153
154## React Native Navigation, or other custom approaches
155
156`StorybookUI` is a RN `View` component that can be embedded anywhere in your RN application, e.g. on a tab or within an admin screen.
157
158You could also create a separate app just for storybook that also works as a package for your visual components.
159
160# Storybook server (optional)
161
162Storybook server is used to control the component visible on the device via a web ui. This is useful to control multiple devices at once and compare them at the same time.
163
164Install the package
165
166yarn `yarn add @storybook/react-native-server`
167
168npm `npm i --save @storybook/react-native-server`
169
170To run the server you can use `yarn start-storybook`
171or add a script to your package.json like
172
173```
174"storybook": "start-storybook"
175```
176
177_You can change "storybook" to any name you like._
178
179This will open the server web client, you will need to open storybook on the device for the stories to appear in the sidebar.
180
181To enable addons for react native server add a folder `storybook/` in the root of the project with a addons.js file inside. The server will detect this file and import it. The file should contain the addon imports similar to the rn-addons.js file but using the regular storybook (for web) addons. For example:
182
183```
184// storybook/addons.js
185require('@storybook/addon-knobs/register');
186require('@storybook/addon-actions/register');
187```
188
189If you get the error `Can't resolve 'babel-loader'` install babel-loader from npm and it should fix it.
190
191### Server cli options
192
193```
194-h, --host <host>
195 host to listen on
196-p, --port <port>
197 port to listen on
198--https
199 whether server is running on https
200-c, --config-dir [dir-name]
201 storybook config directory
202-e, --environment [environment]
203 DEVELOPMENT/PRODUCTION environment for webpack
204-i, --manual-id
205 allow multiple users to work with same storybook
206--smoke-test
207 Exit after successful start
208```
209
210# getStorybookUI Options
211
212You can pass these parameters to getStorybookUI call in your storybook entry point:
213
214```
215{
216 onDeviceUI: Boolean (true)
217 -- display navigator and addons on the device
218 disableWebsockets: Boolean (false)
219 -- allows to display stories without running storybook server. Should be used with onDeviceUI
220 secured: Boolean (false)
221 -- use wss/https instead of ws/http
222 host: String (NativeModules.SourceCode.scriptURL)
223 -- host to use
224 port: Number (7007)
225 -- port to use
226 query: String ("")
227 -- additional query string to pass to websockets
228 isUIHidden: Boolean (false)
229 -- should the ui be closed initially.
230 tabOpen: Number (0)
231 -- which tab should be open. -1 Navigator, 0 Preview, 1 Addons
232 initialSelection: Object (null)
233 -- initialize storybook with a specific story. In case a valid object is passed, it will take precedence over `shouldPersistSelection. ex: `{ kind: 'Knobs', story: 'with knobs' }`
234 shouldPersistSelection: Boolean (true)
235 -- initialize storybook with the last selected story.
236 shouldDisableKeyboardAvoidingView: Boolean (false)
237 -- Disable KeyboardAvoidingView wrapping Storybook's view
238 keyboardAvoidingViewVerticalOffset: Number (0)
239 -- With shouldDisableKeyboardAvoidingView=true, this will set the keyboardverticaloffset (https://facebook.github.io/react-native/docs/keyboardavoidingview#keyboardverticaloffset) value for KeyboardAvoidingView wrapping Storybook's view
240}
241```
242
243# Contributing
244
245We welcome contributions to Storybook!
246
247- 📥 Pull requests and 🌟 Stars are always welcome.
248- Read our [contributing guide](https://github.com/storybookjs/react-native/blob/master/CONTRIBUTING.md) to get started,
249 or find us on [Discord](https://discord.gg/sMFvFsG) and look for the react-native channel.
250
251Looking for a first issue to tackle?
252
253- We tag issues with [Good First Issue](https://github.com/storybookjs/react-native/issues?q=is%3Aopen+is%3Aissue+label%3A%22good+first+issue%22) when we think they are well suited for people who are new to the codebase or OSS in general.
254- [Talk to us](https://discord.gg/sMFvFsG), we'll find something to suits your skills and learning interest.