API 参考

基本(Primary)

¥Primary

styled(styled)

这是默认导出。这是我们用来创建 styled.tagname 辅助方法的底层工厂。

¥This is the default export. This is a low-level factory we use to create the styled.tagname helper methods.

ArgumentsDescription
  1. component / tagname

Either a valid react component or a tagname like 'div'.

返回一个接受标记模板字面量并将其转换为 StyledComponent 的函数。

¥Returns a function that accepts a tagged template literal and turns it into a StyledComponent.


你可以在 入门 部分看到这个方法的介绍。

¥You can see this method being introduced in the Getting started section.

TaggedTemplateLiteral(TaggedTemplateLiteral)

这就是你传递到样式调用中的内容 - 标记的模板字面量。这是 ES6 语言的特性。你可以在 标记模板字面量 部分了解有关它们的更多信息。

¥This is what you pass into your styled calls – a tagged template literal. This is an ES6 language feature. You can learn more about them in the Tagged Template Literals section.

InputsDescription
Rule

Any CSS rules (string)

Interpolation

This can either be a string or a function. Strings are combined with the rules as-is. Functions will receive the styled component's props as the first and only argument.

阅读 根据属性进行调整 部分中有关如何根据属性调整样式的更多信息。

¥Read more about how to adapt styling based on props in the Adapting based on props section.

传递到插值函数的属性会附加一个特殊属性 theme,该属性由更高级别的 ThemeProvider 组件注入。有关详细信息,请查看 主题化 部分。

¥The properties that are passed into an interpolated function get attached a special property, theme, which is injected by a higher level ThemeProvider component. Check the section on Theming for more information on this.

✨ Magic

你还可以直接从插值或输入对象返回对象,它们将被视为内联样式。然而,强烈建议不要这样做,因为 CSS 语法支持伪选择器、媒体查询、嵌套等,而对象语法则不支持。

¥You can also return objects from interpolations or input objects directly, and they'll be treated as inline styles. However this is highly discouraged, as the CSS syntax has support for pseudo selectors, media queries, nesting, etc., which the object syntax doesn't.

StyledComponent(StyledComponent)

一个样式化的 React 组件。当你使用样式调用 styled.tagnamestyled(Component) 时,会返回该值。

¥A styled React component. This is returned when you call styled.tagname or styled(Component) with styles.

该组件可以采用任何属性。如果它是有效属性,它会将其传递到 HTML 节点,否则它仅将其传递到插值函数中。(见 标记模板字面量

¥This component can take any prop. It passes it on to the HTML node if it's a valid attribute, otherwise it only passes it into interpolated functions. (see Tagged Template Literal)

你可以毫无问题地将任意类名传递给样式组件,并且它将应用于样式调用定义的样式旁边。(例如 <MyStyledComp className="bootstrap__btn" />

¥You can pass an arbitrary classname to a styled component without problem and it will be applied next to the styles defined by the styled call. (e.g. <MyStyledComp className="bootstrap__btn" />)

.attrs(.attrs)

这是一个可链接的方法,它将一些属性附加到样式组件上。第一个也是唯一的参数是一个对象,它将被合并到组件的其余 props 中。attrs 对象接受以下值:

¥This is a chainable method that attaches some props to a styled component. The first and only argument is an object that will be merged into the rest of the component's props. The attrs object accepts the following values:

ValuesDescription
Prop Value

These can be of any type, except functions. They'll stay static and will be merged into the existing component props.

Prop Factory

A function that receives the props that are passed into the component and computes a value, that is then going to be merged into the existing component props.

返回另一个 StyledComponent

¥Returns another StyledComponent.

附加额外属性 部分了解有关此构造函数的更多信息。

¥Learn more about this constructor in the Attaching Additional Props section.

"as" 多态属性("as" polymorphic prop)

¥"as" polymorphic prop

| v4

如果你想保留应用于组件的所有样式,但只是切换最终渲染的内容(无论是不同的 HTML 标签还是不同的自定义组件),你可以使用 "as" 属性在运行时执行此操作。

¥If you want to keep all the styling you've applied to a component but just switch out what's being ultimately rendered (be it a different HTML tag or a different custom component), you can use the "as" prop to do this at runtime.

这种东西在像导航栏这样的用例中非常有用,其中一些项目应该是链接,有些只是按钮,但所有项目的样式都相同。

¥This sort of thing is very useful in use cases like a navigation bar where some of the items should be links and some just buttons, but all be styled the same way.

"forwardedAs" 属性("forwardedAs" prop)

¥"forwardedAs" prop

| v4.3

如果你选择使用也接受 "as" 属性的 styled() HOC 封装另一个组件,请使用 "forwardedAs" 将所需的属性传递给封装的组件。

¥If you choose to wrap another component with the styled() HOC that also accepts an "as" prop, use "forwardedAs" to pass along the desired prop to the wrapped component.

瞬态属性(Transient props)

¥Transient props

| v5.1

如果你想阻止样式组件使用的 props 被传递到底层 React 节点或渲染到 DOM 元素,你可以在 prop 名称前加上美元符号 ($),将其变成瞬态 prop。

¥If you want to prevent props meant to be consumed by styled components from being passed to the underlying React node or rendered to the DOM element, you can prefix the prop name with a dollar sign ($), turning it into a transient prop.

在此示例中,$draggable 不像 draggable 那样渲染到 DOM。

¥In this example, $draggable isn't rendered to the DOM like draggable is.

Drag me!

shouldForwardProp(shouldForwardProp)

| v5.1

这是一种比瞬态 prop 更动态、更精细的过滤机制。在多个高阶组件组合在一起并且碰巧共享相同的 prop 名称的情况下,它非常方便。shouldForwardProp 的工作方式与 Array.filter 的谓词回调非常相似。测试失败的 prop 不会传递到底层组件,就像瞬态 prop 一样。

¥This is a more dynamic, granular filtering mechanism than transient props. It's handy in situations where multiple higher-order components are being composed together and happen to share the same prop name.shouldForwardProp works much like the predicate callback of Array.filter. A prop that fails the test isn't passed down to underlying components, just like a transient prop.

请记住,如本例所示,其他可链接方法应始终在 .withConfig 之后执行。

¥Keep in mind that, as in this example, other chainable methods should always be executed after .withConfig.

Drag Me!

(可选)shouldForwardProp 可以采用第二个参数来提供对默认验证器函数的访问。这个函数可以用作后备,当然,它也可以像谓词一样工作,根据已知的 HTML 属性进行过滤。

¥Optionally, shouldForwardProp can take a second parameter that provides access to the default validator function. This function can be used as a fallback, and of course, it also works like a predicate, filtering based on known HTML attributes.

ThemeProvider(ThemeProvider)

用于主题化的辅助组件。通过上下文 API 将主题注入到组件树中其下方任意位置的所有样式组件中。检查 主题化 部分。

¥A helper component for theming. Injects the theme into all styled components anywhere beneath it in the component tree, via the context API. Check the section on Theming.

PropsDescription
theme

An object (or function returning an object) that will be injected as theme into all interpolations in styled components beneath the provider.

简单用法:

¥Simple usage:

I'm mediumseagreen!

使用嵌套 ThemeProvider 添加或替换外部主题:

¥Adding to or replacing an outer theme using nested ThemeProvider:

I'm mediumseagreen with a white background!
I'm mediumseagreen with a black background!

css 属性(css prop)

¥css prop

| v4

有时你不想仅仅为了应用一些样式而创建额外的组件。css 属性是一种迭代组件的便捷方法,而无需确定固定的组件边界。它适用于普通 HTML 标签和组件,并支持任何样式组件支持的所有内容,包括基于 props、主题和自定义组件进行调整。

¥Sometimes you don't want to create an extra component just to apply a bit of styling. The css prop is a convenient way to iterate on your components without settling on fixed component boundaries yet. It works on both normal HTML tags as well as components, and supports everything any styled component supports, including adapting based on props, theming and custom components.

Note

要启用对 css 属性的支持,你必须使用 Babel 插件

¥To enable support for the css prop you have to use the Babel plugin.

<div
  css={`
    background: papayawhip;
    color: ${props => props.theme.colors.text};
  `}
/>
<Button
  css="padding: 0.5em 1em;"
/>

在底层,Babel 插件将任何带有 css prop 的元素转换为样式组件。例如上面的代码就变成:

¥Under the hood, the Babel plugin turns any element with a css prop into a styled component. For example, the above code becomes:

import styled from 'styled-components';


const StyledDiv = styled.div`
  background: papayawhip;
  color: ${props => props.theme.colors.text};
`


const StyledButton = styled(Button)`
  padding: 0.5em 1em;
`


<StyledDiv />
<StyledButton />

请注意,你甚至不必添加导入,Babel 插件会自动执行此操作!(除非你使用 Babel 宏,请参见下文)

¥Note that you don't even have to add the import, the Babel plugin does that automatically! (unless you're using the Babel macro, see below)

与 Babel 宏一起使用(Usage with the Babel macro)

¥Usage with the Babel macro

Note

由于缺乏使用和其他消费者不必要的膨胀,此功能在 v6.1 中被删除。更多信息

¥This functionality was removed in v6.1 due to lack of usage and unnecessary bloat for other consumers. More info

你可以使用 Babel 宏create-react-app 中完成此操作。不幸的是,Babel 宏仅在导入时运行,因此无法自动添加导入。如果你手动将导入添加到宏,则上述代码可以完美运行:

¥You can use the Babel macro to make this work in create-react-app. Unfortunately, Babel macros only run when imported so the import can not be added automatically. The above code works perfectly if you add the import to the macro manually:

import styled from 'styled-components/macro'


<div
  css={`
    background: papayawhip;
    color: ${props => props.theme.colors.text};
  `}
/>
<Button
  css="padding: 0.5em 1em;"
/>

与 TypeScript 一起使用(Usage with TypeScript)

¥Usage with TypeScript

为了防止任意元素上的 css 属性出现 TypeScript 错误,请安装 @types/styled-components 并在项目中添加以下导入:

¥To prevent TypeScript errors on the css prop on arbitrary elements, install @types/styled-components and add the following import once in your project:

import {} from 'styled-components/cssprop'

请参阅 https://github.com/DefinitelyTyped/DefinitelyTyped/issues/31245#issuecomment-446011384 了解更多信息。

¥See https://github.com/DefinitelyTyped/DefinitelyTyped/issues/31245#issuecomment-446011384 for more information.

如果你使用的版本高于 v6,则无需安装 @types/styled-components。相反,你可以直接在项目中导入 CSSProp,如下所示:

¥If you're using a higher version than v6, you do not need to install @types/styled-components. Instead, you can directly import the CSSProp in your project like this:

import {} from 'react'
import type { CSSProp } from 'styled-components'


declare module 'react' {
  interface Attributes {
    css?: CSSProp | undefined
  }
}

辅助程序(Helpers)

¥Helpers

createGlobalStyle(createGlobalStyle)

| v4 | web-only

用于生成处理全局样式的特殊 StyledComponent 的辅助函数。通常,样式化组件会自动将范围限定为本地 CSS 类,因此与其他组件隔离。在 createGlobalStyle 中,此限制被删除,并且可以应用 CSS 重置或基本样式表等内容。

¥A helper function to generate a special StyledComponent that handles global styles. Normally, styled components are automatically scoped to a local CSS class and therefore isolated from other components. In the case of createGlobalStyle, this limitation is removed and things like CSS resets or base stylesheets can be applied.

ArgumentsDescription
  1. TaggedTemplateLiteral

A tagged template literal with your CSS and interpolations.

返回不接受子项的 StyledComponent。将其放置在 React 树的顶部,当组件为 "rendered" 时,将注入全局样式。

¥Returns a StyledComponent that does not accept children. Place it at the top of your React tree and the global styles will be injected when the component is "rendered".

import { createGlobalStyle } from 'styled-components'


const GlobalStyle = createGlobalStyle<{ $whiteColor?: boolean; }>`
  body {
    color: ${props => (props.$whiteColor ? 'white' : 'black')};
  }
`


// later in your app


<React.Fragment>
  <GlobalStyle $whiteColor />
  <Navigation /> {/* example of other top-level stuff */}
</React.Fragment>

由于 GlobalStyle 组件是 StyledComponent,这意味着它还可以访问 <ThemeProvider> 组件 的主题(如果提供)。

¥Since the GlobalStyle component is a StyledComponent, that means it also has access to theming from the <ThemeProvider> component if provided.

import { createGlobalStyle, ThemeProvider } from 'styled-components'


const GlobalStyle = createGlobalStyle<{ $whiteColor?: boolean; }>`
  body {
    color: ${props => (props.$whiteColor ? 'white' : 'black')};
    font-family: ${props => props.theme.fontFamily};
  }
`


// later in your app


<ThemeProvider theme={{ fontFamily: 'Helvetica Neue' }}>
  <React.Fragment>
    <Navigation /> {/* example of other top-level stuff */}
    <GlobalStyle $whiteColor />
  </React.Fragment>
</ThemeProvider>

css(css)

一个辅助函数,用于通过插值从模板字面量生成 CSS。如果由于标记模板字面量在 JavaScript 中的工作方式而返回带有插值内函数的模板字面量,则需要使用此选项。

¥A helper function to generate CSS from a template literal with interpolations. You need to use this if you return a template literal with functions inside an interpolation due to how tagged template literals work in JavaScript.

如果你要插入字符串,则仅当你要插入函数时才需要使用它。

¥If you're interpolating a string you do not need to use this, only if you're interpolating a function.

ArgumentsDescription
  1. TaggedTemplateLiteral

A tagged template literal with your CSS and interpolations.

返回一个插值数组,它是一个扁平化的数据结构,你可以将其作为插值本身传递。

¥Returns an array of interpolations, which is a flattened data structure that you can pass as an interpolation itself.

import styled, { css } from 'styled-components'


interface ComponentProps {
  $complex?: boolean;
  $whiteColor?: boolean;
}


const complexMixin = css<ComponentProps>`
  color: ${props => (props.$whiteColor ? 'white' : 'black')};
`


const StyledComp = styled.div<ComponentProps>`
  /* This is an example of a nested interpolation */
  ${props => (props.$complex ? complexMixin : 'color: blue;')};
`

如果你省略 css,你的函数将是 toString(),并且你将不会获得预期的结果。

¥If you leave off the css your function will be toString()ed and you'll not get the results you expected.

keyframes(keyframes)

| web-only

创建动画关键帧的辅助方法。

¥A helper method to create keyframes for animations.

ArgumentsDescription
  1. TaggedTemplateLiteral

A tagged template literal with your keyframes inside.

返回要在动画声明中使用的关键帧模型。如果你希望获取生成的动画名称,可以在返回的模型上使用 getName() API。

¥Returns a Keyframes model, to be used in your animation declarations. You can use the getName() API on the returned model if you wish to obtain the generated animation name.

Note

在 styled-components v3 及以下版本中,keyframes 辅助程序直接返回动画名称,而不是使用 getName 方法返回对象。

¥In styled-components v3 and below, the keyframes helper directly returned the animation name instead of an object with the getName method.

import styled, { keyframes } from 'styled-components'


const fadeIn = keyframes`
  0% {
    opacity: 0;
  }
  100% {
    opacity: 1;
  }
`


const FadeInButton = styled.button`
  animation: 1s ${fadeIn} ease-out;
`

如果你将样式规则编写为部分样式,请确保使用 css 辅助程序。

¥If you are composing your style rule as a partial, make sure to use the css helper.

import styled, { css, keyframes } from 'styled-components'


interface AnimationProps {
  $animationLength: number;
}


const pulse = keyframes`
  0% {
    opacity: 0;
  }
  100% {
    opacity: 1;
  }
`


const animation = props =>
  css<AnimationProps>`
    ${pulse} ${props.$animationLength} infinite alternate;
  `


const PulseButton = styled.button<AnimationProps>`
  animation: ${animation};
`

你可以在 动画 部分了解有关使用带有样式组件的动画的更多信息。

¥You can learn more about using animations with styled-components in the Animations section.

StyleSheetManager(StyleSheetManager)

用于修改样式处理方式的辅助组件。对于涉及样式组件的给定子树,你可以自定义各种行为,例如 CSS 运行时处理器 (stylis) 如何通过用户态插件和选项覆盖处理样式。

¥A helper component for modifying how your styles are processed. For a given subtree involving styled-components, you can customize various behaviors like how the CSS runtime processor (stylis) handles styles via userland plugins and option overrides.

PropsDescription
disableCSSOMInjection (v5+)

Switches to the slower text node-based CSS injection system for adding styles to the DOM. Useful for integrating with third party tools that haven't been upgraded to consume styles from the CSSOM APIs.

disableVendorPrefixes (v5, removed in v6)

Opts the given subtree out of adding legacy CSS properties for rendered components.

enableVendorPrefixes (v6+)

Opts the given subtree into adding legacy CSS properties for rendered components.

sheet

Thar be dragons ahead. Create and provide your own StyleSheet if necessary for advanced SSR scenarios.

stylisPlugins (v5+)

An array of plugins to be run by stylis during compilation. Check out

what's available on npm

.

target

Thar be dragons ahead. Provide an alternate DOM node to inject styles info.

例如,如果你的应用适用于旧版浏览器,你可能需要为你的样式启用浏览器前缀:

¥For example if your app is intended for legacy browsers, you may want to enable vendor prefixing for your styles:

If you inspect me, there are vendor prefixes for the flexbox style.

另一个例子是通过 userland stylis-plugin-rtl 插件为你的样式启用从右到左的翻译:

¥Another example would be enabling right-to-left translation for your styles via the userland stylis-plugin-rtl plugin:

My border is now on the right!

isStyledComponent(isStyledComponent)

帮助识别样式组件的实用程序。

¥A utility to help identify styled components.

ArgumentsDescription
  1. Function

Any function expected to possibly be a styled component or React component wrapped in a styled component

如果传递的函数是有效的样式化组件封装组件类,则返回 true。它对于确定是否需要封装组件以便将其用作组件选择器非常有用:

¥Returns true if the passed function is a valid styled components-wrapped component class. It can be useful for determining if a component needs to be wrapped such that it can be used as a component selector:

import React from 'react'
import styled, { isStyledComponent } from 'styled-components'
import MaybeStyledComponent from './somewhere-else'


let TargetedComponent = isStyledComponent(MaybeStyledComponent)
  ? MaybeStyledComponent
  : styled(MaybeStyledComponent)``


const ParentComponent = styled.div`
  color: royalblue;


  ${TargetedComponent} {
    color: tomato;
  }
`

withTheme(withTheme)

这是一个高阶组件工厂,用于从 ThemeProvider 获取当前主题并将其作为 theme prop 传递给你的组件。

¥This is a higher order component factory to get the current theme from a ThemeProvider and pass it to your component as a theme prop.

ArgumentsDescription
  1. Component

Any valid React component that can handle a theme prop.

返回封装器内传递的组件(高阶组件)。传递的组件将接收带有当前主题对象的 theme 属性。

¥Returns the passed component inside a wrapper (higher order component). The passed component will receive a theme prop with the current theme object.

import { withTheme } from 'styled-components'


class MyComponent extends React.Component {
  render() {
    console.log('Current theme: ', this.props.theme)
    // ...
  }
}


export default withTheme(MyComponent)
Note

所有样式组件 自动接收主题作为属性,因此仅当你出于其他原因希望访问主题时才需要这样做。

¥All styled components automatically receive the theme as a prop, so this is only necessary if you wish to access the theme for other reasons.

useTheme(useTheme)

| v5

这是一个自定义钩子,用于从 ThemeProvider 获取当前主题。

¥This is a custom hook to get the current theme from a ThemeProvider.

import { useTheme } from 'styled-components'


function MyComponent() {
  const theme = useTheme()
  console.log('Current theme: ', theme)


  // ...
}
Note

所有样式组件 自动接收主题作为属性,因此仅当你出于其他原因希望访问主题时才需要这样做。

¥All styled components automatically receive the theme as a prop, so this is only necessary if you wish to access the theme for other reasons.

ThemeConsumer(ThemeConsumer)

| v4

这是 React.createContext 创建的 "consumer" 组件,作为 ThemeProvider 的配套组件。它使用 渲染属性模式 允许在渲染期间动态访问主题。

¥This is the "consumer" component created by React.createContext as the companion component to ThemeProvider. It uses the render prop pattern to allow for dynamic access to the theme during rendering.

它将当前主题(基于组件树中更高的 ThemeProvider)作为参数传递给子函数。从此函数中,你可能会返回更多 JSX,也可能什么也不返回。

¥It passes the current theme (based on a ThemeProvider higher in your component tree) as an argument to the child function. From this function, you may return further JSX or nothing.

import { ThemeConsumer } from 'styled-components'


export default class MyComponent extends React.Component {
  render() {
    return (
      <ThemeConsumer>
        {theme => <div>The theme color is {theme.color}.</div>}
      </ThemeConsumer>
    )
  }
}
Note

所有样式组件 自动接收主题作为属性,因此仅当你出于其他原因希望访问主题时才需要这样做。

¥All styled components automatically receive the theme as a prop, so this is only necessary if you wish to access the theme for other reasons.

测试实用工具(Test Utilities)

¥Test Utilities

find(find)

| v3

一种方便的方法,用于在给定 DOM 根中查找样式化组件的渲染 DOM 节点的单个实例。

¥A convenience method to find a single instance of a styled component's rendered DOM node within a given DOM root.

import styled from 'styled-components'
import { find } from 'styled-components/test-utils'


const Foo = styled.div`
  color: red;
`


/**


 * Somewhere in your app:


 *  * ReactDOM.render(


 *   <main>


 *     <Foo />


 *   </main>, document.body


 * );
 */


// retrieves the first instance of "Foo" in the body (querySelector under the hood)
find(document.body, Foo) // HTMLDivElement | null

findAll(findAll)

| v3

一种在给定 DOM 根中查找样式化组件渲染的 DOM 节点的所有实例的便捷方法。

¥A convenience method to find all instances of a styled component's rendered DOM node within a given DOM root.

import styled from 'styled-components'
import { findAll } from 'styled-components/test-utils'


const Foo = styled.div`
  color: ${props => props.color};
`


/**


 * Somewhere in your app:


 *  * ReactDOM.render(


 *   <main>


 *     <Foo color="red" />


 *     <Foo color="green" />


 *   </main>, document.body


 * );
 */


// retrieves a NodeList of instances of "Foo" in the body (querySelectorAll under the hood)
findAll(document.body, Foo) // NodeList<HTMLDivElement> | null

enzymeFind(enzymeFind)

| v4

一种在 enzyme 封装纸内查找特定样式组件实例的便捷方法。

¥A convenience method for finding instances of a particular styled component within an enzyme wrapper.

import { mount } from 'enzyme'
import styled from 'styled-components'
import { enzymeFind } from 'styled-components/test-utils'


const Foo = styled.div`
  color: red;
`


const wrapper = mount(
  <div>
    <Foo>bar</Foo>
  </div>
)


enzymeFind(wrapper, Foo)

支持的 CSS(Supported CSS)

¥Supported CSS

在样式化组件中,我们支持所有 CSS 以及嵌套。由于我们生成实际的样式表而不是内联样式,因此在 CSS 中起作用的任何内容都在样式组件中起作用!

¥Within a styled component, we support all of CSS plus nesting. Since we generate an actual stylesheet and not inline styles, whatever works in CSS works in styled-components!

Hello World!

& 符号 (&) 被我们为该样式组件生成的唯一类名所取代,从而可以轻松实现复杂的逻辑。

¥Ampersands (&) get replaced by our generated, unique classname for that styled component, making it easy to have complex logic.

TypeScript(TypeScript)

| v6

styled-components 提供 TypeScript 定义,增强 IDE 中的编辑体验并提高 TypeScript 项目的类型安全性。

¥styled-components provides TypeScript definitions which empowers the editing experience in IDEs and increases type safety for TypeScript projects.

Note

对于旧版本的样式组件,可以通过 @types/styled-components NPM 包获取社区定义。

¥For older versions of styled-components, there are community definitions available via the @types/styled-components NPM package.

创建声明文件(Create a declarations file)

¥Create a declarations file

样式组件的 TypeScript 定义可以通过使用自 v4.1.4 版本以来的 声明合并 进行扩展。

¥TypeScript definitions for styled-components can be extended by using declaration merging since version v4.1.4 of the definitions.

因此,第一步是创建声明文件。例如,我们将其命名为 styled.d.ts

¥So the first step is creating a declarations file. Let's name it styled.d.ts for example.

// import original module declarations
import 'styled-components';


// and extend them!
declare module 'styled-components' {
  export interface DefaultTheme {
    borderRadius: string;


    colors: {
      main: string;
      secondary: string;
    };
  }
}

React-Native:

import 'styled-components/native'


declare module 'styled-components/native' {
  export interface DefaultTheme {
    borderRadius: string;


    colors: {
      main: string;
      secondary: string;
    };
  }
}

DefaultTheme 被用作开箱即用的 props.theme 接口。默认情况下,接口 DefaultTheme 是空的,因此我们需要扩展它。

¥DefaultTheme is being used as an interface of props.theme out of the box. By default the interface DefaultTheme is empty so that's why we need to extend it.

创建主题(Create a theme)

¥Create a theme

现在我们可以使用上面步骤中声明的 DefaultTheme 创建一个主题。

¥Now we can create a theme just by using the DefaultTheme declared at the step above.

// my-theme.ts
import { DefaultTheme } from 'styled-components';


const myTheme: DefaultTheme = {
  borderRadius: '5px',


  colors: {
    main: 'cyan',
    secondary: 'magenta',
  },
};


export { myTheme };

样式组件(Styling components)

¥Styling components

就是这样!我们只需使用任何原始导入即可使用样式组件。

¥That's it! We're able to use styled-components just by using any original import.

import styled, { createGlobalStyle, css } from 'styled-components';


// theme is now fully typed
export const MyComponent = styled.div`
  color: ${props => props.theme.colors.main};
`;


// theme is also fully typed
export MyGlobalStyle = createGlobalStyle`
  body {
    background-color: ${props => props.theme.colors.secondary};
  }
`;


// and this theme is fully typed as well
export cssHelper = css`
  border: 1px solid ${props => props.theme.borderRadius};
`;

使用自定义属性(Using custom props)

¥Using custom props

如果你是 根据属性调整样式,并且这些 props 不是基本标签/组件 props 的一部分,你可以使用如下类型参数告诉 TypeScript 这些额外的自定义 props 是什么 (需要 TypeScript v2.9+):

¥If you are adapting the styles based on props, and those props are not part of the base tag / component props, you can tell TypeScript what those extra custom props are, with type arguments like this (TypeScript v2.9+ is required):

import styled from 'styled-components';
import Header from './Header';


interface TitleProps {
  readonly $isActive: boolean;
}


const Title = styled.h1<TitleProps>`
  color: ${(props) => (props.$isActive ? props.theme.colors.main : props.theme.colors.secondary)};
`;

注意:如果你设置标准标签的样式(如上例中的 <h1>),则样式化组件 不会传递自定义 props(以避免 未知属性警告)。

¥Note: if you style a standard tag (like <h1> in above example), styled-components will not pass the custom props (to avoid the Unknown Prop Warning).

但是,它会将所有这些传递给自定义 React 组件:

¥However, it will pass all of them to a custom React component:

import styled from 'styled-components';
import Header from './Header';


const NewHeader = styled(Header)<{ customColor: string }>`
  color: ${(props) => props.customColor};
`;
// Header will also receive props.customColor

如果 customColor 属性不应传输到 Header 组件,你可以利用 瞬态属性,在其前面加上美元符号 ($):

¥If the customColor property should not be transferred to the Header component, you can leverage transient props, by prefixing it with a dollar sign ($):

import styled from 'styled-components';
import Header from './Header';


const NewHeader2 = styled(Header)<{ $customColor: string }>`
  color: ${(props) => props.$customColor};
`;
// Header does NOT receive props.$customColor

根据你的用例,你可以通过自己提取自定义属性来获得类似的结果:

¥Depending on your use case, you can achieve a similar result by extracting the custom props yourself:

import styled from 'styled-components';
import Header, { Props as HeaderProps } from './Header';


const NewHeader3 = styled(({ customColor, ...rest }: { customColor: string } & HeaderProps) => <Header {...rest} />)`
  color: ${(props) => props.customColor};
`;

或者使用 shouldForwardProp

¥Or using shouldForwardProp:

import styled from 'styled-components';
import Header from './Header';


const NewHeader4 = styled(Header).withConfig({
  shouldForwardProp: (prop) => !['customColor'].includes(prop),
})<{ customColor: string }>`
  color: ${(props) => props.customColor};
`;

className 的警告(Caveat with className)

¥Caveat with className

定义组件时,你需要在 Props 界面中将 className 标记为可选:

¥When defining a component you will need to mark className as optional in your Props interface:

interface LogoProps {
  /* This prop is optional, since TypeScript won't know that it's passed by the wrapper */
  className?: string;
}


class Logo extends React.Component<LogoProps, {}> {
  render() {
    return <div className={this.props.className}>Logo</div>;
  }
}


const LogoStyled = styled(Logo)`
  font-family: 'Helvetica';
  font-weight: bold;
  font-size: 1.8rem;
`;

函数组件的注意事项(Caveat with Function Components)

¥Caveat with Function Components

要使用函数组件并对 props 进行类型检查,你需要定义组件及其类型。这对于样式组件来说并不特殊,这就是 React 的工作原理:

¥To use function components and have typechecking for the props you'll need to define the component alongside with its type. This is not special to styled-components, this is just how React works:

interface BoxProps {
  theme?: ThemeInterface;
  borders?: boolean;
  className?: string;
}


const Box: React.FunctionComponent<BoxProps> = (props) => <div className={props.className}>{props.children}</div>;


const StyledBox = styled(Box)`
  padding: ${(props) => props.theme.lateralPadding};
`;

以前的 API(Previous APIs)

¥Previous APIs

.extend(.extend)

Note

styled-components v4 中删除了 .extend API。请改用 styled(StyledComponent)。有关更多信息,请参阅:https://github.com/styled-components/styled-components/issues/1546

¥The .extend API was removed in styled-components v4. Use styled(StyledComponent) instead. For more information, see: https://github.com/styled-components/styled-components/issues/1546

这是一种创建新的 StyledComponent 并扩展其规则的方法。

¥This is a method that creates a new StyledComponent and extends its rules.

ArgumentsDescription
  1. TaggedTemplateLiteral

A tagged template literal with your CSS and interpolations.

import styled from 'styled-components'


const Component = styled.div`
  color: red;
`


const Component2 = Component.extend`
  background: white;
  color: blue;
`

返回一个新的 StyledComponent,其中新规则合并到调用此方法的组件的规则中。

¥Returns a new StyledComponent with the new rules merged into the ones of the component this method was called on.

injectGlobal(injectGlobal)

Note

在 styled-components v4 中,injectGlobal API 被删除并被 createGlobalStyle 取代。

¥The injectGlobal API was removed and replaced by createGlobalStyle in styled-components v4.

编写全局 CSS 的辅助方法。它不返回组件,而是直接将样式添加到样式表中。

¥A helper method to write global CSS. It does not return a component, but adds the styles to the stylesheet directly.

ArgumentsDescription
  1. TaggedTemplateLiteral

A tagged template literal with your global styles inside.

import { injectGlobal } from 'styled-components'


injectGlobal`
  @font-face {
    font-family: "Operator Mono";
    src: url("../fonts/Operator-Mono.ttf");
  }


  body {
    margin: 0;
  }
`

我们不鼓励使用此功能。如果必须的话,尝试在每个应用中最多使用一次它,并将其包含在单个文件中。这是一个应急方案。仅将其用于罕见的 @font-face 定义或主体样式。

¥We do not encourage the use of this. Try to use it once per app at most, if you must, contained in a single file. This is an escape hatch. Only use it for the rare @font-face definition or body styling.

"innerRef" 属性("innerRef" prop)

¥"innerRef" prop

Note

"innerRef" 属性在 styled-components v4 中被删除,取而代之的是 React 16 forwardRef API。只需使用普通的 ref 属性即可。

¥The "innerRef" prop was removed in styled-components v4 in favor of the React 16 forwardRef API. Just use the normal ref prop instead.

ref 属性传递给样式化组件将为你提供 StyledComponent 封装器的实例,但不会传递给底层 DOM 节点。这是由于裁判的工作方式造成的。不可能在我们的封装器上直接调用 DOM 方法,例如 focus

¥Passing a ref prop to a styled component will give you an instance of the StyledComponent wrapper, but not to the underlying DOM node. This is due to how refs work. It's not possible to call DOM methods, like focus, on our wrappers directly.

要获取对实际的、封装的 DOM 节点的引用,请将回调传递给 innerRef 属性。

¥To get a ref to the actual, wrapped DOM node, pass the callback to the innerRef prop instead.

Note

我们不支持字符串引用(即 innerRef="node"),因为它们在 React 中已被弃用。

¥We don't support string refs (i.e. innerRef="node"), since they're already deprecated in React.

此示例使用 innerRef 保存对样式输入的引用,并在用户将鼠标悬停在其上时将其聚焦。

¥This example uses innerRef to save a ref to the styled input and focuses it once the user hovers over it.

const Input = styled.input`
  padding: 0.5em;
  margin: 0.5em;
  color: #BF4F74;
  background: papayawhip;
  border: none;
  border-radius: 3px;
`


class Form extends React.Component {
  render() {
    return (
      <Input
        placeholder="Hover here..."
        innerRef={x => {
          this.input = x
        }}
        onMouseEnter={() => this.input.focus()}
      />
    )
  }
}

.withComponent(.withComponent)

Note

withComponent API 在 styled-components v4 中被 "as" 属性 取代,并在 v6 中完全删除。

¥The withComponent API was replaced by "as" prop in styled-components v4, and fully-removed in v6.

这是一种创建新的 StyledComponent 的方法,其中应用了不同的标签或组件,但其规则与调用它的规则相同。

¥This is a method that creates a new StyledComponent with a different tag or component applied to it, but all the same rules of the one it's called on.

ArgumentsDescription
  1. component / tagname

Either a valid react component or a tagname like 'div'.

返回一个新的 StyledComponent,并在使用时应用新的标签/组件。

¥Returns a new StyledComponent with the new tag / component being applied when it's used.

继续下一页

工具