# PickerDialog - 滚轮选择弹窗

## 说明

带滚轮选择器的弹窗，支持 1~4 列（超出按前 4 列截取）。基于 `ActionCustomDialog` 封装，默认提供「取消 / 确定」两个按钮，点击确定时回调当前各列选中值。

下表中标注「继承自 BaseDialog」的属性为 Dialog 体系公共属性（类型为 `Omit<BaseDialogPropsType, 'showTitle' | 'showButton'>` 再加滚轮相关属性）。

## 属性

| 属性 | 说明 | 类型 | 默认值 | 必填 |
|------|------|------|--------|------|
| **visible** | 是否显示弹窗 | `boolean` | - | 是 |
| **columns** | 滚轮列配置，1~4 列，超出部分被截取 | `PickerColumn[]` | - | 是 |
| **colorType** | 选中文字色系 | `ColorType` | `'green'` | 否 |
| **onChange** | 滚动时实时回调，返回全部列当前值及变化的列索引 | `(values: string[], columnIndex: number) => void` | - | 否 |
| **onConfirm** | 点击默认确定按钮时回调当前各列选中值 | `(values: string[]) => void` | - | 否 |
| **title** | 标题文案（继承自 BaseDialog） | `string` | - | 否 |
| **buttons** | 自定义底部按钮，1~3 个（继承自 BaseDialog） | `AbstractDialogButtonType[]` | `[取消, 确定]` | 否 |
| **colorDepth** | 弹窗底色深度（继承自 BaseDialog） | `'base' \| 'low'` | `'base'` | 否 |
| **canDismiss** | 点击遮罩是否可关闭（继承自 BaseDialog） | `boolean` | `true` | 否 |
| **cancelable** | 返回键及无 callback 按钮是否可关闭弹窗（继承自 BaseDialog） | `boolean` | `true` | 否 |
| **hasShade** | 是否显示半透明遮罩背景（继承自 BaseDialog） | `boolean` | `true` | 否 |
| **onDismiss** | 非点击按钮方式（遮罩、返回键）关闭时回调（继承自 BaseDialog） | `() => void` | - | 否 |
| **onModalShow** | 弹窗显示时回调（继承自 BaseDialog） | `() => void` | - | 否 |
| **onModalHide** | 弹窗隐藏时回调（继承自 BaseDialog） | `() => void` | - | 否 |
| **accessible** | 无障碍：是否启用（继承自 BaseDialog） | `boolean` | `true` | 否 |
| **accessibilityLabel** | 无障碍标签（继承自 BaseDialog） | `string` | - | 否 |
| **layerDismissAccessibilityHint** | 遮罩可点击区域的无障碍标签（继承自 BaseDialog） | `string` | - | 否 |

### PickerColumn（列配置）

| 字段 | 说明 | 类型 | 默认值 | 必填 |
|------|------|------|--------|------|
| **options** | 选项列表 | `string[]` | - | 是 |
| **title** | 列标题（显示在滚轮上方；任一列有标题则各列都占位标题行） | `string` | - | 否 |
| **defaultValue** | 默认选中值，缺省时取 `options[0]` | `string` | - | 否 |
| **unit** | 选项单位 | `string` | - | 否 |

## 使用示例

```tsx
import { PickerDialog } from 'miot/ui/hyperOSUI';

<PickerDialog
  visible={visible}
  title="选择时间"
  colorType="blue"
  columns={[
    { title: '小时', options: ['00', '01', '02', '03'], defaultValue: '01', unit: '时' },
    { title: '分钟', options: ['00', '15', '30', '45'], defaultValue: '30', unit: '分' },
  ]}
  onChange={(values, columnIndex) => console.log(values, columnIndex)}
  onConfirm={(values) => {
    setTime(values);
    setVisible(false);
  }}
  onDismiss={() => setVisible(false)}
/>
```

## 注意事项

- 最多展示 4 列，`columns` 超过 4 项时只取前 4 列。
- `onConfirm` 仅在使用默认按钮时由内置「确定」按钮触发；一旦传入自定义 `buttons`，默认确定按钮被替换，`onConfirm` 不会自动触发，需在自定义按钮的 `callback` 内自行处理选中值。
- `onChange` 在滚动过程中实时触发（返回最新的全列值与当前变化列索引），`onConfirm` 只在确定时触发一次。
- 列标题为「要么全有、要么全无」的占位策略：只要有任意一列设置了 `title`，所有列都会渲染标题行（无标题的列用空白占位）。
- 当 `columns` 的选项集合发生变化时，各列选中值会重置为各自的初始值（`defaultValue` 或首项）。
- 内部依赖 `StringSpinner` 渲染滚轮，选项均为字符串。

## 修改记录

| 日期 | 版本 | 修改内容 | 修改原因 | 关联 |
|------|------|----------|----------|------|
| 2026-09-16 | v1.18.20 | 修复多列场景下选中值回传错乱（智能门锁周期密码时间显示异常） | — | IOT-75567 |
| 2026-06-12 | v1.18.12 | 修复滚轮弹窗若干问题 | — | 817dd26f |
| 2026-06-04 | v1.18.12 | 弹窗样式优化 | — | 12981332 |
| 2026-05-26 | v1.18.8 | 修复潜在隐患问题 | — | 4c8d1241 |
| 2026-04-16 | v1.18.5-alpha.0 | 滚轮弹窗细节样式优化 | — | 805a263e |
| 2026-04-14 | v1.18.5-alpha.0 | HyperOS 滚轮选择弹窗初版实现 | — | 9dc50c99 |
