Skip to content

Instantly share code, notes, and snippets.

@KrofDrakula
Created May 18, 2018 19:42
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save KrofDrakula/51741d7da1f1b698fdaaa2345aa81631 to your computer and use it in GitHub Desktop.
Save KrofDrakula/51741d7da1f1b698fdaaa2345aa81631 to your computer and use it in GitHub Desktop.
A stateful HOC for pure components
import { h, Component } from 'preact';
const withState = Wrapped => class extends Component {
constructor(props) {
super(props);
this.state = props;
}
componentWillReceiveProps(nextProps) {
this.setState(nextProps);
}
handleChange = ev => {
const { name, value } = ev.target;
this.setState({ name: value });
}
render(_, props) {
return <Wrapped
{...props}
set={s => this.setState(s)}
onChange={this.handleChange}
/>;
}
};
export default withState;
import { h, render } from 'preact';
import withState from './stateful';
const RANDOM_NAMES = [
'Summer', 'Beth', 'Jerry', 'Rick', 'Morty'
];
const rnd = arr => () => arr[~~(Math.random() * arr.length)];
const getRandomName = rnd(RANDOM_NAMES);
// component has no state, but is provided with
// mutative functions to manipulate props:
// - set(props) -- works this this.setState()
// - onChange(ev) -- sets the prop named `ev.target.name`
// to `ev.target.value`
const Greeter = ({ name, set, onChange }) => (
<div>
<span>Hello, {name}!</span>
<input
type="text"
name="name"
value={name}
onInput={onChange}
/>
<button
onClick={() => set({name: getRandomName()})}
>Get a new one!</button>
</div>
);
const StatefulGreeter = withState(Greeter);
render(<StatefulGreeter name="Mr Meeseeks"/>, document.body);
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment