theme

mail@pastecode.io avatar
unknown
plain_text
a year ago
7.8 kB
1
Indexable
Never
import { createTheme } from '@mui/material';
import { forwardRef } from 'react';
import { LinkProps } from '@mui/material/Link';
import { Link as RouterLink, LinkProps as RouterLinkProps } from 'react-router-dom';
import SlideLeftTransition from './common/components/dialog/slideUpTransition';
import type {} from '@mui/x-data-grid/themeAugmentation';

declare module '@mui/material/styles' {
  interface Palette {
    gray: Palette['primary'];
    white: Palette['primary'];
  }
  interface PaletteOptions {
    gray: PaletteOptions['primary'];
    white: PaletteOptions['primary'];
  }
  interface CommonColors {
    red: string;
    borderGray: string;
  }
  interface TypeText {
    darkGray: string;
  }
  interface TypographyVariants {
    small: React.CSSProperties;
  }
  interface TypographyVariantsOptions {
    small?: React.CSSProperties;
  }
}

declare module '@mui/material/Button' {
  interface ButtonPropsColorOverrides {
    gray: true;
    white: true;
  }
}

declare module '@mui/material/ButtonGroup' {
  interface ButtonGroupPropsColorOverrides {
    gray: true;
    white: true;
  }
}

declare module '@mui/material/Typography' {
  interface TypographyPropsVariantOverrides {
    small: true;
  }
}

const LinkBehavior = forwardRef<
  HTMLAnchorElement,
  Omit<RouterLinkProps, 'to'> & { href: RouterLinkProps['to'] }
>((props, ref) => {
  const { href, ...other } = props;
  // Map href (MUI) -> to (react-router)
  return <RouterLink ref={ref} to={href} {...other} />;
});

LinkBehavior.displayName = 'LinkBehavior';

const baseTextColor = '#000000';
const primaryColor = '#003366';
const baseBorderColor = '#C7C8CA';

const theme = createTheme({
  components: {
    MuiLink: {
      defaultProps: {
        component: LinkBehavior,
      } as LinkProps,
    },
    MuiButtonBase: {
      defaultProps: {
        LinkComponent: LinkBehavior,
        disableRipple: true,
      },
      styleOverrides: {
        root: {
          fontWeight: 400,
        },
      },
    },
    MuiButtonGroup: {
      defaultProps: {
        disableElevation: true,
        disableRipple: true,
      },
    },
    MuiButton: {
      defaultProps: {
        disableElevation: true,
      },
      styleOverrides: {
        root: {
          textTransform: 'none',
          fontWeight: 400,
        },
      },
      variants: [
        {
          props: { variant: 'outlined', color: 'gray' },
          style: {
            borderColor: '#E2E4EA',
            color: baseTextColor,
          },
        },
        {
          props: { variant: 'text', color: 'gray' },
          style: {
            color: '#4D4D4F',
          },
        },
      ],
    },
    MuiInput: {
      defaultProps: {
        disableUnderline: true,
      },
      styleOverrides: {
        root: {
          border: `1px solid ${baseBorderColor}`,
          backgroundColor: '#ffffff',
          borderRadius: 4,
        },
      },
    },
    MuiTextField: {
      defaultProps: {
        variant: 'outlined',
      },
      styleOverrides: {
        root: {
          '& legend': { display: 'none' },
          '& .MuiOutlinedInput-root': {
            '& fieldset, &:hover fieldset, &.Mui-focused fieldset': {
              top: 0,
              borderWidth: 1,
            },
          },
          '& .MuiOutlinedInput-root:not(.Mui-error):not(.Mui-focused)': {
            '& fieldset, &:hover fieldset, &.Mui-focused fieldset': {
              borderColor: baseBorderColor,
            },
          },
        },
      },
    },
    MuiRadio: {
      defaultProps: {
        size: 'small',
      },
    },
    MuiFormControlLabel: {
      defaultProps: {
        componentsProps: {
          typography: {
            variant: 'caption',
          },
        },
      },
    },
    MuiInputBase: {
      styleOverrides: {
        root: {
          '& .MuiInputBase-input': {
            padding: '8px 14px',
            height: 36,
            boxSizing: 'border-box',
          },
          'label + &': {
            marginTop: 24,
          },
        },
      },
    },
    MuiSelect: {
      styleOverrides: {
        select: {
          fontSize: 14,
          height: 36,
        },
        nativeInput: {
          lineHeight: 1,
        },
      },
    },
    MuiInputLabel: {
      defaultProps: {
        shrink: true,
      },
    },
    MuiFormLabel: {
      styleOverrides: {
        root: {
          fontSize: 12,
          color: '#4D4D4F',
          transform: 'unset !important',
        },
      },
    },
    MuiCheckbox: {
      defaultProps: {
        size: 'small',
      },
      styleOverrides: {
        root: {
          color: baseBorderColor,
        },
      },
    },
    MuiDataGrid: {
      styleOverrides: {
        root: {
          border: 'none',
          fontSize: 14,
          '& .MuiDataGrid-actionsCell': {
            flexGrow: 1,
          },
          '& .MuiDataGrid-columnHeaders': {
            backgroundColor: '#FBFBFB',
            border: 'none',
          },
          '& .MuiDataGrid-columnSeparator': {
            display: 'none',
          },
          '& .MuiDataGrid-row': {
            border: 'none',
            borderBottom: '4px solid #F5F5F5',
          },
          '& .MuiDataGrid-cell': {
            border: 'none',
            '&:focus': {
              outline: 'none!important',
            },
          },
          '& .MuiDataGrid-columnHeader': {
            '&:focus': {
              outline: 'none',
            },
          },
          '& .MuiDataGrid-cellCheckbox': {
            '&:focus-within': {
              outline: 'none',
            },
          },
        },
      },
    },
    MuiChip: {
      styleOverrides: {
        root: {
          textTransform: 'uppercase',
          padding: '3px 10px',
          borderRadius: 5,
          fontSize: 12,
          height: 'auto',
          fontWeight: 500,
        },
        label: {
          padding: 0,
        },
        deleteIcon: {
          margin: 0,
        },
      },
    },
    MuiTab: {
      styleOverrides: {
        root: {
          fontWeight: 600,
          padding: '10px 15px',
        },
      },
    },
    MuiOutlinedInput: {
      styleOverrides: {
        root: {
          fontSize: 14,
          borderColor: baseBorderColor,
        },
      },
    },
    MuiDialog: {
      defaultProps: {
        TransitionComponent: SlideLeftTransition,
      },
    },
  },
  palette: {
    text: {
      primary: baseTextColor,
      secondary: '#8A8C8E',
      darkGray: '#4D4D4F',
    },
    common: {
      red: '#E11B22',
      borderGray: baseBorderColor,
    },
    background: {
      default: '#F9F9F9',
    },
    gray: {
      main: '#E2E4EA',
      contrastText: baseTextColor,
    },
    warning: {
      main: '#FCD3C1',
      contrastText: '#E11B22',
    },
    info: {
      main: '#C1E6ED',
      contrastText: primaryColor,
    },
    success: {
      main: '#27A63C',
      contrastText: '#ffffff',
    },
    primary: {
      main: primaryColor,
    },
    secondary: {
      main: '#E11B22',
    },
    white: {
      main: '#ffffff',
      contrastText: primaryColor,
    },
  },
  typography: {
    fontFamily: ['Inter', 'sans-serif'].join(','),
    fontSize: 16,
    h1: {
      fontSize: 48,
      fontWeight: 500,
    },
    h2: {
      fontSize: 28,
      fontWeight: 700,
    },
    h3: {
      fontSize: 22,
      fontWeight: 700,
    },
    h4: {
      fontSize: 20,
      fontWeight: 700,
    },
    h5: {
      fontSize: 18,
      fontWeight: 500,
    },
    subtitle2: {
      fontSize: 14,
      fontWeight: 400,
    },
    small: {
      fontSize: 12,
    },
  },
  shape: {
    borderRadius: 5,
  },
});

theme.shadows[6] = '0px 7px 17px 0px #494B541C';

export default theme;