React children道具允许组件被组合在一起,是构建可重用组件的一个关键概念。从视觉上看,我们可以把它看作是组件中的一个洞,消费者在那里控制渲染的内容。这篇文章介绍了用TypeScript强类型化这个强大而灵活的道具的不同方法:
使用FC 类型
有一个标准的React类型,FC ,我们可以在箭头函数组件上使用。FC是Function Component的缩写,它与一个叫做FunctionComponent 的类型相类似。
这里有一个例子:
type Props = {
title: string,
};
const Page: React.FC<Props> = ({
title,
children,
}) => (
<div>
<h1>{title}</h1>
{children}
</div>
);
FC 是一个通用类型,它接收所有组件道具的具体类型。在上面的例子中,我们传入了一个 类型的别名,其中包含一个 的道具。另外,也可以用一个接口来定义 。Props title Props
注意,children 并没有定义在Props 。相反,它已经被定义在FC 类型中。如果你知道这个事实,这很好,但如果你不知道,可能就会有点困惑了。
明确定义children 道具类型
如果我们明确地定义children ,我们有几个不同的选项来定义其类型。
让我们一个一个来看看 ...
使用JSX.Element
让我们先试试JSX.Element :
type Props = {
title: string,
children: JSX.Element,};
const Page = ({ title, children }: Props) => (
<div>
<h1>{title}</h1>
{children}
</div>
);
children 是目前必须的。如果我们想让这个组件的消费者可以选择,我们在类型注解前加一个问号( )。?
type Props = {
title: string;
children?: JSX.Element;};
JSX.Element 如果孩子被要求是一个单一的React元素,那就很好。然而,它不允许有多个孩子。所以,我们可以做如下调整:
type Props = {
title: string;
children?: JSX.Element | JSX.Element[];};
使用ReactChild
JSX.Element 的一个缺点是它不允许有字符串。所以,我们可以在联合类型中加入字符串:
type Props = {
title: string;
children: | JSX.Element | JSX.Element[] | string | string[];};
...但是数字呢?
......这就失控了!
幸运的是,有一个标准类型叫ReactChild ,它包括React元素、字符串和数字。因此,我们可以扩大children 的类型,如下所示:
type Props = {
title: string;
children?: | React.ReactChild | React.ReactChild[];};
使用ReactNode
React.ReactChild | React.ReactChild[] 提供了我们需要的广泛的值,但有点啰嗦。 是一个更简洁的选择。ReactNode
type Props = {
title: string;
children?: React.ReactNode;};
ReactNode 允许多个元素、字符串、数字、片段、门户......。
非常完美!
FC 通用类型在引擎盖下也使用ReactNode 。
类组件
如果我们使用的是类组件呢?让我们来探讨这个问题:
type Props = {
title: string,
};
export class Page extends React.Component<Props> {
render() {
return (
<div>
<h1>{this.props.title}</h1>
{this.props.children}
</div>
);
}
}
像FC ,Component 类型自动包括children 道具。
如果我们将鼠标悬停在children 道具上,我们会发现它被赋予的类型。

所以,类组件中的children 道具的类型也是ReactNode 。
结束语
如果我们使用类型为FC 的函数组件,那么children 道具就已经被输入了。如果我们明确地对children 道具进行类型化,一般来说,ReactNode 是最好的选择。