import React, { FC, memo, useEffect, useMemo, useState } from 'react'; import { cn } from '../../util/bem'; import { externalClasses, MediaPropsType } from '../../util/externalClasses'; import { FormSizesType, IconColorType, SizeType, TextColorType } from '../../util/global-props'; import { Icon } from '../icon/icon.component'; import { iconMap } from '../icon/icon.library'; import { Loader, loaderSize } from '../loader/loader.component'; import './button.component.scss'; export type ButtonPropsType = { className?: string; children?: React.ReactNode; before?: React.ReactNode; after?: React.ReactNode; type?: 'button' | 'submit' | 'reset'; icon?: keyof typeof iconMap; iconAfter?: boolean; iconFloat?: 'left' | 'right'; iconColor?: IconColorType; iconMargin?: SizeType; iconSize?: number; fullWidthContent?: boolean; align?: 'left' | 'center' | 'right'; viewType?: 'primary' | 'primary-green' | 'primary-white' | 'white' | 'white-border-grey-3' | 'secondary' | 'dark' | 'transparent-black' | 'transparent-grey' | 'transparent-transparent' | 'transparent-transparent-border-grey-3' | 'transparent-white' | 'alert' | 'violet'; size?: FormSizesType; color?: TextColorType; bold?: boolean; uppercase?: boolean; active?: boolean; loading?: boolean; fullWidth?: boolean; rounded?: boolean; disabled?: boolean; flex?: number | string; margin?: SizeType; style?: React.CSSProperties; hide?: MediaPropsType; disableBorderRadius?: boolean; squareBorderRadius?: boolean; data?: Record; ref?: React.Ref; onClick?: React.EventHandler>; onFocus?: React.EventHandler>; onMouseLeave?: React.EventHandler>; onMouseEnter?: React.EventHandler>; } const className = cn('button'); export const Button: FC = memo((props) => { const [ loading, setLoading ] = useState(false); const getIconColor = () => { if (props.iconColor) { return props.iconColor; } if (props.viewType === 'primary' || props.viewType === 'alert' || props.viewType === 'dark') { return 'white'; } return 'dark'; }; const iconFloatStyle = useMemo(() => props.iconFloat && { [ `margin-${ (() => (props.iconFloat === 'left' ? 'right' : 'left'))() }` ]: 'auto' }, [ props.iconFloat ]); const getContent = () => ( { props.before } { props.icon && !props.iconAfter && ( ) } { props.children } { props.icon && props.iconAfter && ( ) } { props.after } ); const getLoader = () => (
); useEffect(() => { if (props.loading) { setTimeout(() => setLoading(true), 100); } if (!props.loading) { setTimeout(() => setLoading(false), 100); } }, [ props.loading ]); return ( // eslint-disable-next-line react/button-has-type ); }); Button.defaultProps = { type: 'button', size: 'md', viewType: 'primary', iconMargin: 'xs', iconAfter: false, bold: true };