relation-graph/sf-relation调用refresh()方法后视口位置和缩放比重置的解决方法

relation-graph/sf-relation调用refresh()方法后视口位置和缩放比重置的解决方法

先直接给解决方法,在sf-relation.min.common.js中搜索<刷新>,然后更改这个方法,修改成如下所示:

let refreshZoomFlag = true
function refresh(reload = true) {
    
    
  if (reload) resetViewSize();
  else {
    
    
    zoom(refreshZoomFlag ? 0.01 : -0.01);
    refreshZoomFlag = !refreshZoomFlag;
  }
  (0,external_commonjs_vue_commonjs2_vue_root_Vue_namespaceObject.nextTick)(() => {
    
    
    graphSettingWrap.graphSetting.layouter.refresh();
    refreshNVAnalysisInfo();
    document.body.addEventListener('mousemove', wow);
  });
}

之后在外部调用refresh方法时,使用refresh(false)就可以在不重置视口位置和缩放比的情况下刷新布局了。

下面是事件始末:

事情的起因是我用Vue3 + sf-relation写了一个树状图谱,在加了动态节点及节点展开/收起方法后发现每次调用refresh()都会导致视口位置和缩放比重置,没办法,功能都快写完了,那就改改源码试试吧。

(注:以下都以sf-relation为例)

找到node_modules里的sf-relation下的sf-relation.min.common.js:

image-20221118164857943

在其中搜索了一下refresh()这个方法,暴露出来的方法长这样:

image-20221118165343305

那我们就要开始找重置布局的问题在哪了。由于作者写了比较详细的方法注释,可以看出问题就在resetViewSize()这个方法:

image-20221118170322618

另外的方法中graphSetingWrap.graphSetting.layouter.refresh()是调用目前布局所对应的refresh方法,由于我用的树状布局,我就也看了下对应SeeksBidirectionalTreeLayouter类的refresh方法,发现只是重新计算node位置并渲染的方法;refreshNVAnalysisInfo()是用于设置重新计算好的canvas位置与大小的方法;

于是为了修改对源代码的影响最小化,采用了下面的方式重写refresh:

image-20221118170811335

按道理说这样已经改好了,但在这之后我再试的时候,在调用refresh后会导致页面lines(links)连接线的位置错误,而且我找了半天也没找到画连接线的函数具体在哪。但在不断修改尝试的过程中我发现在连接线渲染位置错误之后,使用滚轮缩放一遍视图就可以使连接线位置正确,于是用了一个取巧的方法解决了:

image-20221118171121495

也就是每次将页面放大/缩小1%使连线正确渲染;

至此sf-relation关于refresh的问题已经解决了。

猜你喜欢

转载自blog.csdn.net/qq_41575208/article/details/127926446