我的表即使调用useeffect也不会重新呈现

ccrfmcuu  于 2021-09-13  发布在  Java
关注(0)|答案(2)|浏览(313)

directoryList 是由文件详细信息组成的列表状态( filename,keyword,status,checked )在我的一个组件中。
我的全部代码都添加到codesandbox中
说明:
添加一个文本文件并单击上载
在关键字输入框中输入一个单词,并在默认行中给出数值
单击“申请已选中”
单击“查找”按钮

directoryList = [{
filename:'',
checked: false,
keyword:'',
linestoBecopied:0,
status:""
}]

我有一个按钮叫 Find . 如果我点击按钮, findButtonHandler 将被调用。
在这里,我试图更改状态,值正在更改,但ui不会重新呈现。如果我点击 Find 按钮两次,ui将重新呈现。

useEffect(() => {
     console.log("useEffect called")
    }, [directoryList]);

      const fileChangeHandler = (e) =>
      {
        const files=[]
        console.log("hiiiii")
        for(let i = 0; i< e.target.files.length; i++) {
          files.push(e.target.files[i])
      }
      console.log(files)
      setFiles(files)
    }
      const uploadClickHandler=()=>
      {
        var list=[];
        for(let i=0;i<files.length;i++ )
        {
        var file = files[i];
        console.log(file.name)
        var obj = {
          filename: file.name,
          status:"",
          checked:true,
            keyWord:"",
            linesToBeCopied:""
        }
        list.push(obj);
      }
        setDirectoryList([...list])
        console.log(directoryList)

      }

      const applyForCheckHandler = () =>
      {
        const list = [...directoryList]
        list.map((dir,i) => (
          dir.keyWord=keyWord,
          dir.linesToBeCopied=defLines
        ))
        console.log(list)
        setDirectoryList([...list])

      }

      const checkBoxHandler = (filename) =>
      {
        console.log("hi")
        var list1 = directoryList
        list1.map((dir,i) => {
          if(i==filename)
          {
          if(dir.checked==true)
           dir.checked=false
          else
           dir.checked=true 
        }})
        console.log(list1)
        setDirectoryList(list1)
      }

    **const findButtonHandler = () =>
      {
        let list1 = [...directoryList]
        for(let i=0;i<files.length;i++)
        {
          let status=""
          var file = files[i]
          list1.map((dir,i) => {
            if(dir.filename==file.name && dir.checked)
            {

               var reader = new FileReader();
               reader.onload = function(progressEvent){
               var lines = this.result.split('\n');
               for(var line = 0; line < lines.length; line++){
                 console.log(lines[line])
                 if(lines[line].includes(dir.keyWord)){
                   console.log("text found")
                   status = "Found"
                   dir.status = "Found"
                   break;
                   }
                 else{
                  status="Not Found"
                  dir.status = status
                 }
              }
            };  reader.readAsText(file);
            }

        })}
        console.log(list1)

      }**

      const saveHandler = () => {
        const formData = new FormData()
        var str = JSON.stringify(directoryList)
        var list = JSON.parse(str);
        var list1 = directoryList
        var filename=""
        console.log(directoryList.length)
        list1.map((dir,i) => {
          console.log(dir.filename+dir.checked)
          if(dir.checked==true && dir.status=='Found')
            filename = filename + dir.filename + ","
        })
        var lines = defLines
        var keyword = keyWord

        for(let i = 0; i< files.length; i++) {
          formData.append('file', files[i])
        }
        formData.append("lines",lines)
        formData.append("keyword",keyword)
        formData.append("filenames",filename)

        console.log(lines)
        console.log(keyWord)
        console.log(filename)

        axios.post('http://localhost:8080/save', formData,{
          headers:{
          "Content-Type":"multipart/form-data"
         } })
        .then((response) => {
          fileDownload(response.data,'output.txt')

        }).catch(error =>
          {
            console.log(error.message)
          });
      }
    return (
        <>
        <HeadingComponent>
            <h3>Data Quest</h3>
        </HeadingComponent>
        <FirstComponent>
          <SearchDirComponent>
        Select Filesto Upload : <input type='file' name="files" id="inputfile" onChange={fileChangeHandler} multiple></input>
        </SearchDirComponent>
       <FirstButtonComponent>
       <Button
        variant="contained"
        color="default"
        startIcon={<CloudUploadIcon />}
        onClick={uploadClickHandler}
      >
        Upload
      </Button>
      <Button
        variant="contained"
        color="secondary"
        startIcon={<DeleteIcon />}
      >
        Close
      </Button>
       </FirstButtonComponent>

        </FirstComponent>
        <SecondComponent>
          <SecondInputComponent>
        <div> Search Keyword :  <OutlinedInput type='text' name="directoryname"  value={keyWord} onChange={(e)=> setkeyword(e.target.value)}style = {{width: 100,height:30,paddingLeft:10}}></OutlinedInput></div>
        <div style={{paddingLeft:150}}> Default Lines <OutlinedInput type='text' name="defaultLines" value={defLines} onChange={(e)=> setDefLines(e.target.value)} style = {{width: 100,height:30,paddingLeft:10}}></OutlinedInput></div>
        <div style={{paddingLeft:150}}>
        <Button
        variant="contained"
        color="primary"
        onClick={applyForCheckHandler}
        style={{fontSize:14 ,width:220,height:27}}
      >
        Apply for checked
      </Button>
        </div>
        </SecondInputComponent>
        <ApplyButtonComponent>

        </ApplyButtonComponent>
        </SecondComponent>
       <TableComponent> 
    <TableContainer component={Paper}>
      <Table aria-label="simple table">
        <TableHead>
          <TableRow>
            <TableCell align="center">&nbsp;&nbsp;Select Files</TableCell>
            <TableCell align="center">File Name</TableCell>
            <TableCell align="center">Search Keyword&nbsp;(g)</TableCell>
            <TableCell align="center">Lines to be copied&nbsp;(g)</TableCell>
            <TableCell align="center">Status&nbsp;(g)</TableCell>
          </TableRow>
        </TableHead>
        <TableBody>
          {directoryList.length>0 && directoryList.map((directory,i) => (
            <TableRow key={directory.filename}>
              <TableCell component="th" scope="row" align="center">
               <Checkbox checked={directory.checked} onClick={() => checkBoxHandler(i)} name={directory.filename}></Checkbox></TableCell>
              <TableCell align="center">{directory.filename}</TableCell>
              <TableCell align="center">{directory.keyWord}</TableCell>
              <TableCell align="center">{directory.linesToBeCopied}</TableCell>
              <TableCell align="center">{directory.status}</TableCell>
            </TableRow>
          ))}
        </TableBody>
      </Table>
    </TableContainer>
        </TableComponent>
        { directoryList.length >0 &&

        <ButtonComponent>
          <div>
        <Button variant="contained" color="secondary" onClick={findButtonHandler}>
        Find
        </Button></div>
        <div>
        <Button variant="contained" color="primary" style={{paddingLeft: 20}} onClick={saveHandler}>
        Save
       </Button></div>
        </ButtonComponent>} 
        </>
    )
}
xmq68pz9

xmq68pz91#

我看到这里是因为你所在的州 directoryList 从未更改,因此组件不会触发重新渲染。
请试着改变你的想法 directoryList 这样说:

const findButtonHandler = () => {
    let list1 = [...directoryList]

     for(let i=0;i<files.length;i++)
     {
       let status=""
       var file = files[i]
       list1.map((dir,i) => {
         if(dir.filename==file.name && dir.checked) {

            var reader = new FileReader();
            reader.onload = function(progressEvent){
            var lines = this.result.split('\n');
            for(var line = 0; line < lines.length; line++){
              console.log(lines[line])
              if(lines[line].includes(dir.keyWord)){
                console.log("text found")
                status = "Found"
                dir.status = "Found"
                break;
                }
              else{
               status="Not Found"
               dir.status = status
              }
           }
         };  reader.readAsText(file);
         }

         list1[i].status = status // add this line
     }
     )}
     console.log(list1)
    setDirectoryList([...list1]);
  };

并查看结果,请记住,仅当状态发生更改时才会触发重新渲染。如果使用了hook,则必须声明要在数组中触发调用useffect的状态。

useEffect(() => {
     console.log("useEffect called")
    }, [directoryList]);
``` `useEffect` 当值为时将调用或重新渲染组件 `directoryList` 改变
y4ekin9u

y4ekin9u2#

reader.onload()是异步函数,因此状态值不会在第一次更改

相关问题