如何基于React.js中的多个复选框状态禁用/启用按钮

时间:2020-09-02 18:38:50

标签: javascript reactjs redux

我在页面上有一个组件,可渲染一堆复选框和切换开关。

我在底部还有一个名为confirm的按钮,用于保存更改并请求更新后端。

不过,我想支持一项功能,当用户未对这些复选框或切换按钮进行任何更改时,应禁用confirm按钮。并且当用户切换或检查其中任何一项时,confirm按钮就会启用并可以点击。

所以现在我在做什么

const MyComponent = () => {
  const dispatch = useDispatch();
  // get the current state from the store
  const state = useSelector((state: RootState) => state.settings);

  const [isCheckbox1Checked, setCheckbox1] = useState(false);
  const [isCheckbox2Checked, setCheckbox2] = useState(false);
  const [isCheckbox3Checked, setCheckbox3] = useState(false);
  const [isConfirmBtnEnabled, setConfirmBtn] = useState(false);


  const [updateBtnEnabled, enableUpdateBtn] = useState(false);

  useEffect(() => {
    (async () => {
      // `getSettingsConfig` is a async thunk action
      await dispatch(getSettingsConfig());

      setCheckbox1(state.isCheckbox1Checked);

      setCheckbox2(state.isCheckbox2Checked);

      setCheckbox3(state.isCheckbox3Checked);
    })();
  }, [
    dispatch,

    state.isCheckbox1Checked,

    state.isCheckbox2Checked,

    state.isCheckbox3Checked
    // ..
  ]);

  return (
    <>
      <div className="checkboxes">
        <Checkbox1
          onCheck={() => {
            setCheckbox1(true);
            setConfirmBtn(true);
          }}
        />
        <Checkbox2
          onCheck={() => {
            setCheckbox2(true);
            setConfirmBtn(true);
          }}
        />
        <Checkbox3
          onCheck={() => {
            setCheckbox3(true);
            setConfirmBtn(true);
          }}
        />
      </div>
      <button disabled={!isConfirmBtnEnabled}>Confirm</button>
    </>
  );
};

现在看来工作正常,但需要手动向每个复选框发送setConfirmBtn垃圾邮件,并在此页面上进行切换。我想知道是否有更好的方法。

我还考虑过每次这些状态发生任何变化时,都使用useEffect来调用isConfirmBtnEnabled。但是,由于初始状态是通过调度异步thunk从存储中派生的,因此在页面装入后,这些复选框和切换的状态将始终发生变化,因此这意味着我无法使用其他useEffect来监听这些状态的变化。

1 个答案:

答案 0 :(得分:1)

您可以使用useEffect钩子查看三个复选框,并根据isConfirmBtnEnabled钩子内部更新的useEffect更新按钮状态:

useEffect(()=>{

   setConfirmBtn(isCheckbox1Checked || isCheckbox2Checked || isCheckbox3Checked)

},[isCheckbox1Checked,isCheckbox2Checked,isCheckbox3Checked])

编辑:


const MyComponent = () => {
  const dispatch = useDispatch();
  // get the current state from the store
  const state = useSelector((state: RootState) => state.settings);

  const [checkboxes, setCheckboxes] = useState({c1:false,c2:false,c3:false});
  const [isConfirmBtnEnabled, setConfirmBtn] = useState(false);


  const [updateBtnEnabled, enableUpdateBtn] = useState(false);

  useEffect(() => {
    (async () => {
      // `getSettingsConfig` is a async thunk action
      await dispatch(getSettingsConfig());
  [1,2,3].forEach(i=>{
        setCheckboxes({...checkboxes,[`c${i}`]:state[`isCheckbox${1}Checked`]})
      })
    
    })();
  }, [
    dispatch,

    state
    // ..
  ]);

   useEffect(()=>{
    setConfirmBtn(Object.values(checkboxes).reduce((a,c)=>(a=a || c),false))
   },[checkboxes])
  const _onCheck=(i)=>{
 setCheckboxes({...checkboxes,[`c${i}`]:tur})
   }
  return (
    <>
      <div className="checkboxes">
        <Checkbox1
          onCheck={() => _onCheck(1)}
        />
        <Checkbox2
         onCheck={() => _onCheck(2)}
        />
        <Checkbox3
          onCheck={() => _onCheck(3)}
        />
      </div>
      <button disabled={!isConfirmBtnEnabled}>Confirm</button>
    </>
  );
};