useState 钩子的意外行为 [英] Unexpected behaviour of useState hook
问题描述
我正在尝试一个图像映射器库,发现了一个意外的行为.处理函数 handleInc
的行为取决于它是由 +
按钮触发还是通过单击图像中的突出显示区域(需要移动鼠标以突出显示区域出现).
当使用 +
按钮时,行为与预期一致,但单击图像中突出显示的区域时,状态变量 count
似乎没有超出 1代码>.
相同函数 handleInc
表现不同的原因是什么.
这是代码(
I was trying out an image mapper library and found an unexpected behaviour. The handler function handleInc
behaves differently depending on whether its triggered by the +
button or via clicking on the highlighted area in the image (need to move mouse around in order for highlighted area to appear).
When using +
button the behaviour is as expected but when clicking highlighted area in the image, the state variable count
doesn't seems to go beyound 1
.
What's the reason for behind the same function handleInc
behaving differently.
Here is the code (sandbox for the code below)
import { useState } from "react";
import "./styles.css";
// https://github.com/img-mapper/react-img-mapper
import ImageMapper from "react-img-mapper";
const URL =
"https://helpx.adobe.com/content/dam/help/en/stock/how-to/visual-reverse-image-search/jcr_content/main-pars/image/visual-reverse-image-search-v2_intro.jpg";
export default function App() {
const [count, setCount] = useState(0);
const handleInc = () => {
// this print expected value when + button is clicked
// but print 0 if highlighted area is clicked
console.log(count);
setCount(count + 1);
};
const handleDec = () => {
console.log(count);
setCount(count - 1);
};
return (
<div className="App">
<h1>Hello CodeSandbox</h1>
<h2>Start editing to see some magic happen!</h2>
<button onClick={handleInc}>+</button>
{count}
<button onClick={handleDec}>-</button>
<ImageMapper
src={URL}
map={{
name: "asdf",
areas: [
{
id: 0,
active: true,
title: "BB(1-4)",
shape: "poly",
name: "BB(1-4)",
fillColor: "#eab54d4d",
strokeColor: "black",
coords: [
260,
142,
77,
196,
184,
530,
840,
529,
928,
283,
894,
26,
389,
53,
343,
31,
321,
90
]
}
]
}}
stayMultiHighlighted
onClick={handleInc}
/>
</div>
);
}
Seems that the ImageMapper
component is memoizing the callbacks, in other words, it has closed over the initial count
state value and never updates from that point.
If you use a functional state update then clicking the highlighted area seems to work as I think you expect it to. Functional state updates work by updating from the previous state versus the state from render cycle the callback was enqueued in.
const handleInc = () => {
setCount(count => count + 1);
};
const handleDec = () => {
setCount(count => count - 1);
};
Demo
这篇关于useState 钩子的意外行为的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!