【问题标题】:React Hook useState value being reset to initial valueReact Hook useState 值被重置为初始值
【发布时间】:2021-08-08 20:55:55
【问题描述】:

使用 React useState hook 设置的值的状态被设置为正确的值,然后重置为 null。下面的关键代码。将 startDate 设置为当前日期和时间的单击事件是 startDate 初始化位置的 3 个组件。当 setStartDate 不起作用时,我创建了一个箭头函数 updateStartDate。两者都有相同的问题,即 startDate 在单击事件之后发生更改(根据顶部组件中的 console.log 见证),但在下一个单击事件之前为空(根据 click 事件中的 console.log)。这不是异步问题,因为我看到在后续点击之前所做的更改。

如果这不起作用,请解释。我可能可以使用 useReducer 进行修复,但如果我可以做些什么来纠正这个问题,我更愿意保留 useState ......如果无法纠正,那么我想至少了解它为什么不起作用,这样我就可以避免这个问题未来。

export const DisplayTicTacToeContainer = (props) => {
 const [startDate, setStartDate]= useState();
 const updateStartDate = (newDate) => {
   setStartDate(newDate);
 }
 useEffect (() => {
   setStartDate(null);
 }, []);

 useEffect(() => {
    console.log( "displayTicTacToeContainer useEffect for change of startDate = ", startDate)
  }, [startDate]);

 return (
      <DisplayTicTacToeMatch  arrayOfMatchingItems ={arrayOfMatchingItems}
        startDate={startDate} 
        setStartDate={setStartDate}
        updateStartDate={updateStartDate}          
      />);
}

//-----------------------------------------------
export const DisplayTicTacToeMatch = (props)  => {
 const   { startDate,
           setStartDate,
           updateStartDate,
           } = props;

 useEffect(() => {
  // Performs some prep and working fine.
 }, []);

 return (
    <TicTacToe
      startDate={startDate} 
      setStartDate={setStartDate}
      updateStartDate={updateStartDate}
    />
  );
}
//-----------------------------------------------
const TicTacToeContainer = (props) => {
 const { startDate,
         setStartDate,
         updateStartDate,
        } = props;

 const [board, setBoard] = useState(<Board 
     updateStartDate={updateStartDate}
     startDate={startDate} 
     setStartDate={setStartDate}/>);

 return (
        <Board/>
    )
}
export default TicTacToeContainer;

我将组件重命名为 BoardComponent 并将状态变量重命名为 boardLayout。我在下面包含了 BoardComponent 的全部返回部分。

由于我仍然遇到这个问题,我同意你的观点,“DisplayTicTacToeContainer 正在安装两次”。关于如何避免这种情况发生的任何想法?

除了无法设置开始日期外,一切正常。

//-----------------------------------------------
const Board = (props) => {
 const { updateStartDate,
         startDate,
         setStartDate,
    } = props;

    return (
        <>
        <Grid container maxwidth="lg" alignItems="center" spacing={1}>
            <Grid item xs={9}>
                <Grid container alignItems="center">
                    <Grid item xs={9}>
                        <Typography variant = "body1">                      
                        First select a square.  Once the "Inquiry" word or phrase appears below, find 
                        the correct response in the column on the right and select that buttton.  A correct
                        response will fill the square previously selected with an "O" or "X".
                        </Typography>
                        <div style={{ width: '100%' }}>
                    <Box
                        display="flex"
                        flexWrap="wrap"
                        p={1}
                        m={1}
                        bgcolor="background.paper"
                        css={{ maxWidth: 900 }}
                    >
                    <Box p={1} bgcolor="grey.300">
                        Inquiry : {inquiry}
                    </Box>
                    </Box>
                    <Box
                        display="flex"
                        flexWrap="wrap"
                        p={1}
                        m={1}
                        bgcolor="background.paper"
                        css={{ maxWidth: 900 }}
                    >
                    <Box p={1} bgcolor="grey.300">
                        Next move by : {currentPlayer}
                    </Box>

                    <Box p={1} bgcolor="grey.300">
                        {showStatus}
                    </Box>
                    </Box>
                    </div>
                    </Grid>

                </Grid>
                        <MyAux>
                            {boardLayout.map((row, rowId) => { 
            const columns = row.map((column, columnId) => (
    
                <Grid key={columnId} item>
                    <ButtonBase > 
                        <Paper
                            onClick={(e) => {
                                clickSquareHandler(e);
                                }}
                            elevation={4}
                            data-coord={rowId + ':' + columnId}
                            id={"Square" + rowId.toString() +  columnId.toString()}
                            className={classes.Paper}>
                            <Icon
                                className={classes.Icon}
                                style={{fontSize: 78}}>
                            </Icon>
                        </Paper>
                    </ButtonBase>
                </Grid>
                ));
                return (
                <Grid
                    key={rowId}
                    className={classes.Grid}
                    container
                    spacing={2}>
                    {columns}

                </Grid>)
           })}
                        </MyAux>
                        </Grid>

        <Grid item xs={3} >
        <Paper className={classes.paper}>
        <Typography variant = "body1">    
            Response Options
        </Typography>
            <ButtonGroup
            orientation="vertical"
            color="secondary"
            aria-label="vertical outlined secondary button group"
        >
            {responseChoices.map((choice) => (
                              
                <Controls.Button
                    key ={choice.value}  
                    text={choice.value}
                    variant="contained"
                    color = "secondary"
                    onClick={() => {
                    chooseChecker(choice);
                    }}
                    className={
                    response && response.value === choice.value ? "selected" : ""
                    }
                    disabled={!!selected[choice.value]}
                    fullWidth = "true"
                    size = "small"
                    />
                ))}
            </ButtonGroup>
            </Paper>
            </Grid>
            </Grid>
                </>
    )
}

BoardContainer.propTypes = {
    won: PropTypes.func,
    size: PropTypes.number
};

export default BoardContainer;

【问题讨论】:

    标签: javascript reactjs react-hooks initialization use-state


    【解决方案1】:

    至少,下面的代码没有多大意义。 请不要将状态值设置为组件。 另外,尝试将状态变量命名为与组件不同的名称,因为它会使您在某些方面感到困惑。

     const [board, setBoard] = useState(<Board 
         updateStartDate={updateStartDate}
         startDate={startDate} 
         setStartDate={setStartDate}/>);
    
     return (
            <Board/>
        )
    

    另一种可能性是DisplayTicTacToeContainer 被安装了两次,但我无法用提供的代码确认。

    【讨论】:

    • 我可能说错了。根据有关重置 useState 变量的另一个 Stack Overflow 问题,我添加了此代码以检查组件是否重新挂载,并且在重置值之前我只找到了一个实例,但之间没有实例。添加代码:useEffect(() => { console.log("Mounted") }, [])
    • 虽然我无法证明该组件安装了两次,但它显示出这样做的一些特征,因为其他几个状态变量有问题。所有问题都通过实施上下文和减速器得到解决。现在工作正常。
    猜你喜欢
    • 1970-01-01
    • 2020-03-08
    • 2021-09-22
    • 2021-10-26
    • 2020-07-21
    • 2020-05-29
    • 2021-12-29
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多