networkx画弯曲的边

柔光的暖阳◎ 2022-09-10 06:11 210阅读 0赞

networkx里面自绘的边都是直的,当多个节点处于同一条直线还有连边的时候就特别难看。如果能否让networkx画弯曲的边,那么这种情况就可以好办的多了。

思路为:

  1. 绘制节点,获取节点的pos坐标。
  2. 在存在边的两个节点之间,使用贝塞尔插值生成两个节点之间曲线的节点坐标。
  3. 使用LineCollection绘制线即可。

下面为整理的代码:

  1. __author__ = 'jmh081701'
  2. import matplotlib.pyplot as plt
  3. import numpy as np
  4. import bezier
  5. from matplotlib.collections import LineCollection
  6. import networkx as nx
  7. import random
  8. G = nx.Graph()
  9. G.add_nodes_from([0,1,2,3])
  10. G.add_edge(0,1,weight=0.1)
  11. G.add_edge(1,2,weight=0.2)
  12. G.add_edge(0,2,weight=0.3)
  13. G.add_edge(1,3,weight=0.4)
  14. graph = G
  15. def curved_line(x0, y0, x1, y1, eps=0.2, pointn=30):
  16. x2 = (x0+x1)/2.0 + 0.1 ** (eps+abs(x0-x1)) * (-1) ** (random.randint(1,4))
  17. y2 = (y0+y1)/2.0 + 0.1 ** (eps+abs(y0-y1)) * (-1) ** (random.randint(1,4))
  18. nodes = np.asfortranarray([
  19. [x0, x2, x1],
  20. [y0, y2, y1]
  21. ])
  22. curve = bezier.Curve(nodes,
  23. degree=2)
  24. s_vals = np.linspace(0.0, 1.0, pointn)
  25. data=curve.evaluate_multi(s_vals)
  26. x=data[0]
  27. y=data[1]
  28. segments =[]
  29. for index in range(0,len(x)):
  30. segments.append([x[index],y[index]])
  31. segments = [segments]
  32. return segments
  33. def curved_graph(_graph, pos = None, eps=0.2, pointn=30):
  34. if pos == None:
  35. pos = nx.spring_layout(graph)
  36. for u,v in graph.edges():
  37. x0, y0 = pos[u]
  38. x1, y1 = pos[v]
  39. segs = curved_line(x0,y0,x1,y1)
  40. lc = LineCollection(segs)
  41. plt.gca().add_collection(lc)
  42. plt.gca().autoscale_view()
  43. if __name__ == '__main__':
  44. #画节点
  45. pos = nx.spring_layout(graph)
  46. nx.draw_networkx_nodes(G,pos, with_label=True)
  47. nx.draw_networkx_edges(G,pos)
  48. plt.show()
  49. #画曲线
  50. nx.draw_networkx_nodes(G,pos, with_label=True)
  51. curved_graph(graph,pos)
  52. plt.show()

直线连边版:
在这里插入图片描述

贝塞尔曲线连边版:
在这里插入图片描述

在这里插入图片描述

发表评论

表情:
评论列表 (有 0 条评论,210人围观)

还没有评论,来说两句吧...

相关阅读

    相关 pymunk怎么创建弯曲实体

    要创建弯曲实体,首先要创建一个多边形,并给它设置相应的顶点。然后,使用pymunk的`Body`对象创建一个物理实体,并将多边形作为形状分配给该实体。 例如: im

    相关 networkx弯曲

    networkx里面自绘的边都是直的,当多个节点处于同一条直线还有连边的时候就特别难看。如果能否让networkx画弯曲的边,那么这种情况就可以好办的多了。 思路为: 1.