Created
November 7, 2019 20:40
-
-
Save mskoroglu/172a07cbd05c6962a8391f35750564c6 to your computer and use it in GitHub Desktop.
React multi-state hooks — https://codesandbox.io/s/youthful-zhukovsky-8jd62
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import React from "react"; | |
import { withState, multiState } from "./multi-state"; | |
const Input = ({ state, ...props }) => ( | |
<input | |
value={state.value} | |
onChange={e => state.setValue(e.target.value)} | |
{...props} | |
/> | |
); | |
const StatefulInput = withState(Input); | |
const App = () => { | |
const state = multiState({ | |
name: "John", | |
surname: "Doe", | |
favoriteFruit: "Banana" | |
}); | |
const fruits = ["Apple", "Banana", "Orange"]; | |
return ( | |
<div> | |
<StatefulInput state={state.nameState()} /> | |
<StatefulInput | |
state={state.surnameState()} | |
style={{ display: "block", marginTop: ".5rem" }} | |
/> | |
<select | |
value={state.favoriteFruit} | |
onChange={e => state.setFavoriteFruit(e.target.value)} | |
style={{ marginTop: ".5rem" }} | |
> | |
{fruits.map((fruit, i) => ( | |
<option key={i}>{fruit}</option> | |
))} | |
</select> | |
<pre>{JSON.stringify(state, null, 2)}</pre> | |
<FooForm /> | |
</div> | |
); | |
}; | |
const FooForm = () => { | |
const { email, setEmail, password, ...state } = multiState({ | |
id: 1, | |
email: null, | |
password: "s3cret" | |
}); | |
return ( | |
<ul> | |
<li>id: {state.id}</li> | |
<li> | |
email: {email} — | |
<button onClick={() => setEmail("[email protected]")}>change</button> | |
</li> | |
<li>password: {password}</li> | |
</ul> | |
); | |
}; |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import React from "react"; | |
export const multiState = map => | |
Object.keys(map).reduce((state, key) => { | |
const [value, setValue] = React.useState(map[key]); | |
const setter = "set" + key.charAt(0).toUpperCase() + key.slice(1); | |
const fnName = key + "State"; | |
return Object.assign(state, { | |
[key]: value, | |
[setter]: setValue, | |
[fnName]: () => ({ value, setValue }) | |
}); | |
}, {}); | |
export const withState = Component => ({ state, ...props }) => ( | |
<Component state={state} {...props} /> | |
); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment