Material ui 自动完成按回车键创建新筹码

Material ui Autocomplete press enter to create new chips

我希望我可以使用 material ui 的自动完成来做这样的事情:wertarbyte

也就是说,插入文本(字符串)时没有您必须 select.

的元素列表

因此不应出现 noOptions 消息,每次在键盘上按下回车键时都会插入文本。

Link: codesandbox

代码:

import React from "react";
import Chip from "@material-ui/core/Chip";
import Autocomplete from "@material-ui/lab/Autocomplete";
import { makeStyles } from "@material-ui/core/styles";
import TextField from "@material-ui/core/TextField";

const useStyles = makeStyles(theme => ({
  root: {
    width: 500,
    "& > * + *": {
      marginTop: theme.spacing(3)
    }
  }
}));

export default function Tags() {
  const classes = useStyles();

  return (
    <div className={classes.root}>
      <Autocomplete
        multiple
        id="tags-outlined"
        options={[]}
        defaultValue={["foo", "bar"]}
        //getOptionLabel={(option) => option}
        //defaultValue={[top100Films[13]]}
        //filterSelectedOptions
        renderInput={params => (
          <TextField
            {...params}
            variant="outlined"
            label="filterSelectedOptions"
            placeholder="Favorites"
          />
        )}
      />
    </div>
  );
}

为此,请勿使用 MUI 中的 Autocomplete 元素。只需使用标准 TextFieldInputProps。您需要做的就是向侦听 'Enter' 的 TextField 添加一个 onKeyDown 侦听器,当函数被触发时,将其添加到 [=13= 中的筹码数组中].它可能看起来像这样:

const [inputValue, setInputValue] = useState('');
const [chips, setChips] = useState([])
const inputChange = ({target: {value}}) => {setInputValue(value)};
const handleKeyDown = ({key}) => {
 if(key === 'Enter') {
  setChips([...chips, inputValue])
 }
};
     <TextField
            fullWidth
            variant="outlined"
            label="Fish and Chips"
            value={inputValue}
            onChange={inputChange}
            multiline
            InputProps={{
              startAdornment: chips.map((item) => (
                <Chip
                  key={item}
                  label={item}
                />
              )),
            }}
          />

此处所写未经测试,但应该可以。我在我的一个应用程序中做过类似的事情。

如果你有简单的元素(不是对象,只是字符串),并且你真的不需要处理状态(你的自动完成不受控制)你可以使用 freeSolo 属性 Autocomplete.

<Autocomplete
    multiple
    freeSolo
    id="tags-outlined"
    options={["foo", "bar"]}
    defaultValue={["foo", "bar"]}
    renderInput={params => (
        <TextField
            {...params}
            variant="outlined"
            label="filterSelectedOptions"
            placeholder="Favorites"
        />
    )}
/>

如果您的元素比较复杂并且您确实需要控制该元素:

  1. 确保自动完成标签是受控的(你设法值)。

  2. 监听 TextField 上的按键事件。

  3. 如果代码是 Enter (e.code === 'Enter') - 获取输入值并将其推送到您拥有的当前值列表中。

  4. 确保您还处理 onChange 来处理元素的删除:

代码如下:

const [autoCompleteValue, setAutoCompleteValue] = useState(["foo", "bar"]);

return (
  
  <Autocomplete
    multiple
    id="tags-outlined"
    options={[]}
    value={autoCompleteValue}
    onChange={(e, newval, reason) => {
      setAutoCompleteValue(newval);
    }}
    renderInput={params => (
      <TextField
        {...params}
        variant="outlined"
        label="filterSelectedOptions"
        placeholder="Favorites"
        onKeyDown={e => {
          if (e.code === 'enter' && e.target.value) {
            setAutoCompleteValue(autoCompleteValue.concat(e.target.value));
          }
        }}
      />
    )}
  />
);

检查两个选项的实时工作示例:https://codesandbox.io/s/mui-autocomplete-create-options-on-enter-gw1jc

对于任何想要在回车键上输入当前最佳匹配(而不是任何自定义文本)的人,您可以使用 autoHighlight 属性。

<Autocomplete
    multiple
    autoHighlight
    id="tags-outlined"
    options={["foo", "bar"]}
    defaultValue={["foo", "bar"]}
    renderInput={params => (
        <TextField
            {...params}
            variant="outlined"
            label="filterSelectedOptions"
            placeholder="Favorites"
        />
    )}
/>