如何引用作为功能组件的样式化组件?

时间:2020-10-10 02:42:55

标签: javascript reactjs next.js styled-components

这是我能想到的最基本的例子:

import React from 'react';
import {
  css,
} from 'styled-components';

const Foo = (props) => {
  console.log(props);

  const {
    children,
  } = props;

  return <div {...props}>{children}</div>;
};

export default () => {
  return <div
    css={css`
      ${Foo} {
        background: #f00;
      }
    `}
  >
    <Foo>FOO</Foo>
  </div>;
};

在此示例中,我要为Foo的后代div组件设置样式。

我希望最终的标记看起来像这样:

<div class="test__Foo-wusfqk-0 hNfawX">FOO</div>

但是,它只是简单的:

<div>FOO</div>

似乎没有在任何地方应用样式。

此外,组件Foo仅呈现一次,但是使用不同的参数调用了两次:

{children: {…}, theme: {…}}
  children: {$$typeof: Symbol(react.element), key: null, ref: null, props: {…}, type: ƒ, …}
  theme: {}

{children: "FOO"}

我应该提到我尝试过:

// @flow

import React from 'react';
import styled, {
  css,
} from 'styled-components';

const Foo = styled((props) => {
  const {
    className,
    children,
  } = props;

  return <div className={className}>{children}</div>;
});

export default () => {
  return <div
    css={css`
      ${Foo} {
        background: #f00;
      }
    `}
  >
    <Foo>FOO</Foo>
  </div>;
};


但是,在中执行此代码时,出现以下错误:

id为“ sc-dlnjPT”的组件Styled(Component)已动态创建。

您可能会看到此警告,因为您在另一个组件中调用了样式。

要解决此问题,请仅在任何渲染方法和函数组件之外创建新的StyledComponents。

id为“ sc-hKFyIo”的组件Styled(Component)已动态创建。

您可能会看到此警告,因为您在另一个组件中调用了样式。

要解决此问题,请仅在任何渲染方法和函数组件之外创建新的StyledComponents。

错误:无效的挂钩调用。挂钩只能在功能组件的主体内部调用。发生这种情况可能是由于以下原因之一:

  1. 您可能使用了不匹配的React和渲染器版本(例如React DOM)
  2. 您可能正在违反挂钩规则
  3. 您可能在同一应用中拥有多个React副本

鉴于主题代码段,这没有多大意义。

1 个答案:

答案 0 :(得分:1)

主要问题是<Foo />不是样式组件,而是功能组件

我认为您需要做

const Foo = styled.div`
    background: #f00;
`

然后,您可以使用Foocss引用来更改$的样式

您的代码不起作用的原因如下

仅在样式化组件的上下文中支持此行为:在以下示例中尝试安装B将失败,因为组件Foo是React.Component的实例,而不是样式化组件。

const Foo = () => <div> </div>

const B = styled.div`
  ${Foo} {
  }
`

但是,将Foo包装在styled()工厂中使其可以进行插值-只需确保包装的组件沿className传递即可。

const Foo = (props) => {
  console.log(props);

  const {
    children,
  } = props;

  return <div className="Test-Class" {...props}>{children}</div>;
};

const StyledFoo = styled(Foo)``

const Main = styled.div`
  ${StyledFoo} {
    background: #f00;
  }
`

代码沙箱

import { render } from "react-dom";
import React from "react";
import styled from "styled-components";

const Foo = (props) => {
  const { className, children } = props;

  return <div className={className}>{children}</div>;
};

const Bar = styled(Foo)``;

const Main = styled.div`
  ${Bar} {
    background-color: #000;
    color: #fff;
  }
`;
const App = () => {
  return (
    <Main>
      {" "}
      <Bar>Hello </Bar>{" "}
    </Main>
  );
};

render(<App />, document.getElementById("root"));

https://codesandbox.io/s/styled-components-forked-5s201?file=/index.js