Skip to content

Instantly share code, notes, and snippets.

@jstcki
Last active August 10, 2018 04:37
Show Gist options
  • Save jstcki/27dc76b6f8411b4725bb to your computer and use it in GitHub Desktop.
Save jstcki/27dc76b6f8411b4725bb to your computer and use it in GitHub Desktop.
Interpolate anything with React Motion
license: mit

React Motion's interpolated styles are just arbitrary values and don't have to map to actual CSS styles.

In this example, only a single value t is interpolated by React Motion from 0 to 1 when the mouse is pressed, and passed to an color interpolator created with d3-interpolate. Additionally, it's used to scale the text and to display a percentage.

<!DOCTYPE html>
<head>
<meta charset="utf-8">
<style>
body {
margin:0;
font-family: Helvetica, sans-serif;
font-size: 3em;
}
div {
width: 100vw;
height: 100vh;
display: flex;
align-items: center;
justify-content: center;
text-align: center;
}
</style>
</head>
<body>
<div id="app" />
<script src="https://unpkg.com/[email protected]/babel.min.js"></script>
<script src="https://unpkg.com/[email protected]/dist/react.js"></script>
<script src="https://unpkg.com/[email protected]/dist/react-dom.js"></script>
<script src="https://unpkg.com/[email protected]/build/react-motion.js"></script>
<script src="https://unpkg.com/[email protected]"></script>
<script type="text/babel">
const {Motion, spring, presets} = ReactMotion;
// Super-slow spring
const springConfig = {stiffness: 50, damping: 20};
const formatPercent = d3.format('.0%');
class Color extends React.Component {
constructor() {
super();
this.state = {down: false};
this.onPress = () => this.setState({down: true});
this.onRelease = () => this.setState({down: false});
}
render() {
const interpolateColor = d3.interpolateHclLong(this.props.from, this.props.to);
return (
<Motion
defaultStyle={{t: 0}}
style={{t: spring(this.state.down ? 1 : 0, springConfig)}}
>
{({t}) => (
<div
onMouseDown={this.onPress}
onMouseUp={this.onRelease}
onTouchStart={this.onPress}
onTouchEnd={this.onRelease}
style={{background: interpolateColor(t)}}
>
<span
style={{transform: `scale(${1-t * 0.5})`}}
>
Press me<br />{formatPercent(t)}
</span>
</div>
)}
</Motion>
);
}
}
ReactDOM.render(
<Color from='#ffde28' to='#c85bff' />,
document.getElementById('app')
);
</script>
</body>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment