跳到内容
+

自动完成

自动完成是一个文本输入框,当用户开始输入时,会弹出一个包含建议选项的面板,从而增强了文本输入体验。

简介

Autocomplete 是文本输入框的增强版本,它会在用户输入时显示建议选项,并允许用户从列表中选择一个选项。


功能标识
  • 完成字符串在文本框中的输入光标后内联显示。内联完成字符串在视觉上突出显示,并具有选定状态。
  • 第一个选项会自动高亮显示。
  • 当 Autocomplete 失去焦点时,选定的选项将成为输入框的值,除非用户选择不同的选项或更改输入框中的字符串。
  • 输入框始终失去焦点。
  • 如果没有选择任何值,输入框的文本在失去焦点时会被清除。
  • 当用户按下 escape 键且弹出框关闭时,清除所有值。
  • 该组件被禁用。
  • 输入框无法被清除
  • 当选择一个值时,弹出框不会关闭。
  • 弹出框中的列表框不会循环焦点。
  • 从列表框中隐藏已选选项。
  • 用户输入不受提供的选项的约束。
  • 高亮可以移动到输入框。
  • 弹出框将在输入框获得焦点时打开。
  • 弹出框将位于父组件的 DOM 结构下。
  • 该组件变为只读。在多标签模式下也支持,此时标签无法删除。
  • 输入框的文本在获得焦点时被选中。这有助于用户清除选定的值。

用法

安装完成后,您可以开始使用以下基本元素构建此组件

import Autocomplete from '@mui/joy/Autocomplete';
import Input from '@mui/joy/Input';

export default function App() {
  return <Autocomplete options={['Option 1', 'Option 2']} />;
}

基础

Autocomplete 组件需要一个 options 列表,在文本框获得焦点后显示。该值必须从预定义的允许值集合中选择。

Enter 键开始编辑

自定义

选项结构

默认情况下,options 接受 string 数组或 { label: string }

const options = [
  { label: 'The Godfather', id: 1 },
  { label: 'Pulp Fiction', id: 2 },
];
// or
const options = ['The Godfather', 'Pulp Fiction'];

但是,您可以通过提供 getOptionLabel 属性来使用不同的结构

const options = [
  { title: 'Pulp Fiction', id: 2 },
  // ...
];

<Autocomplete getOptionLabel={option => option.title}>

选项外观

要自定义选项的外观,请将 renderOption 属性与 AutocompleteOption 组件结合使用作为选项容器。

变体

自动完成组件支持四种全局变体:outlined(默认)、softsolidplain

变体和颜色值会传递到 Autocomplete 的 inputlistbox 插槽。

要自定义特定插槽的变体和颜色,请使用 slotProps

<Autocomplete
  variant="plain"
  slotProps={{
    listbox: {
      variant: 'outlined',
    },
  }}
/>

标签

将 Autocomplete、FormLabel 和 FormHelperText(可选)放在 FormControl 组件下,以创建一个可访问的自动完成组件。

组合框的描述。
Enter 键开始编辑

装饰器

使用 startDecoratorendDecorator 将装饰器插入到自动完成组件。

The Shawshank Redemption
Enter 键开始编辑

受控状态

该组件有两种可以控制的状态

  1. “value” 状态,使用 value/onChange 属性组合。此状态表示用户选择的值,例如按下 Enter 键时。
  2. “input value” 状态,使用 inputValue/onInputChange 属性组合。此状态表示文本框中显示的值。

这两个状态是隔离的,应该独立控制。

value: 'Option 1'

inputValue: ''


禁用选项

使用 getOptionDisabled 属性读取选项并返回 true 以禁用它们。

Enter 键开始编辑

分组选项

您可以使用 groupBy 属性对选项进行分组。如果这样做,请确保选项也按照分组的维度进行排序,否则,您会注意到重复的标题。

Enter 键开始编辑

加载中

只要网络请求处于挂起状态,它就会显示进度状态。

搜索输入框

使用 freeSolo 创建一个带有建议体验的搜索输入框,例如 Google 搜索或 react-autowhatever

用户创建的选项

如果您打算将 freeSolo 模式用于类似组合框的体验(select 元素的增强版本),我们建议设置

  • selectOnFocus 以帮助用户清除选定的值。
  • clearOnBlur 以帮助用户输入新值。
  • handleHomeEndKeys 以使用 HomeEnd 键在弹出框内移动焦点。
  • 最后一个选项,例如:添加“您的搜索”。

当用户想要添加新值时,您还可以显示一个对话框。

验证

要显示无效状态,请在 FormControl 上设置 error 属性。

哎呀!出错了。
Enter 键开始编辑

多选

默认情况下,自动完成组件使用 Chip 组件来渲染用户选择的选项。

当自动完成组件获得焦点时,用户可以按退格键从列表中删除最后选择的选项。

Inception
Enter 键开始编辑

选定选项外观

使用 renderTag 属性自定义外观。

Inception

限制要显示的选定选项数量

您可以使用 limitTags 属性来限制在未聚焦时显示的选项数量。

Inception
Forrest Gump
+1
Enter 键开始编辑

尺寸

自动完成组件开箱即用地提供三种尺寸:smmd(默认)和 lg。尺寸会传递到内部组件,包括 InputChipList

Inception
Inception
Inception

尺寸也可以在 FormControl 上控制。

Inception
这是一个小型描述。
Enter 键开始编辑

自定义过滤器

该组件公开了一个工厂,用于创建可以提供给 filterOptions 属性的过滤器方法。您可以使用它来更改默认的选项过滤行为。

import { createFilterOptions } from '@mui/material/Autocomplete';

参数

  1. configobject [可选])
  • config.ignoreAccentsbool [可选]):默认为 true。删除变音符号。
  • config.ignoreCasebool [可选]):默认为 true。将所有内容转换为小写。
  • config.limitnumber [可选]):默认为 null。限制要显示的建议选项的数量。例如,如果 config.limit100,则仅显示前 100 个匹配的选项。如果有很多选项匹配且未设置虚拟化,则此功能很有用。
  • config.matchFrom'any' | 'start' [可选]):默认为 'any'
  • config.stringifyfunc [可选]):控制如何将选项转换为字符串,以便可以将其与输入文本片段进行匹配。
  • config.trimbool [可选]):默认为 false。删除尾随空格。

返回值

filterOptions:返回的过滤器方法可以直接提供给 Autocomplete 组件的 filterOptions 属性,或者提供给 hook 的同名参数。

在以下演示中,选项需要以查询前缀开头

const filterOptions = createFilterOptions({
  matchFrom: 'start',
  stringify: (option) => option.title,
});

<Autocomplete filterOptions={filterOptions} />;

高级过滤器

对于更丰富的过滤机制,例如模糊匹配,建议查看 match-sorter。例如

import { matchSorter } from 'match-sorter';

const filterOptions = (options, { inputValue }) => matchSorter(options, inputValue);

<Autocomplete filterOptions={filterOptions} />;

CSS 变量 Playground

Autocomplete 组件重用 Input 组件的 CSS 变量,为您提供一致的自定义体验。

The Godfather
Pulp Fiction
<Autocomplete />

CSS 变量


常见示例

提示

以下演示展示了如何使用 filterOptions 属性向 Autocomplete 添加提示功能

高亮选项

以下演示依赖于 autosuggest-highlight,这是一个小巧 (1 kB) 的实用程序,用于在 autosuggest 和 autocomplete 组件中高亮文本。

GitHub 的选择器

要重现 GitHub 的标签选择器,Autocomplete 在 MUI Base Popper 中渲染。要从自动完成组件中移除弹出行为,请将 listbox 插槽替换为 AutocompleteListbox 组件。

  • help wanted
  • type: bug

虚拟化

在 10,000 个随机生成的选项中搜索。列表通过 react-window 实现虚拟化。

Enter 键开始编辑

事件

如果您想阻止默认的按键处理程序行为,可以将事件的 defaultMuiPrevented 属性设置为 true

<Autocomplete
  onKeyDown={(event) => {
    if (event.key === 'Enter') {
      // Prevent's default 'Enter' behavior.
      event.defaultMuiPrevented = true;
      // your handler code
    }
  }}
/>

限制

autocomplete/autofill

默认情况下,该组件使用 autoComplete="off" 属性禁用输入框的 autocomplete 功能(记住用户在之前的会话中为给定字段输入的内容)。Google Chrome 目前不支持此属性设置 (Issue 41239842)。一种可能的解决方法是删除 id 以使组件生成一个随机的 id。

除了记住过去输入的值之外,浏览器还可能提出 autofill 建议(保存的登录名、地址或付款详细信息)。如果您想避免 autofill,可以尝试以下操作

  • 命名输入框时不要泄露浏览器可以使用的任何信息。例如,使用 id="field1" 而不是 id="country"。如果您将 id 留空,组件将使用随机 id。

  • 设置 autoComplete="new-password"(某些浏览器会为此属性设置的输入框建议使用强密码)

    <Autocomplete
      slotProps={{
        input: {
          autoComplete: 'new-password',
        },
      }}
    />
    

阅读 MDN 上的指南 了解更多详情。

iOS VoiceOver

iOS Safari 上的 VoiceOver 对 aria-owns 属性的支持不是很好。您可以使用 disablePortal 属性来解决此问题。

<Autocomplete
  slotProps={{
    listbox: {
      disablePortal: true,
    },
  }}
/>

可访问性

(WAI-ARIA: https://www.w3.org/WAI/ARIA/apg/patterns/combobox/)

我们鼓励为文本框使用标签。该组件实现了 WAI-ARIA 创作实践。

API

请参阅下面的文档,以获得此处提及的组件的所有属性和类的完整参考。