如何在D3.js中制作多个组网络节点的凸包

问题描述 投票:4回答:2

我正在尝试制作网络图,其中节点按属性分组,并在节点中通过位置(力布局)和凸包将它们按组捆绑在一起。类似于this,但没有单击以折叠/展开。对于初学者来说,该模型/代码过于复杂,无法对其进行剖析和学习。

我的问题可以简单地说:是否有网络+分组功能的示例代码,其中包括多个组中节点的可能性?

有时,一个组中只有一个节点,而基本凸包的工作时间少于三个。上面的示例对此有一个修复程序(我不理解),this one也可以创建不可见的节点,并且可能更容易。

组可以嵌套在多层中。 This tutorial提供使用d3.nest()获取层次结构中的数据所需的所有信息。但这可能不是层次结构,可能是一个节点位于多个组中,并且需要位于正确的外壳和位置中。某些节点将不在任何组中,但仍将在网络中连接。

我知道力布局中的力是相加的,因此使组和链接都以简单的方式影响节点位置应该不是问题,但是我没有看到这样的简单示例。我的方法是将网络连接添加到多焦点示例,然后查看是否可以正常工作。

作为奖励,节点不应重叠,对于分层元素,应将基本层节点放在一个圆周围,以使多个组中的节点位于这些组之间like this。我之所以提及这些是因为对这些功能的渴望可能会为上述需求提供最佳解决方案。

我将根据this JSFiddle进行构建;随着我自己在代码上取得进展,我将继续更新和完善这个问题。我希望能找到比我想要的要折叠的代码更近的任何代码指针,关于D3的局限性/问题的警告(例如需要针对1-2个节点的凸包的变通方法)以及提供其中之一的代码的指针。以易于理解和模块化的方式实现最终目标。真的,我们会提供任何帮助。

d3.js data-visualization convex-hull
2个回答
4
投票

尽管这个问题在过去一周没有引起太多关注,但希望答案对某些人有用。我设法对linkDistance使用了一个函数,该函数开始时会很大,然后会缩小,具体取决于(1)源和目标是否在同一集合中,以及(2)该集合的级别,即组或子组或子分组。

基本解决方案的思想来自only example I could find of this capability。我使用的实际linkDistance函数有点简化,但是可以很好地完成工作,并且可以轻松地将其用于许多其他人的许多其他用途(我希望如此)。根据您的分组,您可能希望通过类似我在这里使用的功能来调整链接的其他功能(如颜色)。

force
    .nodes(graph.nodes)
    .links(graph.links)
    .linkDistance(function(thisLink) { 
        var myLength = 100, theSource = thisLink.source, theTarget = thisLink.target;
        groupNodes.forEach(function(groupList) { 
            if (groupList.indexOf(theSource) >= 0 && groupList.indexOf(theTarget) >= 0) {
                myLength = myLength * 0.7;
            }
        });
        subgroupNodes.forEach(function(groupList) { 
            if (groupList.indexOf(theSource) >= 0 && groupList.indexOf(theTarget) >= 0) {
                myLength = myLength * 0.4;
            }
        });
        subsubgroupNodes.forEach(function(groupList) { 
            if (groupList.indexOf(theSource) >= 0 && groupList.indexOf(theTarget) >= 0) {
                myLength = myLength * 0.2;
            }
        });
        return myLength; } )
    .linkStrength(function(l, i) { return 1; } )
    .gravity(0.05)   
    .charge(-600)   
    .friction(0.5)  
    .start();

此解决方案的一个版本以及其他改进,可以在this JSFiddle处找到。

尽管这通过根据组成员关系调整链接力来回答我的问题,但它并没有按照我最初的意图组合链接+组的力。我仍然希望能够赋予子分组“欲望”,使其彼此远离而进入角落,但受到连接它们的边缘的约束(而不是迫使它们处于圆形布局)。

请注意,我的组在外部定义为列表列表。如果您的情况下的组成员身份是节点属性,则可以使用d3.nest()函数生成必须使用map函数创建的节点组,但是如果组重叠,我认为这将不起作用成员。


0
投票

这是一个很好的例子,包括cytoscape.js在内的许多网络库都不允许这种复杂的分组。我有2个问题:

© www.soinside.com 2019 - 2024. All rights reserved.