React Stopwatch
by Allie Yu
HTML
<script src="https://cdnjs.cloudflare.com/ajax/libs/babel-core/5.8.24/browser.js"></script>
<script src="https://fb.me/react-with-addons-0.14.0.js"></script>
<script src="https://fb.me/react-dom-0.14.0.js"></script>
<script src="https://facebook.github.io/react/js/jsfiddle-integration-babel.js"></script>
<div id="container">
<!-- This element's contents will be replaced with your component. -->
</div>
CSS
body {
font-family: monospace;
}
button {
box-sizing: border-box;
margin: 5px 2px 10px 0;
padding: 5px 8px;
width: 50px;
}
#timer {
font-size: 1.45em;
font-weight: 100;
}
Babel + JSX
const leftPad = (width, n) => {
if ((n + '').length > width) {
return n;
}
const padding = new Array(width).join('0');
return (padding + n).slice(-width);
};
class Stopwatch extends React.Component {
constructor(props) {
super(props);
["lap", "update", "reset", "toggle"].forEach((method) => {
this[method] = this[method].bind(this);
});
this.state = this.initialState = {
isRunning: false,
lapTimes: [],
timeElapsed: 0,
};
}
toggle() {
this.setState({isRunning: !this.state.isRunning}, () => {
this.state.isRunning ? this.startTimer() : clearInterval(this.timer)
});
}
lap() {
const {lapTimes, timeElapsed} = this.state;
this.setState({lapTimes: lapTimes.concat(timeElapsed)});
}
reset() {
clearInterval(this.timer);
this.setState(this.initialState);
}
startTimer() {
this.startTime = Date.now();
this.timer = setInterval(this.update, 10);
}
update() {
const delta = Date.now() - this.startTime;
this.setState({timeElapsed: this.state.timeElapsed + delta});
this.startTime = Date.now();
}
render() {
const {isRunning, lapTimes, timeElapsed} = this.state;
return (
<div>
<TimeElapsed id="timer" timeElapsed={timeElapsed} />
<button onClick={this.toggle}>
{isRunning ? 'Stop' : 'Start'}
</button>
<button
onClick={isRunning ? this.lap : this.reset}
disabled={!isRunning && !timeElapsed}
>
{isRunning || !timeElapsed ? 'Lap' : 'Reset'}
</button>
{lapTimes.length > 0 && <LapTimes lapTimes={lapTimes} />}
</div>
);
}
}
class TimeElapsed extends React.Component {
getUnits() {
const seconds = this.props.timeElapsed / 1000;
return {
min: Math.floor(seconds / 60).toString(),
sec: Math.floor(seconds % 60).toString(),
msec: (seconds % 1).toFixed(3).substring(2)
};
}
render() {
const units =...