Skip to content

Instantly share code, notes, and snippets.

@cbdyzj
Created April 10, 2022 01:13
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 cbdyzj/d5cacd7bd216b5065c92ab4a0c0c2699 to your computer and use it in GitHub Desktop.
Save cbdyzj/d5cacd7bd216b5065c92ab4a0c0c2699 to your computer and use it in GitHub Desktop.
Counter.jsx
import React, { useReducer } from 'react'
import styled from '@emotion/styled'
import { sleep } from '../../utils/schedule.js'
const initialState = { count: 7n }
function reducer(state = initialState, action) {
if (action.type === 'setCount') {
return {
...state,
count: action.payload
}
}
return state
}
const Container = styled.div`
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
height: 75vh;
& input {
max-width: 60%;
border-width: 0 0 .5px 0;
outline: none;
font-size: 30px;
text-align: center;
}
& button {
border-radius: 4px;
font-size: 14px;
margin: 11px 4px;
padding: 0 16px;
border: 0;
line-height: 27px;
height: 36px;
min-width: 80px;
text-align: center;
outline: none;
user-select: none;
background-color: #f8f9fa;
transition: color 0.3s;
}
& button:hover {
box-shadow: 0 1px 1px rgba(0, 0, 0, .1);
border: 1px solid #dadce0;
color: #202124;
}
& button:active {
color: rgba(0, 0, 0, 0.3)
}
& button:disabled {
color: rgba(0, 0, 0, 0.3)
}
`
function convertToBigInt(value, def) {
try {
return BigInt(value)
} catch (err) {
alert(err.message)
return def
}
}
export default function Counter(props) {
const [state, dispatch] = useReducer(reducer, initialState);
const count = state.count
const [plus1sButtonDisabled, setPlus1sButtonDisabled] = React.useState(false)
function onInputChange(ev) {
dispatch({
type: 'setCount',
payload: convertToBigInt(ev.target.value, count)
})
}
function onClickMinus() {
dispatch({
type: 'setCount',
payload: count - 1n
})
}
async function onClickPlus1s() {
setPlus1sButtonDisabled(true)
await sleep(1000)
dispatch({
type: 'setCount',
payload: count + 1n
})
setPlus1sButtonDisabled(false)
}
return (
<Container>
<input type="text" value={String(count)} onChange={onInputChange}/>
<div>
<button onClick={onClickMinus}>-</button>
<button onClick={onClickPlus1s} disabled={plus1sButtonDisabled}>+1s</button>
</div>
</Container>
)
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment