使用D3 v5和React重新渲染后保留缩放

时间:2019-11-22 16:40:36

标签: javascript reactjs d3.js

我正在构建一个包含“力布局”树的应用程序,该树应该在用户每次单击节点时重新渲染(这是不可商议的)。 我已经实现了缩放,并且可以按预期工作。

对于树的第一次运行,我正在手动计算其坐标并重新缩放比例,以使所有内容都可见而无需缩小。 第一次渲染后,我将在每次缩放事件后保存树的坐标,并在重建树时将其重新应用。一切正常,缩放比例长为1。 如果不同,坐标会变得混乱,并且我无法将树保持在与重新渲染之前相同的位置。

我如何能够保持与以前完全相同的转换/缩放?

我观察到的一件事是坐标似乎乘以比例尺,因此位置发生了错误的变化。

代码如下:

// Adds the zoom event listener and saves the last coordinates / scale
const zoom = d3.zoom().on('zoom', () => {
  const newTransform = d3.event.transform;

  SVGGroup.attr('transform', newTransform);

  setPreviousTransform(newTransform);
});


// Runs after every render to apply either the initial position/scale calculated by me or the existing one
let transform = null;
  if (previousTransform) {
    transform = d3.zoomIdentity
      .scale(previousTransform.k)
      .translate(previousTransform.x, previousTransform.y);
  } else {
    transform = d3.zoomIdentity.scale(ratio).translate(x, y);
  }

1 个答案:

答案 0 :(得分:1)

坐标将乘以当前缩放比例,因此,如果缩放比例较低,则结果将略有偏离;如果缩放比例较高,则结果将与天文学相距甚远。将这些值除以缩放比例可以消除问题。

const transform = previousTransform
  ? d3.zoomIdentity
      .scale(previousTransform.k)
      .translate(
        previousTransform.x / previousTransform.k,
        previousTransform.y / previousTransform.k
      )
  : d3.zoomIdentity.translate(x, y);