Текстовое поле (Text Field)
Текстовые поля позволяют пользователям вводить и редактировать текст.
Текстовые поля позволяют пользователям вводить текст в пользовательский интерфейс. Они обычно появляются в формах и диалогах.
Базовое текстовое поле
Компонент-обертка TextField представляет собой полноценный элемент формы, включающий подпись (label), поле для ввода (input) и подсказку (help text). Он имеет три варианта: с обводкой (по умолчанию), заполненный и стандартный.
Примечание: Стандартный вариант TextField больше не документирован в Material Design guidelines (вот почему), но MUI будет продолжать его поддерживать.
Свойства формы
Поддерживаются стандартные атрибуты формы, например, required, disabled, type, и т.д., а также helperText, который используется для предоставления контекста о вводимом поле, например, о том, как оно будет использоваться.
Валидация
Свойство error включает или выключает состояние ошибки. Затем можно воспользоваться свойством helperText, чтобы сообщить пользователю об ошибке.
Многострочное поле
Свойство multiline преобразует текстовое поле в элемент TextareaAutosize. Если не установлено свойство rows, высота текстового поля динамически соответствует его содержимому (с помощью TextareaAutosize). Чтобы ограничить высоту, можно использовать свойства minRows и maxRows.
Выбор
Свойство select заставляет текстовое поле использовать компонент Select внутри поля.
Дополнительные элементы
Основной способ добавить дополнительный элемент в поле - с помощью InputAdornment. Его можно использовать для добавления префикса (до ввода), суффикса (после ввода) или действия. Например, можно добавить кнопку-иконку, которая будет прятать или показывать пароль.
kg
kg
Weight
$
kg
kg
Weight
$
kg
kg
Weight
$
Вариант filled можно сделать еще меньше, если переместить подпись.
Отступ
Свойство margin можно использовать для изменения вертикального отступа текстового поля. Использование none (по умолчанию) не добавляет отступ к FormControl, тогда как dense и normal добавляют.
Полная ширина
Свойство fullWidth можно использовать для того, чтобы поле занимало всю ширину своего контейнера.
Неуправляемые (uncontrolled) и управляемые (controlled) поля
Компонент может быть управляемым или неуправляемым.
Компоненты
TextField состоит из меньших компонентов (FormControl, Input, FilledInput, InputLabel, OutlinedInput, и FormHelperText), которые вы можете использовать напрямую, если хотите кастомизировать текстовое поле.
Вы также могли заметить, что в компоненте TextField отсутствуют некоторые нативные свойства элемента "input" из HTML. Это специально. Компонент сам заботится о наиболее часто используемых свойствах. Затем пользователю остается использовать базовый компонент, показанный в следующем демонстрационном примере. Тем не менее, вы можете использовать inputProps (и свойства InputProps, InputLabelProps), если вы хотите избежать шаблонного кода.
Кастомизация
Вот несколько примеров кастомизации компонента. Подробнее об этом можно узнать на странице документации по переопределениям.
Кастомизация не ограничивается CSS. Вы можете использовать композицию для создания особенных компонентов и придания вашему приложению уникальности. Ниже приведен пример с использованием компонента InputBase, вдохновленный Google Maps.
🎨 Если вы ищете вдохновение, вы можете посмотреть примеры кастомизации MUI Treasury.
useFormControl
Для расширенной кастомизации используется хук useFormControl(). Этот хук возвращает значение контекста родительского компонента FormControl.
API
import { useFormControl } from '@mui/material/FormControl';
Возвращает
value (object):
value.adornedStart(bool): Указывает, имеет ли дочерний компонентInputилиSelectдополнительный элемент (adornment) в начале.value.setAdornedStart(func): Функция-сеттер для состоянияadornedStart.value.color(string): Используется цвет темы, наследуется от свойстваFormControlcolor.value.disabled(bool): Указывает, отображается ли компонент в отключенном состоянии, наследуется от свойстваFormControldisabled.value.error(bool): Указывает, отображается ли компонент в состоянии ошибки, наследуется от свойстваFormControlerrorvalue.filled(bool): Указывает, заполнено ли полеvalue.focused(bool): Указывает, отображается ли компонент и его дочерние элементы в сфокусированном состоянииvalue.fullWidth(bool): Указывает, занимает ли компонент всю ширину своего контейнера, наследуется от свойстваFormControlfullWidthvalue.hiddenLabel(bool): Указывает, скрывается ли подпись, наследуется от свойстваFormControlhiddenLabelvalue.required(bool): Указывает, указывает ли метка на то, что поле является обязательным, наследуется от свойстваFormControlrequiredvalue.size(string): Размер компонента, наследуется от свойстваFormControlsizevalue.variant(string): Вариант используется компонентомFormControlи его дочерними компонентами, наследуется от свойстваFormControlvariantvalue.onBlur(func): Функция будет вызываться, когда поле дефокусируетсяvalue.onFocus(func): Функция будет вызываться, когда поле фокусируетсяvalue.onEmpty(func): Функция будет вызываться, когда поле становится пустымvalue.onFilled(func): Функция будет вызываться, когда поле становится заполненным
Пример
Ограничения
Сжатие подписи (shrink)
Состояние подписи "shrink" не всегда корректно. Предполагается, что подпись сжимается, как только в поле что-то введено. В некоторых обстоятельствах мы не можем определить состояние "сжатия" (ввод числа, ввод даты, ввод Stripe). Вы можете заметить перекрытие.

Чтобы обойти эту проблему, можно принудительно установить состояние "сжатия" для подписи.
<TextField InputLabelProps={{ shrink: true }} />
или
<InputLabel shrink>Количество</InputLabel>
Плавающая подпись
Плавающая подпись позиционирована абсолютно. Она не повлияет на макет (layout) страницы. Для правильного отображения убедитесь, что поле больше, чем подпись.
type="number"
Поля с type="number" имеют потенциальные проблемы с удобством использования:
- Разрешают некоторые нецифровые символы ('e', '+', '-', '.') и без предупреждения выкидывают другие
- Использование прокрутки для увеличения/уменьшения числа может привести к случайным и труднозаметным изменениям
и многое другое - смотрите эту статью команды GOV.UK Design System для более подробного объяснения.
Для валидации чисел одной из возможных альтернатив является использование стандартного типа ввода type="text" с атрибутом pattern, например:
<TextField inputProps={{ inputMode: 'numeric', pattern: '[0-9]*' }} />
В будущем, возможно, мы предоставим компонент для ввода чисел.
Подсказка
Добавление подсказки влияет на высоту текстового поля. Если два текстовых поля расположены рядом, одно с подсказкой, а другое без него, они будут иметь разную высоту. Например:
Please enter your name
Это можно исправить, передав пробел в свойстве helperText:
Please enter your name
Интеграция со сторонними библиотеками
Для форматирования поля можно использовать сторонние библиотеки. Вы должны предоставить свою реализацию элемента <input> со свойством inputComponent.
В следующем демонстрационном примере используются библиотеки react-imask и react-number-format. Та же концепция может быть применена к, например, react-stripe-element.
Компонент ввода должен предоставлять "ref" со значением, которое реализует следующий интерфейс:
interface InputElement {
focus(): void;
value?: string;
}
const MyInputComponent = React.forwardRef((props, ref) => {
const { component: Component, ...other } = props;
// имплементируем интерфейс `InputElement`
React.useImperativeHandle(ref, () => ({
focus: () => {
// здесь надо фокусировать использованный сторонний компонент
},
// прячем значение, например react-stripe-elements
}));
// `Component` будет вашим `SomeThirdPartyComponent`
return <Component {...other} />;
});
// использование
<TextField
InputProps={{
inputComponent: MyInputComponent,
inputProps: {
component: SomeThirdPartyComponent,
},
}}
/>;
Доступность
Чтобы текстовое поле было доступным (accessible), поле должно быть связано с подписью и подсказкой. Соответствующие узлы DOM должны иметь такую структуру:
<div class="form-control">
<label for="my-input">Электронная почта</label>
<input id="my-input" aria-describedby="my-helper-text" />
<span id="my-helper-text">Мы никому не дадим вашу почту.</span>
</div>
- Если вы используете компонент
TextField, вам просто нужно предоставить уникальныйid, если вы не используетеTextFieldтолько на стороне клиента (client-side). Пока UI не будет гидрирован (hydrated),TextFieldбез явногоidне будет иметь связанных подписей. - Если вы составляете компонент из базовых компонентов:
<FormControl>
<InputLabel htmlFor="my-input">Электронная почта</InputLabel>
<Input id="my-input" aria-describedby="my-helper-text" />
<FormHelperText id="my-helper-text">Мы никому не дадим вашу почту.</FormHelperText>
</FormControl>
Дополнительно
Для более сложных случаев использования вы можете воспользоваться:
- react-hook-form: React-хук для валидации формы.
- react-hook-form-mui: объединение MUI и react-hook-form.
- formik-material-ui: Использование MUI с formik.
- redux-form-material-ui: Использование MUI с Redux Form.
- mui-rff: Использование MUI с React Final Form.
- @ui-schema/ds-material Использование Material UI с UI Schema. Совместимо с JSON Schema.
- @data-driven-forms/mui-component-mapper: Использование Material UI с Data Driven Forms.
Unstyled
The component also comes with an unstyled version. It's ideal for doing heavy customizations and minimizing bundle size.