给出:
const Link = styled.a`
border: solid 1px black;
border-radius: 5px;
padding: 5px;
margin: 10px 5px;
`;
type ButtonProps = React.ButtonHTMLAttributes<HTMLButtonElement>;
const LinkAsButton = styled(Link).attrs<ButtonProps>
>(({
as: 'button',
className: 'btn btn-primary'
})`
border: solid 1px red;
`;
如何将按钮专用道具(例如已禁用)传递给LinkAsButton
?
回购(包括v3和v4的分支)表明存在问题:https://github.com/arteforme/v3-v4-styled-components-migration
在v3中,我可以执行以下操作:
package.json
"dependencies": {
"@types/react": "^16.8.8",
"@types/react-dom": "^16.8.2",
"react": "^16.8.4",
"react-dom": "^16.8.4",
"react-scripts": "2.1.8",
"styled-components": "^3.3.3",
"typescript": "^3.3.3333"
}
组件定义
type ButtonProps = React.ButtonHTMLAttributes<HTMLButtonElement>;
const Link = styled.a`
border: solid 1px black;
border-radius: 5px;
padding: 5px;
margin: 10px 5px;
`;
const LinkAsButton = Link.withComponent('button')
.extend.attrs<ButtonProps>({
className: 'btn btn-primary'
})`
border: solid 1px red;
`;
,在使用代码中,我可以在LinkAsButton
组件上指定按钮专用的道具(例如,禁用,表单等)。
在v4中,我希望达到相同的效果;但是,我没有成功确定如何去做。根据最新文档,我已将LinkAsButton
更新为不再调用extend
或withComponent
,而是将Link
包装在对styled
的调用中并使用{{ 1}}来指定标签。 v4版本如下:
package.json
as
组件定义
dependencies": {
"@types/react": "^16.8.14",
"@types/styled-components": "^4.1.14",
"react": "^16.8.6",
"react-dom": "^16.8.6",
"react-scripts": "2.1.8",
"styled-components": "^4.2.0",
"typescript": "^3.4.5"
}
并且在使用代码中,我在const LinkAsButton = styled(Link).attrs<ButtonProps>
>(({
as: 'button',
className: 'btn btn-primary'
})`
border: solid 1px red;
`;
实例上指定了disabled={true}
,但是无法编译。而是,出现以下错误:
属性'disabled'在类型'IntrinsicAttributes&Pick,HTMLAnchorElement>,“ type”中不存在| “ defaultChecked” | “ defaultValue” | “ suppressContentEditableWarning” | ... 257更多... | “ referrerPolicy”>&{...; },“类型” | ... 261更多... | “ referrerPolicy”>&Partial <...>,“类型” | ....'。 TS2322
看一下定义文件,我注意到可以指定两个通用参数。
LinkAsButton
据我所知,attrs <
U,
NewA extends Partial<StyledComponentPropsWithRef<C> & U> & {
[others: string]: any;
} = {}
> (
attrs: Attrs<StyledComponentPropsWithRef<C> & U, NewA, T>
): ThemedStyledFunction<C, T, O & NewA, A | keyof NewA>;
是包装的组件,我相信C
是NewAttributes。在这种情况下,我无法确定U是什么,但是我尝试指定第二个通用参数。
NewA
这样做会导致以下错误:
类型'ButtonHTMLAttributes'不能分配给类型'Partial,HTMLAnchorElement>,“ type” | “ defaultChecked” | “ defaultValue” | “ suppressContentEditableWarning” | ... 257更多... | “ referrerPolicy”>&{...; }和ButtonHTMLAttributes <... >>'。 属性“ onCopy”的类型不兼容。
掌握这些信息后,我会尝试:
const LinkAsButton = styled(AnchorLink).attrs<{}, ButtonProps>`
// omitted for brevity
`
现在可以在标记中指定const LinkAsButton = styled(Link).attrs<
{},
{ as: string; className: string; disabled?: boolean }
>({
as: 'button',
className: 'btn btn-primary'
})``;
,但不能指定其他按钮专用道具(例如disabled
)
一种方法是执行以下操作:
form
消费代码:
const LinkAsButton = styled(Link)<ButtonProps>`
border: solid 1px red;
`;
但是,这将导致很多代码重复:(。
答案 0 :(得分:0)
通过在调用.attrs之后移动通用参数来使其正常工作。
const LinkAsButton = styled(Link).attrs
>(({
as: 'button',
className: 'btn btn-primary'
})<ButtonProps>`
border: solid 1px red;
`;
现在可以在JSX中设置ButtonProps中定义的任何道具