更新项目数组时无法使用 React useState 更新 UI

Trouble updating UI with React useState when updating an array of items

很难用 React 和 useState 更新我的 UI。任何帮助将不胜感激。基本上我想做的只是删除用户添加的项目。

interface RedirectUrls {
 url: string;
}

const [redirectUrls, setRedirectUrls] = useState<RedirectUrls[]>([
 {
  url: ''
 }
])

function deleteRedirectUrl(url): void {
 let tmpUrls = redirectUrls
 tmpUrls = tmpUrls.filter(item => item.url !== url)
 setRedirectUrls(tmpUrls)
}

function handleChange (index, event): void {
 const tmpUrls = [...redirectUrls]
 tmpUrls[index].url = event.target.value
}

{redirectUrls.map((item, index) => {
 return (
  <div key={index}>
   <input type='text' onChange={(event):void => {handleChange(index,event)}}/>
   <div onClick={():void => {deleteRedirectUrl(item.url)}}>remove</div>
  </div>
 )
})}

几点:

  1. 一个组件应该return一个元素。在你的例子中,map returns 是一个元素数组,我不得不使用一个空元素(或 <React.Fragment>
  2. 来包装集合
  3. 不要忘记将 value 属性 设置为 input 元素以使更改反映在元素中。
  4. 作为最佳实践,在处理状态变量时使用 const 而不是 let,将它们视为不可变的,以避免丢失您的更改,尤其是当有许多状态变量导致多次渲染时
  5. 我们应该说明类型,因为文件是打字稿,您没有指定函数参数的类型
  6. 修改完成后应调用 setter
import React, { useState } from 'react';

interface RedirectUrls {
  url: string;
}

const App = () => {
  const [redirectUrls, setRedirectUrls] = useState<RedirectUrls[]>([
    {
      url: 'firstUrl'
    },
    {
      url: 'secondUrl'
    }
  ])
  function deleteRedirectUrl(url: string): void {
    const tmpUrls = redirectUrls.filter(item => item.url !== url)
    setRedirectUrls(tmpUrls)
  }

  function handleChange(index: number, event: React.ChangeEvent<HTMLInputElement>): void {
    const tmpUrls = [...redirectUrls]
    tmpUrls[index].url = event.target.value
    setRedirectUrls(tmpUrls);
  }

  return <>{redirectUrls.map((item, index) => <div key={index}>
    <input type='text' value={item.url} onChange={(event): void => { handleChange(index, event) }} />
    <div onClick={(): void => { deleteRedirectUrl(item.url) }}>remove</div>
  </div>)}</>;
}


export default App;