// @flow import * as React from 'react'; import { observable, computed, action } from 'mobx'; import { observer } from 'mobx-react'; import styled from 'styled-components'; import Flex from 'shared/components/Flex'; import { LabelText, Outline } from 'components/Input'; import { validateColorHex } from 'shared/utils/color'; const colors = [ '#4E5C6E', '#19B7FF', '#7F6BFF', '#FC7419', '#FC2D2D', '#FFE100', '#14CF9F', '#EE84F0', '#2F362F', ]; type Props = { onSelect: (color: string) => void, value?: string, }; @observer class ColorPicker extends React.Component { @observable selectedColor: string = colors[0]; @observable customColorValue: string = ''; @observable customColorSelected: boolean; componentWillMount() { const { value } = this.props; if (value && colors.includes(value)) { this.selectedColor = value; } else if (value) { this.customColorSelected = true; this.customColorValue = value.replace('#', ''); } } componentDidMount() { this.fireCallback(); } fireCallback = () => { this.props.onSelect( this.customColorSelected ? this.customColor : this.selectedColor ); }; @computed get customColor(): string { return this.customColorValue && validateColorHex(`#${this.customColorValue}`) ? `#${this.customColorValue}` : colors[0]; } @action setColor = (color: string) => { this.selectedColor = color; this.customColorSelected = false; this.fireCallback(); }; @action focusOnCustomColor = (event: SyntheticEvent<*>) => { this.selectedColor = ''; this.customColorSelected = true; this.fireCallback(); }; @action setCustomColor = (event: SyntheticEvent<*>) => { let target = event.target; if (target instanceof HTMLInputElement) { const color = target.value; this.customColorValue = color.replace('#', ''); this.fireCallback(); } }; render() { return ( Color {colors.map(color => ( this.setColor(color)} /> ))} Custom color: # ); } } type SwatchProps = { onClick?: () => void, color?: string, active?: boolean, }; const Swatch = ({ onClick, ...props }: SwatchProps) => ( ); const SwatchOutset = styled(Flex)` width: 24px; height: 24px; margin-right: 5px; border: 2px solid ${({ active, color }) => (active ? color : 'transparent')}; border-radius: 2px; background: ${({ color }) => color}; ${({ onClick }) => onClick && `cursor: pointer;`} &:last-child { margin-right: 0; } `; const SwatchInset = styled(Flex)` width: 20px; height: 20px; border: 1px solid ${({ active, color }) => (active ? 'white' : 'transparent')}; border-radius: 2px; background: ${({ color }) => color}; `; const StyledOutline = styled(Outline)` padding: 5px; flex-wrap: wrap; strong { font-weight: 500; } `; const HexHash = styled.div` margin-left: 12px; padding-bottom: 0; font-weight: 500; user-select: none; `; const CustomColorInput = styled.input` border: 0; flex: 1; width: 65px; margin-right: 12px; padding-bottom: 0; outline: none; background: none; font-family: ${props => props.theme.monospaceFontFamily}; font-weight: 500; &::placeholder { color: ${props => props.theme.slate}; font-family: ${props => props.theme.monospaceFontFamily}; font-weight: 500; } `; export default ColorPicker;