TypeScript无法识别MUI styled组件通用样式对象,如何添加类型修复?
我有多个不同的MUI styled组件,它们包含一些通用样式,因此我编写了一个接收theme参数并返回通用样式的函数getCommonStyled,代码如下:
const getCommonStyled = (theme: Theme) => ({ height: '100%', display: 'flex', flexDirection: 'column', padding: theme.spacing(2), }) const StyledComponent1 = styled('div')(({ theme }) => ({ ...getCommonStyled(theme), color: 'blue' })) const StyledComponent2 = styled(Typography)(({ theme }) => ({ ...getCommonStyled(theme), backgroundColor: 'blue' })) const StyledComponent3 = styled('span')(({ theme }) => ({ ...getCommonStyled(theme), width: 100, height: 100, }))
但TypeScript不允许这种写法,报错信息为:
error TS2769: No overload matches this call.
The last overload gave the following error.
Argument of type '({ theme }: MUIStyledCommonProps & ClassAttributes & HTMLAttributes & { ...; }) => { ...; }' is not assignable to parameter of type 'TemplateStringsArray'.
请问该如何为getCommonStyled添加类型,以消除这些错误?
这个错误的核心是getCommonStyled的返回值类型没有和MUI styled函数期望的样式类型对齐,只需为函数指定明确的返回类型即可解决。
步骤1:导入MUI的样式类型
从MUI的样式模块导入CSSObject类型,它是MUI定义的标准样式对象类型:
import { CSSObject, Theme } from '@mui/material/styles';
步骤2:为getCommonStyled指定返回类型
修改函数,明确它返回CSSObject类型:
const getCommonStyled = (theme: Theme): CSSObject => ({ height: '100%', display: 'flex', flexDirection: 'column', padding: theme.spacing(2), })
这样TypeScript就能识别到函数返回的是符合MUI要求的样式对象,不会再出现类型不匹配的错误。
修改后的完整代码
import { styled, Typography } from '@mui/material'; import { CSSObject, Theme } from '@mui/material/styles'; const getCommonStyled = (theme: Theme): CSSObject => ({ height: '100%', display: 'flex', flexDirection: 'column', padding: theme.spacing(2), }) const StyledComponent1 = styled('div')(({ theme }) => ({ ...getCommonStyled(theme), color: 'blue' })) const StyledComponent2 = styled(Typography)(({ theme }) => ({ ...getCommonStyled(theme), backgroundColor: 'blue' })) const StyledComponent3 = styled('span')(({ theme }) => ({ ...getCommonStyled(theme), width: 100, height: 100, }))
额外说明
如果你的通用样式需要适配不同元素的特定样式属性(比如某些属性只对特定HTML标签有效),可以进一步细化类型,但大部分场景下使用CSSObject就足够解决问题。
内容的提问来源于stack exchange,提问作者theJuls

