#reactjs #typescript #material-ui #react-hooks #react-state-management
#reactjs #typescript #материал-пользовательский интерфейс #реагирующие перехваты #управление состоянием реакции
Вопрос:
Я хотел бы, чтобы начальное состояние для даты TextField
было установлено до undefined
тех пор, пока пользователь не выберет дату, а затем позволит пользователю легко сбросить дату обратно undefined
.
В следующем коде кнопка сброса правильно сбросит parameters.count
состояние 0
, но оно не будет сброшено parameters.date
undefined
. undefined
Обрабатывается ли это специально в этом случае?
import React, { useState } from "react";
import { Button, TextField } from "@material-ui/core";
import "./App.css";
export type Parameters = {
count: number;
date?: string;
};
const initialParameters: Parameters = {
count: 0,
date: undefined,
};
export const App: React.FC = () => {
const [parameters, setParameters] = useState<Parameters>(initialParameters);
const handleCountChange = (event: React.ChangeEvent<HTMLInputElement>) => {
setParameters({
...parameters,
count: Number(event.target.value),
});
};
const handleDateChange = (event: React.ChangeEvent<HTMLInputElement>) => {
setParameters({
...parameters,
date: event.target.value,
});
};
const resetState = () => {
setParameters(initialParameters);
};
return (
<div className="App">
<TextField
type="number"
label="Count"
value={parameters.count}
onChange={handleCountChange}
/>
<TextField
label="Date"
type="date"
value={parameters.date}
onChange={handleDateChange}
InputLabelProps={{
shrink: true,
}}
/>
<Button onClick={resetState}>Reset</Button>
</div>
);
};
Комментарии:
1. Я думаю, что это скорее случай, когда компонент текстового поля не принимает значение undefined в качестве значения (вместо этого должна быть пустая строка). На самом деле удивительно, что он не показывает предупреждение о том, что ввод меняется с контролируемого на неконтролируемый, но, возможно, Material UI не показывает эти предупреждения.
2. Фактически,
<input type="date">
спецификация предполагает , что если значение является недопустимой строкой даты, значение устанавливается в пустую строку: » Если значение элемента не является допустимой строкой даты, то вместо этого установите его в пустую строку». Попробуйте установить начальное значениеdate
to''
вместоundefined
.3. Настройка
date: "",
сработала, спасибо. Я предполагаю, что я пытался использовать систему типов для кодирования «отсутствующего» значения, но это похоже наTextField
желания""
.
Ответ №1:
Решение, основанное на комментарии @cbr, заключается в принудительном undefined
""
использовании перед переходом к TextField
.
import React, { useState } from "react";
import { Button, TextField } from "@material-ui/core";
import "./App.css";
export type Parameters = {
count: number;
date?: string;
};
const initialParameters: Parameters = {
count: 0,
date: undefined,
};
export const App: React.FC = () => {
const [parameters, setParameters] = useState<Parameters>(initialParameters);
const handleCountChange = (event: React.ChangeEvent<HTMLInputElement>) => {
setParameters({
...parameters,
count: Number(event.target.value),
});
};
const handleDateChange = (event: React.ChangeEvent<HTMLInputElement>) => {
setParameters({
...parameters,
date: event.target.value,
});
};
const resetState = () => {
setParameters(initialParameters);
};
// TextField expects blank string to represent no value.
const dateDisplay = parameters.date ? parameters.date : "";
return (
<div className="App">
<TextField
type="number"
label="Count"
value={parameters.count}
onChange={handleCountChange}
/>
<TextField
label="Date"
type="date"
value={dateDisplay}
onChange={handleDateChange}
InputLabelProps={{
shrink: true,
}}
/>
<Button onClick={resetState}>Reset</Button>
</div>
);
};