【发布时间】:2020-10-21 10:41:34
【问题描述】:
目前我的功能组件在收到新道具时没有更新。我想澄清我的心智模型,在查看 react 网站上的 cheat sheet 之后,如果新的道具保存在状态下,它应该更新组件吗?
考虑以下代码:
const defaultStart = dayjs().startOf("month").format("YYYY-MM-DD");
const defaultEnd = dayjs().endOf("month").format("YYYY-MM-DD");
function IncidentList({
incidentsList,
requestIncidents,
selectedLoc,
selectedLoc,
startDate = defaultStart,
endDate = defaultEnd,
}) {
const [selectedEndDate, handleEndDateChange] = useState(endDate);
const [selectedStartDate, handleStartDateChange] = useState(startDate);
useEffect(() => {
┊ const payload = {
┊ ┊ location: selectedLoc,
┊ ┊ start_date: dayjs(selectedStartDate).format("YYYY-MM-DD"),
┊ ┊ end_date: dayjs(selectedEndDate).format("YYYY-MM-DD"),
┊ };
┊ requestIncidents(payload);
}, [requestIncidents, selectedEndDate, selectedStartDate]);
return (
┊ <div className="container sm:p-8 md:p-16">
┊ ┊ <MaterialTable
┊ ┊ ┊ columns={columns}
┊ ┊ ┊ data={incidentsList}
┊ ┊ ┊ title="Incident list"
┊ ┊ ┊ actions={actions}
┊ ┊ ┊ options={{
┊ ┊ ┊ ┊ pageSize: 20,
┊ ┊ ┊ }}
┊ ┊ ┊ components={{
┊ ┊ ┊ ┊ Toolbar: (props) => (
┊ ┊ ┊ ┊ ┊ <div className="p-8">
┊ ┊ ┊ ┊ ┊ ┊ <MTableToolbar {...props} />
┊ ┊ ┊ ┊ ┊ ┊ <div className="ml-8 p-8 border-1 w-1/2">
┊ ┊ ┊ ┊ ┊ ┊ ┊ <div className="flex flex-row">
┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ <p className="text-lg font-semibold">Filter Using:</p>
┊ ┊ ┊ ┊ ┊ ┊ ┊ </div>
┊ ┊ ┊ ┊ ┊ ┊ ┊ <div className="flex flex-row -mx-4">
┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ <div className="px-8">
┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ <DatePicker
┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ format="YYYY-MM-DD"
┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ label="Minimum Date"
┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ inputVariant="outlined"
┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ minDate={new Date("2015-01-01")}
┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ maxDate={dayjs().format()}
┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ value={selectedStartDate}
┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ onChange={handleStartDateChange}
┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ />
┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ </div>
┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ <div className="px-8">
┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ <DatePicker
┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ format="YYYY-MM-DD"
┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ label="Maximum Date"
┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ inputVariant="outlined"
┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ minDate={selectedStartDate}
┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ maxDate={dayjs().format()}
┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ value={selectedEndDate}
┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ onChange={handleEndDateChange}
┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ />
┊ ┊ ┊ ┊ ┊ ┊ ┊ ┊ </div>
┊ ┊ ┊ ┊ ┊ ┊ ┊ </div>
┊ ┊ ┊ ┊ ┊ ┊ </div>
┊ ┊ ┊ ┊ ┊ </div>
┊ ┊ ┊ ┊ ),
┊ ┊ ┊ }} />
const mapStateToProps = (state) => ({
incidentsList: state.incident.incidents,
selectedLoc: state.loc.selectedLoc,
});
IncidentList.propTypes = {
incidentsList: PropTypes.arrayOf(PropTypes.object),
requestIncidents: PropTypes.func,
selectedLoc: PropTypes.number,
endDate: PropTypes.string,
startDate: PropTypes.string,
};
当我更新startDate 和endDate 时,上面的代码没有更新状态。我必须打电话给useEffect 才能同步。我想当我们收到新的道具时,组件应该重新渲染,因此调用useState 将其设置为默认值。
我想知道为什么我必须添加此代码才能使其在我更新道具时期望我的组件更新的地方工作。添加代码:
useEffect(() => {
┊ if (startDate && endDate) {
┊ ┊ handleEndDateChange(endDate);
┊ ┊ handleStartDateChange(startDate);
┊ }
}, [startDate, endDate]);
【问题讨论】:
-
useEffect 将在 [] 中的变量像旧版
componentWillUpdate一样工作时运行。 -
我知道,问题是为什么在我为它提供我用作默认状态的新道具后它不重新渲染@moficodes
标签: javascript reactjs