---
nav:
  title: 组件
  order: 1
group:
  title: 基础组件
  order: 1
title: PisellCards
order: 1
category: atom
---

# PisellCards 卡片组件

PisellCards 是一个卡片组件的命名空间容器，用于收纳各种卡片组件。

## 设计理念

在我们的概念中，只要是按某种规律循环出来的 item，我们都称之为 card，比如：

- 商品列表中的每一个商品
- tabs 列表中的每一个 tab
- 菜单列表中的每一个菜单
- 列表中的每一个列表项

## 组件列表

### TabCard - 标签卡片

标签卡片组件，用于导航、分类切换、筛选等场景。

## 基础使用

### 基础标签

```tsx
import { PisellCards } from '@pisell/materials';

export default () => {
  return (
    <div style={{ display: 'flex', gap: '8px' }}>
      <PisellCards.TabCard tabKey="home" label="首页" />
      <PisellCards.TabCard tabKey="about" label="关于" />
      <PisellCards.TabCard tabKey="contact" label="联系" />
    </div>
  );
};
```

### 激活状态

```tsx
import { PisellCards } from '@pisell/materials';
import { useState } from 'react';

export default () => {
  const [activeKey, setActiveKey] = useState('home');

  return (
    <div style={{ display: 'flex', gap: '8px' }}>
      <PisellCards.TabCard
        tabKey="home"
        label="首页"
        active={{ value: activeKey === 'home' }}
        onClick={(key) => setActiveKey(key)}
      />
      <PisellCards.TabCard
        tabKey="about"
        label="关于"
        active={{ value: activeKey === 'about' }}
        onClick={(key) => setActiveKey(key)}
      />
      <PisellCards.TabCard
        tabKey="contact"
        label="联系"
        active={{ value: activeKey === 'contact' }}
        onClick={(key) => setActiveKey(key)}
      />
    </div>
  );
};
```

### 带图标和徽章

```tsx
import { PisellCards } from '@pisell/materials';
import { HomeOutlined, MessageOutlined, UserOutlined } from '@ant-design/icons';

export default () => {
  return (
    <div style={{ display: 'flex', gap: '8px' }}>
      <PisellCards.TabCard
        tabKey="home"
        label="首页"
        icon={<HomeOutlined />}
      />
      <PisellCards.TabCard
        tabKey="messages"
        label="消息"
        icon={<MessageOutlined />}
        badge={{ count: 5, color: 'red' }}
      />
      <PisellCards.TabCard
        tabKey="profile"
        label="个人"
        icon={<UserOutlined />}
        badge={{ dot: true }}
      />
    </div>
  );
};
```

### 垂直布局

```tsx
import { PisellCards } from '@pisell/materials';
import { HomeOutlined, MessageOutlined, UserOutlined } from '@ant-design/icons';

export default () => {
  return (
    <div style={{ display: 'flex', gap: '8px' }}>
      <PisellCards.TabCard
        tabKey="home"
        label="首页"
        icon={<HomeOutlined />}
        direction="vertical"
      />
      <PisellCards.TabCard
        tabKey="messages"
        label="消息"
        icon={<MessageOutlined />}
        direction="vertical"
        badge={{ count: 5 }}
      />
      <PisellCards.TabCard
        tabKey="profile"
        label="个人"
        icon={<UserOutlined />}
        direction="vertical"
      />
    </div>
  );
};
```

### 不同尺寸

```tsx
import { PisellCards } from '@pisell/materials';

export default () => {
  return (
    <div style={{ display: 'flex', flexDirection: 'column', gap: '16px' }}>
      <div style={{ display: 'flex', gap: '8px' }}>
        <PisellCards.TabCard tabKey="small1" label="小尺寸" size="small" />
        <PisellCards.TabCard tabKey="small2" label="Small" size="small" />
      </div>
      <div style={{ display: 'flex', gap: '8px' }}>
        <PisellCards.TabCard tabKey="medium1" label="中尺寸" size="medium" />
        <PisellCards.TabCard tabKey="medium2" label="Medium" size="medium" />
      </div>
      <div style={{ display: 'flex', gap: '8px' }}>
        <PisellCards.TabCard tabKey="large1" label="大尺寸" size="large" />
        <PisellCards.TabCard tabKey="large2" label="Large" size="large" />
      </div>
    </div>
  );
};
```

### 禁用和加载状态

```tsx
import { PisellCards } from '@pisell/materials';
import { Spin } from 'antd';

export default () => {
  return (
    <div style={{ display: 'flex', gap: '8px' }}>
      <PisellCards.TabCard tabKey="normal" label="正常" />
      <PisellCards.TabCard
        tabKey="disabled"
        label="禁用"
        disabled={{ value: true }}
      />
      <PisellCards.TabCard
        tabKey="loading"
        label="加载中"
        loading={{ value: true, extra: <Spin size="small" /> }}
      />
    </div>
  );
};
```

## API

### TabCard Props

| 参数 | 说明 | 类型 | 默认值 | 必填 |
| --- | --- | --- | --- | --- |
| tabKey | 标签唯一标识 | `string \| number` | - | ✅ |
| label | 标签文本 | `ReactNode` | - | ✅ |
| icon | 标签图标 | `ReactNode` | - | ❌ |
| badge | 徽章配置 | `BadgeConfig` | - | ❌ |
| onClick | 点击事件 | `(tabKey, event) => void` | - | ❌ |
| direction | 布局方向 | `'horizontal' \| 'vertical'` | `'horizontal'` | ❌ |
| size | 标签尺寸 | `'small' \| 'medium' \| 'large'` | `'medium'` | ❌ |
| render | 自定义渲染函数 | `(props) => ReactNode` | - | ❌ |
| active | 激活状态配置 | `StateConfig` | - | ❌ |
| disabled | 禁用状态配置 | `StateConfig` | - | ❌ |
| loading | 加载状态配置 | `StateConfig` | - | ❌ |
| className | 自定义类名 | `string` | - | ❌ |
| style | 自定义样式 | `CSSProperties` | - | ❌ |
| children | 子内容 | `ReactNode` | - | ❌ |

### BadgeConfig

| 参数 | 说明 | 类型 | 默认值 |
| --- | --- | --- | --- |
| count | 徽章数字或文本 | `number \| string` | - |
| dot | 是否显示小红点 | `boolean` | - |
| color | 徽章颜色 | `string` | - |
| offset | 徽章偏移位置 | `[number, number]` | - |

### StateConfig

| 参数 | 说明 | 类型 |
| --- | --- | --- |
| value | 状态值 | `boolean` |
| style | 状态样式 | `CSSProperties` |
| className | 状态类名 | `string` |
| onChange | 状态改变回调 | `(value: boolean) => void` |
| extra | 额外内容 | `any` |

## 扩展开发

如果你需要开发新的业务卡片组件，请参考 [设计文档](./PisellCards.$tab-design.md) 和 [开发文档](./PisellCards.$tab-dev.md)。

所有业务卡片都应该：

1. 基于 `PisellBasicCardProps` 扩展 Props
2. 实现状态处理逻辑（active、disabled、loading）
3. 收纳到 `PisellCards` 命名空间下

## 注意事项

- `PisellBasicCard` 不是实体组件，仅仅是类型定义
- 业务方需要自行实现状态处理逻辑
- 所有卡片组件都应该收纳到 `PisellCards` 命名空间下
