跳到内容
+

开始使用 Pigment CSS

了解如何开始使用 Pigment CSS 定制你的组件。

Pigment CSS 是一个零运行时的 CSS-in-JS 库,它在构建时预编译,使其与 React Server Components 兼容,并为您提供比其他样式引擎更显著的性能提升。

Pigment CSS 与任何 React 组件库兼容,并且可以与 Vite 和 Next.js 一起使用。

如果您有现有的 Material UI 项目,请查看 迁移到 Pigment CSS 指南。

先决条件

  • Node.js
  • 一个包管理器
  • 一个 Next.js 或 Vite 项目

您可以使用以下命令快速开始 Pigment CSS 的安装和项目创建

curl https://codeload.github.com/mui/pigment-css/tar.gz/master | tar -xz --strip=2  pigment-css-master/examples/pigment-css-nextjs-ts
cd pigment-css-nextjs-ts

手动安装

要在现有项目上开始使用,请使用以下命令安装 Pigment CSS

npm install @pigment-css/react
npm install --save-dev @pigment-css/nextjs-plugin

接下来,前往你的配置文件并导入 withPigment 插件

// next.config.js
import { withPigment } from '@pigment-css/nextjs-plugin';

export default withPigment(nextConfig);

最后,在你的 layout.tsx (Next.js) 或 main.tsx (Vite) 文件中导入 Pigment CSS 样式表

import '@pigment-css/react/styles.css';

用法

Pigment CSS 满足了现代 React 开发的需求:它与 React Server Components 兼容,并让您获得 CSS-in-JS 的好处——所有这些都无需运行时性能成本。

使用 Pigment CSS,您可以创建本地作用域的可重用样式、主题、CSS 变量等等。

样式化

Pigment CSS 通过各种 API 简化了样式的创建和定义

  • css:用于可重用样式
  • globalCss:用于全局样式
  • keyframes:用于可重用动画关键帧
  • styled:用于样式化组件

创建可重用样式

使用 css API 创建可重用样式

import { css } from '@pigment-css/react';

您可以使用模板或对象语法来执行此操作

模板语法

const bodyBackground = css`
  background-color: #000;
  color: #fff;
`;

对象语法

const mainClass = css({
  display: '#000',
  color: '#fff',
});

创建全局样式

使用 globalCss API 定义全局样式,以在整个应用程序中加载。

您应该在 JavaScript 文件的顶层定义这些样式

import { globalCss } from '@pigment-css/react';

globalCss`
  body {
    margin: 0;
    padding: 0;
  }
`;

创建样式化组件

将样式限定于组件可确保仅加载必要的 CSS,并带来更好的模块化、可读性和可维护性。您可以根据 props 或运行时值将条件样式应用于您的组件。

使用 styled API 创建样式化组件

import { styled } from '@pigment-css/react';

const Heading = styled('div')({
  fontSize: '2rem',
  color: '#9FADBC',
  fontWeight: 'bold',
  margin: '1rem',
});

基于 props 的样式化

使用 variants 键来定义基于 props 的不同样式选项。当 prop 的值在构建时已知时,建议使用此方法。

每个 variants 都是一个具有 propsstyle 键的对象

import { styled } from '@pigment-css/react';

const Heading = styled('div')({
  fontSize: '2rem',
  color: '#9FADBC',
  fontWeight: 'bold',
  margin: '1rem',
  variants: [
    {
      props: { variant: 'success' },
      style: { color: '#23AD79' },
    },
    {
      props: { size: 'small' },
      style: { fontSize: '1.5rem' },
    },
  ],
});

基于运行时值的样式化

当 prop 的值在事先未知时,您可以基于运行时值来样式化您的组件

const Heading = styled('h1')({
  color: ({ isError }) => (isError ? 'red' : 'black'),
});

主题

Pigment CSS 支持主题化,以在整个应用程序中应用一致的样式和值。您可以通过在配置文件中定义主题来创建主题

import { withPigment } from '@pigment-css/nextjs-plugin';

export default withPigment(nextConfig, {
  theme: {
    colors: {
      primary: 'tomato',
      secondary: 'cyan',
    },
    spacing: {
      unit: 8,
    },
    typography: {
      fontFamily: 'Inter, sans-serif',
    },
    // ...more keys and values, it's free style!
  },
});

要访问你的主题,请将回调与 styled()css() API 一起使用

const Heading = styled('h1')(({ theme }) => ({
  color: theme.colors.primary,
  fontSize: theme.spacing.unit * 4,
  fontFamily: theme.typography.fontFamily,
}));

CSS 变量支持

当主题值被 extendTheme 实用程序包装时,Pigment CSS 从主题值生成 CSS 变量,从而创建一个 vars 对象

import { withPigment, extendTheme } from '@pigment-css/nextjs-plugin';

export default withPigment(nextConfig, {
  theme: extendTheme({
    colors: {
      primary: 'tomato',
      secondary: 'cyan',
    },
    spacing: {
      unit: 8,
    },
    typography: {
      fontFamily: 'Inter, sans-serif',
    },
  }),
});

配色方案

您可以使用 extendTheme 实用程序中的 colorSchemes 键,根据不同的条件分配不同的值,例如在暗模式和亮模式之间切换

extendTheme({
  colorSchemes: {
    light: {
      colors: {
        background: '#f9f9f9',
        foreground: '#121212',
      },
    },
    dark: {
      colors: {
        background: '#212121',
        foreground: '#fff',
      },
    },
  },
});

Pigment CSS 默认使用 prefers-color-scheme 媒体查询在配色方案之间切换

const colorScheme = css`
  background-color: ${({ theme }) => theme.colorSchemes.dark.colors.background};
  color: ${({ theme }) => theme.colorSchemes.dark.colors.foreground};

  @media (prefers-color-scheme: light) {
    background-color: ${({ theme }) => theme.colorSchemes.light.colors.background};
    color: ${({ theme }) => theme.colorSchemes.light.colors.foreground};
  }
`;

您还可以通过提供 getSelector 函数来自定义行为

 extendTheme({
   colorSchemes: {
     light: { ... },
     dark: { ... },
   },
+  getSelector: (colorScheme) => colorScheme ? `.theme-${colorScheme}` : ':root',
 });

sx prop

Pigment CSS 包含 sx prop,它允许您为任何元素提供一次性的内联自定义样式。

在构建时,Pigment CSS 将 sx prop 替换为 classNamestyle props。sx prop 适用于所有 Material UI 组件以及 HTML 元素和任何第三方 JSX 组件。

<div sx={{ display: 'flex', flexDirection: 'column' }}>

<AnyComponent sx={{ fontSize: 12, color: 'red' }} />;

如果您在 HTML 元素上使用 sx prop,则需要扩充 HTMLAttributes 接口

type Theme = {
  // your theme type
};

declare global {
  namespace React {
    interface HTMLAttributes<T> {
      sx?:
        | React.CSSProperties
        | ((theme: Theme) => React.CSSProperties)
        | ReadonlyArray<
            React.CSSProperties | ((theme: Theme) => React.CSSProperties)
          >;
    }
  }
}

运行时主题

要访问运行时主题,请使用 useTheme hook

import { useTheme } from '@mui/material-pigment-css';

function MyComponent() {
  const theme = useTheme();

  return (
    <div>
      {Object.entries(theme.vars.palette.primary).map(([key, value]) => (
        <div key={key} style={{ width: 40, height: 40, background: value }}>
          {key}: {value}
        </div>
      ))}
    </div>
  );
}