Я столкнулся с некоторым сбивающим с толку поведением при использовании компонента таблицы React и ant-дизайна

#javascript #reactjs #frontend

Вопрос:

По какой-то причине я должен сделать опору «столбцы» компонента таблицы с сохранением состояния. Затем происходит какая-то неожиданная ошибка.

Следующий код работает нормально, как и ожидалось:

 import React, { useEffect, useState } from 'react' import { Modal, Table, Input, Button, Divider, Checkbox } from 'antd'  function App() {  const [searchWord, setSearchWord] = useState('')  const [items, setItems] = useState([])  const [loading, setLoading] = useState(false)  const [selectedItems, setSelectedItems] = useState([])   const initColumns = [  {  title: lt;a onClick={selectAll}gt;Select Alllt;/agt;,  render: (_, record) =gt; (  lt;Checkbox  checked={selectedItems.includes(record)}  onChange={(e) =gt; select(e.target.checked, record)}  /gt;  ),  key: 'select',  width: 100,  align: 'center',  },  {  title: 'ID',  dataIndex: 'objectID',  key: 'objectID',  },  {  title: 'author',  dataIndex: 'author',  key: 'author',  },  {  title: 'title',  dataIndex: 'title',  key: 'title',  },  {  title: 'comments',  dataIndex: 'num_comments',  key: 'comments',  },  ]   function selectAll() {  if (selectedItems.length === items.length) {  setSelectedItems([])  } else {  setSelectedItems([...items])  }  }   function select(checked, item) {  if (checked) {  setSelectedItems((selectedItems) =gt; selectedItems.concat([item]))  } else {  setSelectedItems((selectedItems) =gt;  selectedItems.filter((val) =gt; val !== item)  )  }  }   async function search() {  setLoading(true)  const { hits } = await fetch(  `https://hn.algolia.com/api/v1/search?query=${searchWord}`  ).then((response) =gt; response.json())   setItems(hits.slice(0, 8))  setLoading(false)  }   return (  lt;gt;  lt;Modal width={850} visible={true} closable={false} footer={[]}gt;  lt;Input.Search  value={searchWord}  onChange={(e) =gt; {  setSearchWord(e.target.value)  }}  onSearch={search}  /gt;  lt;Divider /gt;  lt;Table  loading={loading}  rowKey={(record) =gt; record.objectID}  columns={initColumns}  dataSource={items}  /gt;  lt;Divider /gt;  lt;Button onClick={() =gt; console.log(selectedItems)}gt;  Print Selected Items  lt;/Buttongt;  lt;/Modalgt;  lt;/gt;  ) }  export default App  

Функциональность этого фрагмента кода заключается в том, чтобы «отобразить некоторые строки таблицы и выбрать/выбрать все эти строки». введите описание изображения здесь

Until now it works fine. However for some reason I have to make the columns of Table stateful. So I change the code:

 ...  // On some situation I have to change the columns, for example change the columns' width.  const [columns, setColumns] = useState(initColumns)   ...   lt;Table  loading={loading}  rowKey={(record) =gt; record.objectID}  columns={columns}  dataSource={items}  /gt;  ...  

When the change is done, the select/selectAll just won’t work! I thought it might be related to React’s update/refresh logic.

So I tried to add these:

 // On some situation I have to change the columns, for example change the columns' width.  const [columns, setColumns] = useState(initColumns)    useEffect(() =gt; {  setColumns(initColumns)  }, [items, selectedItems])   

The code works fine now. But I still don’t understand why! I’ve been using React for like 2 months now, and I can’t find out this problem on my own.

I would really appreciate if some one can tell me what happened exactly here!

(I tried to make myself clear as I can, but my English is not good enough. If you don’t fully understand my writing, please leave me a message!)