Reputation: 109
When updating a state, react does not re-render the screen. Moreover, the use effect is not called.
When clicking on the "change" button, react does not seem to want to re-render with the new values. Also, the use effect is not called.
const [identity, setIdentity] = useState([{id: 1, name: "Lucas"}, {id: 2, name: "Jean"}]);
const [show, setShow] = useState(false);
useEffect(() => {
console.log("UPDATE");
}, [identity]);
But when another state changes, the screen is updated.
You can try this CodeSandBox: https://codesandbox.io/s/nifty-frog-su3m30?file=/src/App.js
I have a hunch, maybe I'm not using the right method to change the value of my object.
function handleChange(evt) {
const toEdit = identity;
const index = toEdit.findIndex(predicate => predicate.id = 1);
toEdit[index] = {...toEdit[index], name: "Michel"}
console.log({index, toEdit});
setIdentity(toEdit);
}
Upvotes: 1
Views: 48
Reputation: 109
As @DBS and @secan said, I got confused with the state update.
This code works :
function handleChange(evt) {
const toEdit = [...identity]; // this line
const index = toEdit.findIndex(predicate => predicate.id = 1);
toEdit[index] = {...toEdit[index], name: "Michel"}
console.log({index, toEdit});
setIdentity(() => toEdit);
}
When I create my copy, I have to create a new table (with the spread operator for example).
Thanks !
Upvotes: 0
Reputation: 203532
The issue here is state mutation with toEdit[index] = {...toEdit[index], name: "Michel"}
. toEdit
is a reference to the existing state identity
.
function handleChange(evt) {
const toEdit = identity;
const index = toEdit.findIndex(predicate => predicate.id = 1);
toEdit[index] = {...toEdit[index], name: "Michel"}
console.log({index, toEdit});
setIdentity(toEdit);
}
Use a functional state update to access and update from the previous state value. Map the previous state to a new array and create a new object reference for the identity
object you are updating.
function handleChange(evt) {
setIdentity(identity => identity.map(el => el.id === 1 ? {
...el,
name: "Michel"
} : el));
}
Upvotes: 2