reactjs - 带 TypeScript 的样式化组件 .attrs

标签 reactjs typescript styled-components

我对如何使用 .attrs() 有点困惑使用 TypeScript 函数。说我有以下几点:

BottleBar.tsx:

interface IBottleComponentProps {
  fill?: boolean
}

const BottleComponent = styled.div.attrs<IBottleComponentProps>(({fill}) => ({
  style: {
    backgroundImage: `url("./media/images/${fill ? 'Bottle-Filled.png' : 'Bottle-Empty.png'")`
  }
}))<IBottleComponentProps`
  width: 20px;
  height: 20px;
`;

export default function BottleBar() {

  return (
    <Wrapper>
      <BottleComponent />
      <BottleComponent fill />
    </Wrapper>
  )
}

现在,上面的代码有效,但我不确定为什么 IBottleComponentProps在开始和结束时都需要两次 - 如果没有它,我会得到以下信息:
Type '{ fill: boolean; }' is not assignable to type 'IntrinsicAttributes & Pick<Pick<Pick<DetailedHTMLProps<HTMLAttributes<HTMLDivElement>, HTMLDivElement>, "slot" | ... 253 more ... | "onTransitionEndCapture"> & { ...; }, "slot" | ... 254 more ... | "onTransitionEndCapture"> & Partial<...>, "slot" | ... 254 more ... | "onTransitionEndCapture"> & { ...; } & { ...; }'.

此外,在第一个代码示例中,我得到了一个浏览器日志;
index.js:1 Warning: Received `true` for a non-boolean attribute `fill`.

老实说,这很令人困惑,而且 Styled-Components 文档在这方面不是很清楚。朝着正确的方向插入将不胜感激。

最佳答案

答案 1:Warning about fill
您需要选择不同的名称 ,也许 full ,但不是 fill为您的样式组件。如 fill 是一些 HTML 元素的标准属性。 Also, at w3schools

实验:

如果您声明 fill成为 string并传递给它一个字符串值,你可以看到一个 fill添加到您的属性 div HTML DOM , 例子:

<div
  fill="test"
  style="background-image: url(&quot;/media/images/image_file.png&quot;);" class="sc-AxiKw jDjxaQ">
</div>
fill是 SVGAttributes 接口(interface)中的一个属性:

来自 node_modules/@types/react/index.d.ts :
interface SVGAttributes<T> extends AriaAttributes, DOMAttributes<T> {
  // Attributes which also defined in HTMLAttributes
  className?: string;
  id?: string;
  ...
  // SVG Specific attributes
  accentHeight?: number | string;
  ...
  fill?: string;
  ...
}

这就是这个警告的原因:
Warning: Received `true` for a non-boolean attribute `fill`.
If you want to write it to the DOM, pass a string instead: fill="true" or fill={value.toString()}.

答案 2:Why interface is required 2 times?
以下是相关界面的摘录:
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>;
U变成:IBottleComponentProps你通过的C是 HTML 元素还是 react 组件类型

返回类型为 ThemedStyledFunction<C, T, O & NewA, A | keyof NewA> :
export interface ThemedStyledFunction<
    C extends keyof JSX.IntrinsicElements | React.ComponentType<any>,
    T extends object,
    O extends object = {},
    A extends keyof any = never

哪里C , T已经提供。您正在提供 O路过 IBottleComponentProps 第二次 .

如果您不提供您的 BottleComponent将如下所示 {}对于 Prop ,即没有 Prop :

without

如果您提供,它将看起来像下面一个,带有正确的 Prop 。

with

总之,你必须提供2次接口(interface)目前。您可以提供any如果您没有定义接口(interface)。

关于reactjs - 带 TypeScript 的样式化组件 .attrs,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/61979237/

相关文章:

reactjs - 找不到模块 : Can't resolve 'bootstrap/dist/css/bootstrap.css' in 'C:\Users\test\counter-app\src'

javascript - 为什么 If 语句被视为此循环中的函数?

unit-testing - 使用 Mocks 使用 Jest 和 Typescript 进行测试

javascript - ReactJS - 组件外部的全局状态

reactjs - 在 ReactJS 中导入 MUI 组件

angular - 管道中的 @component 不工作 angular2

javascript - 处理 promise 错误的最佳方法是什么?

css - 切换按钮/带有图标和文字的按钮/

javascript - 将 props 从 react-cosmos 传递到 styled-components

reactjs - 如何在样式组件中使用 "hover"(CSS) 操作?