如何把 React.Component 到 CSS 内容 属性 (在 :before/:after 伪元素中)?
How to put React.Component to CSS content property (in :before/:after pseudo-elements)?
在 styled-components
中,我试图通过 content
传递一个 React 图标,使其在悬停时呈现,但由于某种原因,我的悬停呈现是 [Object Object]
。
组件:
export const FooLink = styled(Link)`
padding: 0.5rem 2rem;
color: ${({ theme }) => theme.colors.white};
text-align: center;
margin: 0 auto;
position: relative;
font-size: ${({ theme }) => theme.fontSizes.p};
letter-spacing: 0.15em;
transition: ${({ theme }) => theme.animations.trans3};
&:after {
content: '${FaArrowRight}';
/* content: '>'; */
position: absolute;
opacity: 0;
right: -${({ theme }) => theme.spacings.small};
transition: ${({ theme }) => theme.animations.trans3};
}
&:hover {
padding-right: ${({ theme }) => theme.spacings.small};
padding-left: ${({ theme }) => theme.spacings.xxSmall};
}
&:hover:after {
opacity: 1;
${({ theme }) => theme.spacings.xSmall};
}
`
我把所有东西都带进来了:
import styled from 'styled-components'
import { Link } from 'gatsby'
import { FaArrowRight } from 'react-icons/fa'
对内容的其他尝试
content: ${FaArrowRight};
但我发现这不起作用:
That is because content value must be within quotes in CSS.
意识到我可能在 CSS 精神状态中度过了太长时间,我尝试引入 React:
import React from 'react'
import styled from 'styled-components'
import { Link } from 'gatsby'
import { FaArrowRight } from 'react-icons/fa'
和渲染:
content: '${(<FaArrowRight />)}';
当我尝试使用模板文字时,出现缺少分号的错误:
content: `'${<FaArrowRight />}'`;
所有尝试都呈现为 [Object Object]
研究一下是否有人问过这个问题,我已经通读了:
- css pseudo code “li::before” in react inline style
- Do psuedo selectors work in styled-components the same as in css with unicode characters
在 styled-components
中如何在 content
中呈现 React 图标?
如果需要用styled-components
(or any other CSS-in-JS library) with an icon from react-icons
(or any other library that exports a React.Component
which renders an <svg>
element), I see the only one way: to transform a component to an url()
with a markup string because only this way you can pass an image to content
property in your case. For that transformation, you need: React.createElement()
, ReactDOMServer.renderToStaticMarkup()
and encodeURIComponent()
. Also, you can use Base64代替。
这个有效(CodeSandbox):
import { createElement } from "react";
import { render } from "react-dom";
import { renderToStaticMarkup } from "react-dom/server";
import styled from "styled-components";
import { Link } from "gatsby";
import { FaArrowRight } from "react-icons/fa";
window.___loader = { enqueue: () => {}, hovering: () => {} };
const reactSvgComponentToMarkupString = (Component, props) =>
`data:image/svg+xml,${encodeURIComponent(
renderToStaticMarkup(createElement(Component, props))
)}`;
const FooLink = styled(Link)`
${({ color }) => color && `color: ${color};`}
&:after {
content: ${({ color }) =>
`url(${reactSvgComponentToMarkupString(FaArrowRight, {
color
})})`};
position: absolute;
opacity: 0;
}
&:hover:after {
opacity: 1;
}
`;
render(
<>
<div>
<FooLink to="/test1" color="red">
Link with arrow (red)
</FooLink>
</div>
<div>
<FooLink to="/test2">Link with arrow (default)</FooLink>
</div>
</>,
document.getElementById("root")
);
在 styled-components
中,我试图通过 content
传递一个 React 图标,使其在悬停时呈现,但由于某种原因,我的悬停呈现是 [Object Object]
。
组件:
export const FooLink = styled(Link)`
padding: 0.5rem 2rem;
color: ${({ theme }) => theme.colors.white};
text-align: center;
margin: 0 auto;
position: relative;
font-size: ${({ theme }) => theme.fontSizes.p};
letter-spacing: 0.15em;
transition: ${({ theme }) => theme.animations.trans3};
&:after {
content: '${FaArrowRight}';
/* content: '>'; */
position: absolute;
opacity: 0;
right: -${({ theme }) => theme.spacings.small};
transition: ${({ theme }) => theme.animations.trans3};
}
&:hover {
padding-right: ${({ theme }) => theme.spacings.small};
padding-left: ${({ theme }) => theme.spacings.xxSmall};
}
&:hover:after {
opacity: 1;
${({ theme }) => theme.spacings.xSmall};
}
`
我把所有东西都带进来了:
import styled from 'styled-components'
import { Link } from 'gatsby'
import { FaArrowRight } from 'react-icons/fa'
对内容的其他尝试
content: ${FaArrowRight};
但我发现这不起作用:
That is because content value must be within quotes in CSS.
意识到我可能在 CSS 精神状态中度过了太长时间,我尝试引入 React:
import React from 'react'
import styled from 'styled-components'
import { Link } from 'gatsby'
import { FaArrowRight } from 'react-icons/fa'
和渲染:
content: '${(<FaArrowRight />)}';
当我尝试使用模板文字时,出现缺少分号的错误:
content: `'${<FaArrowRight />}'`;
所有尝试都呈现为 [Object Object]
研究一下是否有人问过这个问题,我已经通读了:
- css pseudo code “li::before” in react inline style
- Do psuedo selectors work in styled-components the same as in css with unicode characters
在 styled-components
中如何在 content
中呈现 React 图标?
如果需要用styled-components
(or any other CSS-in-JS library) with an icon from react-icons
(or any other library that exports a React.Component
which renders an <svg>
element), I see the only one way: to transform a component to an url()
with a markup string because only this way you can pass an image to content
property in your case. For that transformation, you need: React.createElement()
, ReactDOMServer.renderToStaticMarkup()
and encodeURIComponent()
. Also, you can use Base64代替。
这个有效(CodeSandbox):
import { createElement } from "react";
import { render } from "react-dom";
import { renderToStaticMarkup } from "react-dom/server";
import styled from "styled-components";
import { Link } from "gatsby";
import { FaArrowRight } from "react-icons/fa";
window.___loader = { enqueue: () => {}, hovering: () => {} };
const reactSvgComponentToMarkupString = (Component, props) =>
`data:image/svg+xml,${encodeURIComponent(
renderToStaticMarkup(createElement(Component, props))
)}`;
const FooLink = styled(Link)`
${({ color }) => color && `color: ${color};`}
&:after {
content: ${({ color }) =>
`url(${reactSvgComponentToMarkupString(FaArrowRight, {
color
})})`};
position: absolute;
opacity: 0;
}
&:hover:after {
opacity: 1;
}
`;
render(
<>
<div>
<FooLink to="/test1" color="red">
Link with arrow (red)
</FooLink>
</div>
<div>
<FooLink to="/test2">Link with arrow (default)</FooLink>
</div>
</>,
document.getElementById("root")
);