React Jsx 将检查状态设置为 false(重置按钮)

React Jsx set checked state to false (reset button)

在这里,我正在尝试重置此列表中选定的单选按钮, 但是它不起作用,因为 我之前将输入检查从 {checked} 更改为 {user.checked}。参考下方UserListElement.tsx

因此,我尝试了以下两种方法

  1. 在useEffect()中,设置user.userId = false

useEffect(() => {
    user.checked = false;
  }, [isReset, user]);

→ 无变化。

  1. setCheckedtrue 当 addedUserIds 包括 user.userId

 if (addedUserIds.includes(`${user.userId}`)) {
    setChecked(true);
  }

→ 未处理的运行时错误 错误:重新渲染太多。 React 限制渲染次数以防止无限循环。

关于如何使这个工作有任何建议吗?

UserListElement.tsx

export const UserListElement = ({
  user,
  handleOnMemberClicked,
  isReset,
}: {
  user: UserEntity;
  handleOnMemberClicked: (checked: boolean, userId: string | null) => void;
  isReset: boolean;
}) => {
  const [checked, setChecked] = useState(user.checked);
  const addedUserIds = addedUserList.map((item) => item.userId) || [];

  const handleOnChange = (e: ChangeEvent<HTMLInputElement>) => {
    const checkedState = e.target.checked;
    setChecked(checkedState); //not called
    user.checked = checkedState;
    handleOnMemberClicked(checkedState, user.userId);
  };
  useEffect(() => {
    setChecked(false);
  }, [isReset, user]);

  if (addedUserIds.includes(`${user.userId}`)) {
    user.checked = true;
    // setChecked(true) cause runtime error (infinite loop)
  }

  return (
    <li>
      <label className={style.checkboxLabel}>
        <input
          type="checkbox"
          className={style.checkboxCircle}
          checked={user.checked}
          // checked={checked}
          onChange={(e) => handleOnChange(e)}
        />
        <span>{user.name}</span>
      </label>
    </li>
  );
};

UserList.tsx

export const UserList = (props: {
    showsUserList: boolean;handleClose: () => void;corporationId: string;currentUserId: string;samePerson: boolean;twj: string;
  }) => {
    const [isReset, setReset] = useState(false);
    .......
    const resetAll = () => {
      setReset(!isReset);
      setCount((addedUserList.length = 0));
      setAddedUserList([]);
      setUserName('');
    };
    ......
    return ( <
      > < div > xxxxx <
      ul className = {
        `option-module-list no-list option-module-list-member ${style.personListMember}`
      } > {searchedUserList.map((user, i) => ( 
      <UserListElement user = { user }
          handleOnMemberClicked = { handleOnMemberClicked }
          isReset = { isReset }
          key = {i} />
        )) }
        </ul> 
      /div>
    <a className="is-secondary reservation-popup-filter-reset" onClick={resetAll}>
      .....
    }

使用添加UserList.tsx

export class UserDetail {
  constructor(public userId: string | null, public name: string | null) {}
}

export let addedUserList: UserDetail[] = [];
export let setAddedUserList: Dispatch<SetStateAction<UserDetail[]>>;

export const useAddUserList = (idList: UserDetail[]) => {
  [addedUserList, setAddedUserList] = useState(idList);
};

进一步说明:

默认视图

搜索选项(显示过滤列表)

我使用 user.checked 因为当只使用选中时,选中状态不会从筛选列表视图继续到完整视图(例如,当我删除搜索词或关闭弹出窗口时)。

在您的 UserListElement.tsx 中,您在渲染中设置状态,这会触发再次渲染组件,然后再次设置状态,再次触发重新渲染并继续循环。尝试将你的条件放在 useEffect 调用中,你也会改变道具,所以不要设置 user.checked = true。而是从定义它的父组件调用 setter。

useEffect(() => {
  setChecked(false);
  if (addedUserIds.includes(user.userId)) {
    setChecked(true);
  }
}, [user]);

这个问题的真正答案是状态应该保存在你的组件中。复选框的状态应保存在 UsersList 中并作为道具传入。

export const UserListElement = ({
  user,
  handleOnMemberClicked,
  isChecked
}: {
  user: UserEntity;
  handleOnMemberClicked: (checked: boolean, userId: string | null) => void;
  isChecked: boolean;
}) => {
   // no complicated logic in here, just render the checkbox according to the `isChecked` prop, and call the handler when clicked
}

在用户列表中


return searchedUserList.map(user => (
   <UserListElement 
       user={user} 
       key={user.id} 
       isChecked={addedUserIds.includes(user.id)} <-- THIS LINE
       handleOnMemberClicked={handleOnMemberClicked}
    />
)

你可以看到你几乎已经弄明白了,因为你在 child:

  if (addedUserIds.includes(`${user.userId}`)) {
    user.checked = true;
    // setChecked(true) cause runtime error (infinite loop)
  }

这表明 checkdd 值完全取决于 parent 中保存的状态,这意味着 child 中实际上没有任何状态。

此外,在 React 中,从不 改变事物(props 或状态),例如 - user.checked = true - 这肯定会给你留下一个会让你付出代价的错误很多时间。

希望这能说明一些问题