繁体   English   中英

如何使用 React useState 根据输入长度禁用按钮?

[英]How to disable button according to input length by using React useState?

我有一个带有输入字段和按钮的简单页面,我想在两个字段长度都小于 3 时禁用按钮。这很简单,但我对钩子感到困惑,因为它会进入无限循环。 这是代码:

function TableFooterPanel(props) {

    const [firstName, setFirstName] = useState('');
    const [lastName, setLastName] = useState('');
    // const [isButtonDisabled, setIsButtonDisabled] = useState(true);

    const addNewCustomer = async (name, surname) => {
        await service.addCustomer(name, surname);
        props.funcParam();
    }

    var isButtonDisabled = false;

    if (firstName <= 3 || lastName <= 3) {
        isButtonDisabled = true;
    }
    else {
        isButtonDisabled = false;
    }

    return (

        <>
            <Card className='buttonFooter'>
                <Form className='buttonFooter'>
                    <input type="text" placeholder="First Name" defaultValue={firstName} onChange={e => setFirstName(e.target.value)}></input>
                    <input type="text" placeholder="Last Name" defaultValue={lastName} onChange={e => setLastName(e.target.value)}></input>
                    <Button disabled={isButtonDisabled} onClick={() => addNewCustomer(firstName, lastName)}>Add</Button>
                </Form>
            </Card>

        </>

    );

}
export default TableFooterPanel;

使用此代码,框仅检查它们是空的还是已填充的。

如果我取消注释 useState 钩子并尝试将其设置为 if-else 条件,那么这次会发生无限循环并且页面会崩溃。

如何在不陷入无限循环的情况下检查输入长度?

尝试:

   if (firstName.length <= 3 || lastName.length <= 3) {
        isButtonDisabled = true;
    }
    else {
        isButtonDisabled = false;
    }

我建议您不要直接在组件主体中编写代码:您不知道该代码将被执行多少次。 更好地使用useEffect挂钩:

function TableFooterPanel(props) {

const [firstName, setFirstName] = useState('');
const [lastName, setLastName] = useState('');
const [isButtonDisabled, setIsButtonDisabled] = useState(true);

const addNewCustomer = async (name, surname) => {
    await service.addCustomer(name, surname);
    props.funcParam();
}

useEffect(() => {
   if (firstName.length <= 3 || lastName.length <= 3) {
       setIsButtonDisabled(true);
   }
   else {
       setIsButtonDisabled(false);
   }
}, [firstName, lastName]);


return (

    <>
        <Card className='buttonFooter'>
            <Form className='buttonFooter'>
                <input type="text" placeholder="First Name" defaultValue={firstName} onChange={e => setFirstName(e.target.value)}></input>
                <input type="text" placeholder="Last Name" defaultValue={lastName} onChange={e => setLastName(e.target.value)}></input>
                <Button disabled={isButtonDisabled} onClick={() => addNewCustomer(firstName, lastName)}>Add</Button>
            </Form>
        </Card>

    </>

);

}
export default TableFooterPanel;

如您所见,我在 deps 列表中使用了一个带有firstNamelastNameuseEffect挂钩:这意味着,每次firstNamelastName发生变化时,都会触发useEffect

不要忘记,要检查字符串长度,您必须使用length属性 =)。

给你 go: Codesandbox 演示

您可以像这样简单地添加内联禁用参数:

            <button
              disabled={firstName.length < 3 || lastName.length < 3}
              onClick={() => addNewCustomer(firstName, lastName)}
            >
              Add
            </button>

小于 3 是< 3 ,而不是<= 3

这里不需要if条件,直接设置isButtonDisabled的值即可:

const isButtonDisabled = firstName.lenght < 3 || lastName.lenght < 3;

或者只是内联:

<Button disabled={firstName.lenght < 3 || lastName.lenght < 3} />
function TableFooterPanel(props) {

    const [firstName, setFirstName] = useState('');
    const [lastName, setLastName] = useState('');

    const addNewCustomer = async (name, surname) => {
        await service.addCustomer(name, surname);
        props.funcParam();
    }

    return (

        <>
            <Card className='buttonFooter'>
                <Form className='buttonFooter'>
                    <input type="text" placeholder="First Name" defaultValue={firstName} onChange={e => setFirstName(e.target.value)}></input>
                    <input type="text" placeholder="Last Name" defaultValue={lastName} onChange={e => setLastName(e.target.value)}></input>
                    <Button disabled={!(firstName.length < 3 || lastName.length < 3)} onClick={() => addNewCustomer(firstName, lastName)}>Add</Button>
                </Form>
            </Card>

        </>

    );

}
export default TableFooterPanel;

您需要将它们放在useEffect ,否则当此页面上的任何内容更改时它将重新运行并将isButtonDisabled变量设置为 state。

const [isButtonDisabled, setIsButtonDisabled] = useState(true)

useEffect(()=>{
   if (firstName.length <= 3 || lastName.length <= 3) {
       setIsButtonDisabled(true);
   } else {
       setIsButtonDisabled(false);
   }    
},[firstName, lastName])

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM