Press n or j to go to the next uncovered block, b, p or k for the previous block.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 | import { CircleButton } from '@components/circle-button'; import { MAX_STACKING_CYCLES, MIN_STACKING_CYCLES } from '@constants/index'; import { Flex, InputProps, Text, Box, color } from '@stacks/ui'; import { RootState } from '@store/index'; import { selectNextCycleInfo } from '@store/stacking'; import { decrement, increment } from '@utils/mutate-numbers'; import { formatCycles } from '@utils/stacking'; import dayjs from 'dayjs'; import advancedFormat from 'dayjs/plugin/advancedFormat'; import duration from 'dayjs/plugin/duration'; import relativeTime from 'dayjs/plugin/relativeTime'; import updateLocale from 'dayjs/plugin/updateLocale'; import React, { FC, useMemo } from 'react'; import { useSelector } from 'react-redux'; dayjs.extend(duration); dayjs.extend(updateLocale); dayjs.extend(relativeTime); dayjs.extend(advancedFormat); interface DurationCycleFromProps extends Omit<InputProps, 'form'> { duration: number | null; onUpdate(duration: number): void; } const createCycleArray = () => new Array(12).fill(null).map((_, i) => i + 1); const durationWithDefault = (duration: number | null) => duration ?? 1; export const DurationCyclesForm: FC<DurationCycleFromProps> = props => { const { duration, onUpdate } = props; const { cycleInfo } = useSelector((state: RootState) => ({ cycleInfo: selectNextCycleInfo(state), })); const cycleLabels = useMemo(() => { Iif (!cycleInfo) return []; return createCycleArray().map(cycles => { return ` ${formatCycles(cycles)} (ends around ${dayjs() .add(cycleInfo.estimateCycleDurationSeconds * cycles, 'seconds') .format('Do MMMM')})`; }); }, [cycleInfo]); return ( <Flex alignItems="center" justifyContent="space-between" mt="base" padding="8px" boxShadow="low" border={`1px solid ${color('border')}`} borderRadius="8px" onClick={e => (e.stopPropagation(), e.preventDefault())} position="relative" zIndex={10} > <Text alignItems="center" ml="tight" color={color('text-title')}> {cycleLabels[durationWithDefault(duration) - 1]} </Text> <Box> <CircleButton onClick={e => { e.stopPropagation(); onUpdate(Math.max(MIN_STACKING_CYCLES, decrement(durationWithDefault(duration)))); }} > - </CircleButton> <CircleButton ml={[null, 'extra-tight']} onClick={e => { e.stopPropagation(); onUpdate(Math.min(MAX_STACKING_CYCLES, increment(durationWithDefault(duration)))); }} > + </CircleButton> </Box> </Flex> ); }; |