我正在使用Jung构建一棵树,必须将边箭头反转。也就是说,而不是父母 - >孩子,有孩子 - >家长。
我无法更改树的布局结构,因为我使用相应的方法进行进一步分析 - 我只需要这个功能用于视觉目的。
我在我的Eclipse项目中使用jung库作为依赖项,无法编辑直接提供的文件。我已经尝试扩展BasicEdgeRenderer类(并且还尝试创建此类的修改后的副本)来覆盖drawSimpleEdge()方法并反转顶点,但这会导致无数的错误,我似乎无法修复。
然后我考虑过使边缘无向并在所需的位置手动添加箭头,但到目前为止没有成功!
如何实现这一目标的任何帮助都将受到赞赏!!
编辑:我已经添加了与我的图形显示相关的代码部分 - 树具有Node类型的自定义节点的顶点和String类型的边缘。
Layout<Node, String> newLayout = new TreeLayout<Node, String>((Forest<Node, String>) G);
VisualizationViewer<Node,String> vViewer = new VisualizationViewer<Node,String>(newLayout);
vViewer.getRenderContext().setVertexLabelTransformer(
new Transformer<Node, String>(){
public String transform(Node v){
return v.getLabel();
}
});
vViewer.getRenderer().getVertexLabelRenderer().setPosition(Position.CNTR);
vViewer.getRenderContext().setEdgeShapeTransformer(new EdgeShape.Line<Node,String>());
vViewer.getRenderContext().setVertexFillPaintTransformer(vertexPaint);
vViewer.setBackground(Color.WHITE);
答案 0 :(得分:2)
约书亚的答案很好,但是如果你也不改变第239行:
AffineTransform xf = AffineTransform.getTranslateInstance(x2, y2);
为:
AffineTransform xf = AffineTransform.getTranslateInstance(x1, y1);
你根本看不到任何箭头。
答案 1 :(得分:1)
BasicEdgeRenderer.drawSimpleEdge()
还有另一项修改,你可以做到这一点更加密封。
基本上,代码总是绘制一个指向节点第二个端点的箭头,如果边缘是无向的,它会向另一个端点绘制另一个端点。
你想要的是总是画一个指向第一个节点的箭头,所以你可以改变它(行236-7):
graph.getEndpoints(e).getSecond()
成:
graph.getEndpoints(e).getFirst()
和这(行245-246):
getArrowTransform(rc, edgeShape, destVertexShape)
成:
getReverseArrowTransform(rc, edgeShape, destVertexShape)
(如果您希望修改过的代码也为无向边缘做正确的事情 - 那么您可以更改行264,以便它改为调用getArrowTransform()
,但出于您的目的,可能不在乎。)
你甚至可以创建一个BasicEdgeRenderer的修改版本,它有一个为你做逆转的选项;逻辑很简单。不过,这对你来说可能有点过头了。
Tom的解决方案也运行良好,修改的范围更广泛。
相关问题:Q: How to change arrow position or remove it from an edge ? (JUNG)
答案 2 :(得分:0)
通过执行以下操作,我能够在其中一个树样本程序中获得您想要的效果: 我扩展了BasicEdgeRenderer并覆盖了drawSimpleEdge,如下所示: 首先,在342和344线附近填充然后绘制边缘箭头。 g.fill(箭头)和g.draw(箭头)。 注释掉那些线条,你就不会得到你不想要的箭头。接下来,代码检查这是否是无向图:
if (graph.getEdgeType(e) == EdgeType.UNDIRECTED)
如果是这样,它会绘制反向箭头(你想要的那个)。通过注释测试以查看图形/边缘是否是无向的,它将绘制您想要的箭头 对不起,该课程的代码非常混乱。