useState() 훅을 사용하여 리액트 상태를 갱신하려면 어떻게 해야 합니까?
요소인 '하다'가 요.<BasicForm>
검증과 모든 형식을 합니다.state
모두 있습니다.onChange
,onSubmit
) , , 、 를 、 등 、 , 、 등 , , 。children
BasicForm
를 참조해 주세요를 참조해 주세요.
그것은 의도한 대로 작동한다.문제는 리액트 훅을 사용하도록 변환하고 있기 때문에 클래스일 때 했던 다음 동작을 재현하려고 할 때 의구심이 든다는 것입니다.
class BasicForm extends React.Component {
...other code...
touchAllInputsValidateAndSubmit() {
// CREATE DEEP COPY OF THE STATE'S INPUTS OBJECT
let inputs = {};
for (let inputName in this.state.inputs) {
inputs = Object.assign(inputs, {[inputName]:{...this.state.inputs[inputName]}});
}
// TOUCH ALL INPUTS
for (let inputName in inputs) {
inputs[inputName].touched = true;
}
// UPDATE STATE AND CALL VALIDATION
this.setState({
inputs
}, () => this.validateAllFields()); // <---- SECOND CALLBACK ARGUMENT
}
... more code ...
}
가 [버튼을 하면 [Submit]버튼을 클릭하면BasicForm
을 '터치 '터치'하고 '터치'를 불러야 합니다.validateAllFields()
검증 오류는 입력이 터치된 경우에만 표시되기 때문입니다. 않은 so용 so면면면면면면면면면면면면면면면면면면면면면 so so so so soBasicForm
'를 하고 나서 '터치'를 돼요.validateAllFields()
★★★★★★ 。
클래스를는 두 합니다.setState()
위의 코드와 같이 기능합니다. ★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★.validateAllField()
는 상태 업데이트(모든 필드에 해당하는 상태 업데이트) 후에만 호출되었습니다.
, 에서 두 콜백 useState()
, 다다음음음 , , , , , , , , 。
const [inputs, setInputs] = useState({});
... some other code ...
setInputs(auxInputs, () => console.log('Inputs updated!'));
경고: useState() 및 useReducer() 후크로부터의 상태 갱신은 두 번째 콜백 인수를 지원하지 않습니다.렌더링 후 부작용을 실행하려면 useEffect()를 사용하여 컴포넌트 본문에 선언합니다.
위의는 이 에러 에서 이 합니다.useEffect()
좀요. 로는 '아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아. 왜냐하면 제가 알기로는useEffect()
는 상태 갱신이 아니라 렌더 실행에 기반합니다.츠키다 리액트는 수 있기 에 언제 리액트 할지를 할 수 것 .그래서 언제가 될지 완전히 제어할 수 없는 것 같습니다.useEffect()
와 를 됩니다.setState()
두 번째 콜백 인수
지금까지 알아낸 것은 (작동하고 있는 것 같다.
function BasicForm(props) {
const [inputs, setInputs] = useState({});
const [submitted, setSubmitted] = useState(false);
... other code ...
function touchAllInputsValidateAndSubmit() {
const shouldSubmit = true;
// CREATE DEEP COPY OF THE STATE'S INPUTS OBJECT
let auxInputs = {};
for (let inputName in inputs) {
auxInputs = Object.assign(auxInputs, {[inputName]:{...inputs[inputName]}});
}
// TOUCH ALL INPUTS
for (let inputName in auxInputs) {
auxInputs[inputName].touched = true;
}
// UPDATE STATE
setInputs(auxInputs);
setSubmitted(true);
}
// EFFECT HOOK TO CALL VALIDATE ALL WHEN SUBMITTED = 'TRUE'
useEffect(() => {
if (submitted) {
validateAllFields();
}
setSubmitted(false);
});
... some more code ...
}
를 사용하고 있습니다.useEffect()
으로 validateAllFields()
그리고 그 useEffect()
필요한 모든 렌더링에 대해 실행되며 언제 호출해야 하는지 알 수 있습니다.validateAllFields()
제가 게 '이렇게입니다.submitted
하면 그 state variable이 할 때 알 수 .
이게 좋은 해결책인가요?그 밖에 생각할 수 있는 솔루션은 무엇입니까?기분이 정말 이상해요.
상상해 보세요validateAllFields()
는, 어떠한 조건에서도 2 회 호출할 수 없는 함수입니다.다음 렌더링 시 어떻게 알 수 있습니까?submitted
상태는 이미 100% 확실합니까?
다음 렌더링 전에 대기 중인 모든 상태 업데이트를 React에서 수행할 수 있습니까?이게 보장되나요?
최근에 이와 같은 일이 있었습니다(여기서 질문합니다). 당신이 생각해낸 것은 적절한 접근법인 것 같습니다.
arg를 추가할 수 있습니다.useEffect()
원하는 기능을 수행할 수 있습니다.
예.
useEffect(() => { ... }, [submitted])
변화를 주시하다submitted
.
콜백을 사용하도록 후크를 변경하는 방법도 있습니다.예를 들어 다음과 같습니다.
import React, { useState, useCallback } from 'react';
const useStateful = initial => {
const [value, setValue] = useState(initial);
return {
value,
setValue
};
};
const useSetState = initialValue => {
const { value, setValue } = useStateful(initialValue);
return {
setState: useCallback(v => {
return setValue(oldValue => ({
...oldValue,
...(typeof v === 'function' ? v(oldValue) : v)
}));
}, []),
state: value
};
};
이렇게 하면 '고전적'의 행동을 모방할 수 있습니다.setState()
.
이 문제를 해결하려고 합니다.useEffect()
하지만 제 문제는 잘 해결되지 않았어요.효과는 있었지만, 그런 간단한 작업에는 조금 복잡하다는 것을 알게 되었습니다.또, 기능이 몇번이나 실행되고 있는지, 상태가 바뀐 후에 실행되고 있는지에 대해서도 확신이 서지 않았습니다.
의 useEffect()
이펙트 훅에 대한 몇 가지 사용 사례를 언급했는데, 그 중 어느 것도 제가 하려던 용도가 아닙니다.
나는 그것을 없앴다.useEffect()
.setState((prevState) => {...})
이 기능을 사용하면 현재 상태를 확인할 수 있습니다.따라서 코드 시퀀스는 다음과 같습니다.
// ==========================================================================
// FUNCTION TO HANDLE ON SUBMIT
// ==========================================================================
function onSubmit(event){
event.preventDefault();
touchAllInputsValidateAndSubmit();
return;
}
// ==========================================================================
// FUNCTION TO TOUCH ALL INPUTS WHEN BEGIN SUBMITING
// ==========================================================================
function touchAllInputsValidateAndSubmit() {
let auxInputs = {};
const shouldSubmit = true;
setInputs((prevState) => {
// CREATE DEEP COPY OF THE STATE'S INPUTS OBJECT
for (let inputName in prevState) {
auxInputs = Object.assign(auxInputs, {[inputName]:{...prevState[inputName]}});
}
// TOUCH ALL INPUTS
for (let inputName in auxInputs) {
auxInputs[inputName].touched = true;
}
return({
...auxInputs
});
});
validateAllFields(shouldSubmit);
}
// ==========================================================================
// FUNCTION TO VALIDATE ALL INPUT FIELDS
// ==========================================================================
function validateAllFields(shouldSubmit = false) {
// CREATE DEEP COPY OF THE STATE'S INPUTS OBJECT
let auxInputs = {};
setInputs((prevState) => {
// CREATE DEEP COPY OF THE STATE'S INPUTS OBJECT
for (let inputName in prevState) {
auxInputs =
Object.assign(auxInputs, {[inputName]:{...prevState[inputName]}});
}
// ... all the validation code goes here
return auxInputs; // RETURNS THE UPDATED STATE
}); // END OF SETINPUTS
if (shouldSubmit) {
checkValidationAndSubmit();
}
}
에서 를 참조해 주세요.validationAllFields()
그 setInputs( (prevState) => {...})
저는 의 제 최신 인 그, of, 최, 최, 최, and, and, and, and, and, and, and, and, and, and, and, and, and, and, and, and, and, and, and, and, and, and, and, and, myinputs
이 에 합니다).touchAllInputsValidateAndSubmit()
저는 지금 이 에 있기 입니다.setInputs()
기능적
// ==========================================================================
// FUNCTION TO CHECK VALIDATION BEFORE CALLING SUBMITACTION
// ==========================================================================
function checkValidationAndSubmit() {
let valid = true;
// THIS IS JUST TO MAKE SURE IT GETS THE MOST RECENT STATE VERSION
setInputs((prevState) => {
for (let inputName in prevState) {
if (inputs[inputName].valid === false) {
valid = false;
}
}
if (valid) {
props.submitAction(prevState);
}
return prevState;
});
}
을 그대로 하고 있는 것을 해 주세요.setState()
이 기능하고 .checkValidationAndSubmit()
또한 제출하기 전에 현재 검증된 상태를 확인할 필요가 있습니다.
이것은 지금까지 문제없이 동작하고 있습니다.
언급URL : https://stackoverflow.com/questions/55344925/how-to-make-sure-a-react-state-using-usestate-hook-has-been-updated
'programing' 카테고리의 다른 글
왜 모든 렌더에서 useEffect의 정리 기능이 호출됩니까? (0) | 2023.04.05 |
---|---|
셸 스크립트를 사용하여 mongo 명령을 실행하는 방법은 무엇입니까? (0) | 2023.04.05 |
'상세정보' 유형에 속성이 없습니다.HTMLDivElement' (HTMLDivElement) (Resact 16 탑재) (0) | 2023.04.05 |
WordPress "on-the-fly"에서 언어를 전환하는 방법 (0) | 2023.04.05 |
WordPress 및 Ajax - 쇼트코드 콘텐츠 새로고침 (0) | 2023.04.05 |