跳到内容
+

日期和时间选择器 - 基本概念

日期和时间选择器公开了许多组件,以满足您的各种需求。

受控值

所有组件都有 value / onChange API 来设置和控制值

Enter 键开始编辑

导入

@mui/x-date-pickers 导出的所有组件也由 @mui/x-date-pickers-pro 导出,但没有嵌套导入。

例如,要使用 DatePicker 组件,以下三个导入都是有效的

import { DatePicker } from '@mui/x-date-pickers/DatePicker';
import { DatePicker } from '@mui/x-date-pickers';
import { DatePicker } from '@mui/x-date-pickers-pro';

日期库

日期和时间选择器专注于 UI/UX,并且像大多数其他可用的选择器组件一样,需要一个第三方库来格式化、解析和修改日期。

MUI 的组件让您可以选择您喜欢的库来实现此目的。这使您可以灵活地实现您可能已经在应用程序中使用的任何日期库,而无需向您的 bundle 添加额外的库。

为了实现这一点,@mui/x-date-pickers@mui/x-date-pickers-pro 都导出一组 适配器,这些适配器在统一的 API 下公开日期操作库。

可用的库

日期和时间选择器目前支持以下日期库

如果您已经在应用程序中使用上面列出的库之一,那么您可以继续将其与日期和时间选择器一起使用。这将避免捆绑两个库。

如果您没有自己的要求,或者不在 MUI X 组件之外操作日期,那么建议使用 dayjs,因为它对应用程序的 bundle 大小影响最小。

这是在日期和时间选择器内部使用时,这些库中的每一个添加到您的 gzipped bundle 大小的权重

Gzipped 大小
dayjs@1.11.5 6.77 kB
date-fns@2.29.3 19.39 kB
luxon@3.0.4 23.26 kB
moment@2.29.4 20.78 kB

其他组件

选择交互样式

根据您的用例,首选不同的交互样式。

  • 对于使用 popover 或 modal 进行鼠标交互的输入编辑,请使用 Picker 组件
  • 对于仅输入的编辑,请使用 Field 组件
  • 对于内联编辑,请使用 Calendar / Clock 组件

日期或时间编辑?

日期和时间选择器分为六个组件系列。下面的演示展示了每个系列使用其字段组件的情况

日期

时间

日期时间

日期范围

时间范围

日期时间范围

响应式

每个 Picker 都有响应式、桌面和移动变体

  • 响应式组件(例如 DatePicker),它根据运行的设备渲染桌面组件或移动组件。

  • 桌面组件(例如 DesktopDatePicker)最适合鼠标设备和大屏幕。它在 popover 内部渲染视图,并允许直接在字段内部编辑值。

  • 移动组件(例如 MobileDatePicker)最适合触摸设备和小屏幕。它在 modal 内部渲染视图,并且不允许直接在字段内部编辑值。

响应式变体

桌面变体

移动变体

Enter 键开始编辑

查找您的组件

有许多可用的组件,每个组件都适合特定的用例。使用下面的表单查找您需要的组件

导入代码

import { DatePicker } from '@mui/x-date-pickers/DatePicker';
import { DatePicker } from '@mui/x-date-pickers';
import { DatePicker } from '@mui/x-date-pickers-pro';

import { DesktopDatePicker } from '@mui/x-date-pickers/DesktopDatePicker';
import { DesktopDatePicker } from '@mui/x-date-pickers';
import { DesktopDatePicker } from '@mui/x-date-pickers-pro';

import { MobileDatePicker } from '@mui/x-date-pickers/MobileDatePicker';
import { MobileDatePicker } from '@mui/x-date-pickers';
import { MobileDatePicker } from '@mui/x-date-pickers-pro';

import { StaticDatePicker } from '@mui/x-date-pickers/StaticDatePicker';
import { StaticDatePicker } from '@mui/x-date-pickers';
import { StaticDatePicker } from '@mui/x-date-pickers-pro';

实时示例

DatePicker

DesktopDatePicker

MobileDatePicker

StaticDatePicker

选择日期

––

未定义值时的参考日期

如果 valuedefaultValue 包含有效日期,则此日期将用于初始化渲染的组件。

在下面的演示中,您可以看到日历在挂载时设置为 2022 年 4 月

Enter 键开始编辑

valuedefaultValue 不包含有效日期时,组件将尝试查找通过验证的参考日期以初始化其渲染

无验证:使用今天

验证:使用 maxDate 的日期

Enter 键开始编辑

您可以使用 referenceDate prop 覆盖此日期

存储的值null

Enter 键开始编辑

这对于设置组件中不可选择的值部分也很有用。例如,在时间选择器中,它允许您选择值的日期

存储的值null

Enter 键开始编辑

TypeScript

主题增强

为了从主题的 CSS 覆盖默认 prop 自定义 中受益,TypeScript 用户需要导入以下类型。在内部,它使用模块增强来扩展默认主题结构。

import type {} from '@mui/x-date-pickers/themeAugmentation';
import type {} from '@mui/x-date-pickers-pro/themeAugmentation';

const theme = createTheme({
  components: {
    MuiDatePicker: {
      defaultProps: {
        displayWeekNumber: true,
      },
    },
    MuiDateRangeCalendar: {
      styleOverrides: {
        root: {
          backgroundColor: '#f0f0f0',
        },
      },
    },
  },
});

日期类型

日期和时间选择器组件与多个日期库兼容,这些日期库使用不同的格式来表示它们的日期(date-fnsDate 对象,days-jsdaysjs.Dayjs 对象等)。为了正确键入所有与日期相关的 props,适配器覆盖了一个名为 PickerValidDate 的全局类型,以允许使用它们自己的日期格式。如果您尝试将 value={new Date()} 传递给使用 AdapterDayjs 的组件,这将允许 TypeScript 抛出错误。

如果您不确定您的适配器是否已正确设置以推断与日期相关的 props 的类型,您可以导入 PickerValidDate 类型并检查其当前值。

如果它等于您的日期库使用的格式,那么您不必做任何事情

PickerValidDate correctly configured

如果它等于 any,您可以通过在项目的某个文件中手动导入适配器来修复它,如下所示

PickerValidDate not correctly configured
// Replace `AdapterDayjs` with the adapter you are using.
import type {} from '@mui/x-date-pickers/AdapterDayjs';

测试注意事项

响应式组件

请注意,在无头浏览器中运行测试可能无法通过默认的 mediaQuery (pointer: fine)。在这种情况下,您可以通过浏览器标志或首选项强制指针精度

字段组件

要添加关于字段值的测试而无需关心这些字符,您可以在测试相等性之前删除特定字符。这是一个关于如何做到这一点的示例。

// Helper removing specific characters
const cleanText = (string) =>
  string.replace(/\u200e|\u2066|\u2067|\u2068|\u2069/g, '');

// Example of a test using the helper
expect(cleanText(input.value)).to.equal('04-17-2022');

覆盖插槽和插槽属性

日期和时间选择器是使用许多称为 插槽 的子组件构建的复杂组件。插槽通常由 React 组件填充,您可以使用 slots prop 覆盖这些组件。您还可以使用 slotProps prop 将其他 props 传递给可用的插槽。在 Base UI 文档中了解有关插槽心智模型的更多信息:覆盖组件结构

您可以在其各自的 API 参考 文档中找到每个组件的可用插槽列表。

Pickers UI 的某些部分是建立在几个嵌套插槽之上的。例如,DatePickerTextField 的装饰包含三个插槽(inputAdornmentopenPickerButtonopenPickerIcon),您可以根据您要自定义的内容使用它们。