【MUI】CSS最佳实践

Material UI VS MUI Base

MUI Base 是比较基础的版本,而Material UI复杂些,客制化,可以和Emotion (or styled-components)使用

如果是一个比较简单的项目,我觉得用MUI Base 就可以了,但是我们做了几个简单的项目,都没有用MUI Base

CSS

在使用 Material UI 的时候,我一直特别喜欢用sx属性去写样式,结果就会造成代码里面都是这种代码。

于是我得寻找一种最佳的实践方案,详情见css

1、plain css

mui可以使用最原始的css,如

demo

CSS injection order

就是说不用使用!important, 使用的方式如下

js 复制代码
import * as React from 'react';
import { StyledEngineProvider } from '@mui/material/styles';

export default function GlobalCssPriority() {
  return (
    <StyledEngineProvider injectFirst>
      {/* Your component tree. Now you can override MUI's styles. */}
    </StyledEngineProvider>
  );
}

源码实现,看了源码就是在head标签前面插入style属性,我想css in js不都是在head前面动态插入style吗,如果是使用这个,应该注入的时候要放在最前面

Deeper element

方式1: 和我们平时使用的没啥差别

方式2: 使用slotProps

这个感觉得不好用,使用默认的className不就好了,我为啥还要多一步写个slotProps

如果有slotProps,组件的API文档都会写得很清楚,如slider

总结: plain css 与我们之前习惯写得css没啥差别,除了那个 CSS injection order , 既然用了mui,我觉得可以考虑 css in js的写法,比如我用plain css,我怎么用theme定义的变量等

2、Styled Component

js 复制代码
import * as React from 'react';
import Slider from '@mui/material/Slider';
import { styled } from '@mui/material/styles';

// base useages
const CustomizedSlider = styled(Slider)`
  color: #20b2aa;
  :hover {
    color: #2e8b57;
  }
`;

// Deeper elements
const CustomizedSlider = styled(Slider)`
  color: #20b2aa;
  :hover {
    color: #2e8b57;
  }
  & .MuiSlider-thumb {
    border-radius: 1px;
  }
`;

// slotProps
const CustomizedSlider = styled((props) => (
  <Slider slotProps={{ thumb: { className: 'thumb' } }} {...props} />
))`
  color: #20b2aa;
  :hover {
    color: #2e8b57;
  }
  & .thumb {
    border-radius: 1px;
  }
`;

// theme
const CustomizedSlider = styled(Slider)(
  ({ theme }) => `
  color: ${theme.palette.primary.main};
  :hover {
    color: ${darken(theme.palette.primary.main, 0.2)};
  }
`,
);

export default function StyledComponents() {
  return <CustomizedSlider defaultValue={30} />;
}

Protal

js 复制代码
// Styled Component 还可以这么用,棒
const StyledTooltip = styled(({ className, ...props }) => (
// 这个classes到底是咋用的
  <Tooltip {...props} classes={{ popper: className }} />
))`
  & .MuiTooltip-tooltip {
    background: navy;
  }
`;

<StyledTooltip title="I am navy">
  <Button variant="contained" color="primary">
    Styled tooltip
  </Button>
</StyledTooltip>

3、CSS Module

js 复制代码
.slider {
  color: #20b2aa;
}

.slider:hover {
  color: #2e8b57;
}

//Deeper elements
.slider :global .MuiSlider-thumb {
  border-radius: 1px;
}

import * as React from 'react';
// webpack, parcel or else will inject the CSS into the page
import styles from './CssModulesSliderDeep1.module.css';
import Slider from '@mui/material/Slider';

export default function CssModulesSliderDeep1() {
  return (
    <div>
      <Slider defaultValue={30} />
      <Slider defaultValue={30} className={styles.slider} />
    </div>
  );
}

嗯,这种css module的方式就是我们日常最常用的

4、emotion

github.com/emotion-js/...

js 复制代码
import { css } from '@emotion/react';
import Slider from '@mui/material/Slider';
import Box from '@mui/material/Box';

export default function EmotionCSS() {
  return (
    <Box sx={{ width: 300 }}>
      <Slider defaultValue={30} />
      <Slider
        defaultValue={30}
        css={css`
          color: #20b2aa;
          :hover {
            color: #2e8b57;
          }
        `}
      />
    </Box>
  );
}

很不喜欢这种方式,因为模板字符创,没有任何样式提示 。

styled API(), 这个和2点的styled component一样

js 复制代码
 import styled from '@emotion/styled'
 
 const Button = styled.button`
   color: red
 `
 
 render(<Butto/>)

5、 Tailwind CSS

tailwindcss.com/

csharp 复制代码
pnpm add -D tailwindcss postcss autoprefixer

// webpack.config.js

yaml 复制代码
module.exports = {
  module: {
    rules: [
      {
        loader: "postcss-loader",
        options: {
          postcssOptions: {
            ident: "postcss",
            config: false,
            plugins: ["tailwindcss"],
          },
        },
      },
    ],
  },
};

// tailwind.css

css 复制代码
@tailwind base;
@tailwind components;
@tailwind utilities;

// tailwind.config.js

js 复制代码
module.exports = {
  content: [
    './pages/**/*.tsx',
  ],
}

6、 TSS

github.com/garronej/ts...

js 复制代码
import { makeStyles } from 'tss-react/mui';

export function MyComponent(props: Props) {
  const { className } = props;

  const [color, setColor] = useState<'red' | 'blue'>('red');

  const { classes, cx } = useStyles({ color });

  //Thanks to cx, className will take priority over classes.root
  return <span className={cx(classes.root, className)}>hello world</span>;
}

const useStyles = makeStyles<{ color: 'red' | 'blue' }>()((theme, { color }) => ({
  root: {
    color,
    '&:hover': {
      backgroundColor: theme.palette.primary.main,
    },
  },
}));

看上去如果碰到js操作css的情况,比如更换主题,这个tss很方便

相关推荐
学习使我快乐012 小时前
JS进阶 3——深入面向对象、原型
开发语言·前端·javascript
bobostudio19952 小时前
TypeScript 设计模式之【策略模式】
前端·javascript·设计模式·typescript·策略模式
黄尚圈圈3 小时前
Vue 中引入 ECharts 的详细步骤与示例
前端·vue.js·echarts
浮华似水4 小时前
简洁之道 - React Hook Form
前端
正小安6 小时前
如何在微信小程序中实现分包加载和预下载
前端·微信小程序·小程序
_.Switch8 小时前
Python Web 应用中的 API 网关集成与优化
开发语言·前端·后端·python·架构·log4j
一路向前的月光8 小时前
Vue2中的监听和计算属性的区别
前端·javascript·vue.js
长路 ㅤ   8 小时前
vite学习教程06、vite.config.js配置
前端·vite配置·端口设置·本地开发
长路 ㅤ   8 小时前
vue-live2d看板娘集成方案设计使用教程
前端·javascript·vue.js·live2d
Fan_web8 小时前
jQuery——事件委托
开发语言·前端·javascript·css·jquery