可以在matplotlib中使用自定义箭头或多边形作为标记绘制位置和方向吗?
我有一系列飞机的x,y坐标和对应的航向角。我可以绘制出它们飞行的路径,现在我想用一个特殊的标记来标记路径上的某个特定位置,同时显示飞机在那个位置时的航向。
我使用了matplotlib.pyplot中的一个没有底座的箭头来实现这个目的,但在绘制多架飞机时,由于需要定义箭头的头部和尾部位置,导致箭头的长度不一致。我还尝试了一个自定义的三边形符号,使用了元组(numsides, style, angle),以及楔形和大V形符号,但效果都不是很好。
在这个链接中,Saullo Castro展示了一个不错的自定义箭头(arrow1),我在想是否可以用它,或者将其转换成一种方式,简单地在给定的x,y位置绘制,并让它的方向由航向角来定义。
我可以用以下代码绘制这个自定义箭头。有没有什么想法可以让它旋转以反映航向呢?
a1 = np.array([[0,0],[0,1],[-1,2],[3,0],[-1,-2],[0,-1],[0,0]], dtype=float)
polB = patches.Polygon(a1, closed=True, facecolor='grey')
ax.add_patch(polB)
提前谢谢你。
1 个回答
我把多边形简化了一下,发现可以用mpl.transforms.Affine2D().rotate_deg_around()来实现旋转:
a2 = np.array([[newX,newY+2],[newX+1,newY-1],[newX,newY],[newX-1,newY-1],[newX,newY+2]], dtype=float)
polB = patches.Polygon(a2, closed=True, facecolor='gold')
t2 = mpl.transforms.Affine2D().rotate_deg_around(newX,newY,heading) + newax.transData
polB.set_transform(t2)
newax.add_patch(polB)
我最开始尝试把多边形叠加在一个由x和y坐标绘制的线条上。但是,x轴和y轴的比例不一样(我也不想让它们一样),所以当我旋转多边形时,它看起来就变得扭曲和拉伸了。为了解决这个问题,我先添加了一个新的坐标轴,使得x和y的比例相等:
newax = fig.add_axes(ax.get_position(), frameon=False)
newax.set_xlim(-20,20)
newax.set_ylim(-20,20)
这样我就可以随意旋转,而不会出现扭曲的问题。不过,我还需要想办法把这两个坐标轴连接起来,这样我才能在新的坐标轴上绘制多边形,并且这个位置是参考原始坐标轴的。我想到的办法是使用变换,把原始坐标轴上的数据坐标转换为显示坐标,然后再把它们反转回数据坐标,不过这次是在新的坐标轴上的数据坐标:
inTrans = ax.transData.transform((x, y))
inv = newax.transData.inverted()
newTrans = inv.transform((inTrans[0], inTrans[1]))
newX = newTrans[0]
newY = newTrans[1]
这样做感觉有点像是一个复杂的鲁布·戈德堡机器,但最终达到了我想要的效果。
最后,我决定不喜欢这种方法,选择了更简单的做法,使用一个花哨的箭头代替多边形。生活就是这样……