使用useState到地图中的最大更新深度

时间:2020-06-24 21:21:37

标签: javascript reactjs typescript react-hooks

我有一个组件,我正在使用arraymap创建列表。对于每个li,我都会使用ref来获取getBoundingClientRect().xgetBoundingClientRect().y,然后再将{{1}作为refs与{{ 1}}。

array

目标是然后useState传递经过悬停的ref={(el: any) => { if (!el) return; const position = { x: el.getBoundingClientRect().x, y: el.getBoundingClientRect().y, }; setRefs((prevRefs) => [...prevRefs, position]); }} 的{​​{1}}并用onMouseEnter对象在index中对该项目进行操作。

li

但是,我目前遇到错误refs

此错误是由array

产生的

我使用const onMouseEnter = (e: number) => { console.log(refs[e]); // Do something }; 错误地添加了这些对象吗?另外,如下面的完整代码所示。 Error: Maximum update depth exceeded. This can happen when a component repeatedly calls setState inside componentWillUpdate or componentDidUpdate. React limits the number of nested updates to prevent infinite loops.正在运行,而鼠标没有进入或悬停setRefs((prevRefs) => [...prevRefs, position]);

下面的完整代码。

useState

1 个答案:

答案 0 :(得分:1)

如果您真的依赖于使用ref设置渲染方法中的状态,这很难解决。

考虑将坐标存储在普通变量中

// ...
let coords = [];

return (
    <ul>
      {mainMenu.map((i: any, index: number) => (
        <li
          key={i.id}
          onMouseEnter={() => {onMouseEnter(index)}}
          ref={(el: any) => {
            if (!el) return;
            const position = {
              x: el.getBoundingClientRect().x,
              y: el.getBoundingClientRect().y,
            };
            coords = [...coords, position];
          }}
        >
// ...

如果在状态中存储值绝对至关重要,则需要检查该值是否已经存储:

// ...

setRefs(prevRefs => {
  if ( 
    prevRefs && 
    prevRefs.findIndex( idx => idx.x === position.x && idx.y === position.y ) < 0 
  ) {
    return [...prevRefs, position];
  }
  return prevRefs;

// ...

对于支票,您还可以使用<li key={i.id}>元素上的键所使用的ID