Ecosyste.ms: Awesome
An open API service indexing awesome lists of open source software.
https://github.com/colevoss/react-motive
Another React state management library using the new Context API
https://github.com/colevoss/react-motive
react react-context state-management
Last synced: about 1 month ago
JSON representation
Another React state management library using the new Context API
- Host: GitHub
- URL: https://github.com/colevoss/react-motive
- Owner: colevoss
- Created: 2018-04-04T16:34:00.000Z (almost 7 years ago)
- Default Branch: master
- Last Pushed: 2022-12-07T11:12:27.000Z (about 2 years ago)
- Last Synced: 2024-12-16T18:19:17.894Z (about 1 month ago)
- Topics: react, react-context, state-management
- Language: JavaScript
- Size: 922 KB
- Stars: 14
- Watchers: 1
- Forks: 2
- Open Issues: 17
-
Metadata Files:
- Readme: README.md
Awesome Lists containing this project
- awesome-react-state-management - react-motive - Small wrapper around the React Context API with actions/dispatch style state management. (List)
- awesome-react-context - **react-motive** - Small wrapper around the React Context API with actions/dispatch style state management. (Libraries)
README
# React Motive [![npm](https://img.shields.io/npm/v/react-motive.svg)](https://www.npmjs.com/package/react-motive) [![npm](https://img.shields.io/npm/dm/react-motive.svg)](https://www.npmjs.com/package/react-motive) ![npm bundle size (minified)](https://img.shields.io/bundlephobia/min/react-motive.svg) ![Travis](https://img.shields.io/travis/colevoss/react-motive.svg)
Small wrapper around the React Context API with actions/dispatch style state management.
## Install
```
yarn add react-motive
```## Example
[![Edit React Motive Counter Example](https://codesandbox.io/static/img/play-codesandbox.svg)](https://codesandbox.io/s/ll693wn0pl?module=%2Fsrc%2FCounter.js)
```js
import React from 'react';
import createMotive from 'react-motive';/**
* Default State
*/
const defaultState = { count: 0 };/**
* Actions:
*
* Actions don't have to be curried functions if they don't take arguments
* as long as dispatch is given a function that returns a new slice of state.
*/
const increment = () => ({ count }) => ({
count: count + 1,
});const decrement = () => ({ count }) => ({
count: count - 1,
});/**
* Create Container
*/
const Counter = createMotive(defaultState);/**
* Use Consumers
*/
const Display = () => (
{({ state }) =>Count: {state.count}
}
);const Controls = () => (
{({ dispatch }) => (
dispatch(decrement())}>-
dispatch(increment())}>+
)}
);/**
* Put it all together
*/
const AllTogether = () => (
);
```## Documentation
#### `createMotive`
`createMotive` returns an object with a `Provider` component and a `Consumer` component.
```js
const defaultState = { count: 1 };const { Provider, Consumer } = createMotive(defaultState);
```#### ``
The `Provider` is a React component that should wrap all of its corresponding `Consumer` components. This component holds all of the state given from `defaultState` and that is updated later on.
#### ``
The `Consumer` component is what you can use anywhere as long as it's a child of the corresponding `Provider` component. Use this component to get access to the state of its `Provider` and to dispatch updates to that state.
```js
{({ state, dispatch }) => /* ... some react stuff that uses state or dispatch */ }
```
This component takes a render prop as its child. This render prop is given an object with the following members in it.
##### `state`
This is the current state of the corresponding `Provider` component.
#### `dispatch`
`dispatch` should be called with an `action` function. An `action` should return a slice of new state to be merged into the `Provider`'s state.
### Actions
Actions are provided with `state` and `dispatch` as arguments. This means you can dispatch other actions from an action if necessary.
An action must return a partial version of state.
**Pro Tip:** If you need to give actions data, write them as curried functions and call them into `dispatch` with any arugments that they might need.
```js
/**
* Basic action
*/
const increment = (state) => ({
count: state.count + 1,
});dispatch(increment);
/**
* Curried action that takes arguments
*/
const incrementBy = (incrBy) => (state) => ({
count: state.count + incrBy,
});dispatch(incrementBy(2));
/**
* Action that dispatches another action
*/
const delayedIncrement = (state, dispatch) => {
setTimeout(() => dispatch(incrementBy(2)));return {
count: state.count + 1,
};
};dispatch(delayedIncrement);
```#### `combineActions`
`combineActions` will take two actions and combine their returned updated pieces of state into one updated piece of state.
```js
const defaultState = {
a: 0,
b: 0,
};const actionA = (state) => {
return {
a: state.a + 1,
};
};const actionB = (state) => ({
b: state.b + 2,
});const combined = combineActions(actionsA, actionB);
const resultingState = dispatch(combined);
resultingState === { a: 1, b: 2 };
```