为 Matplotlib 箭头添加角度注释

PythonPythonBeginner
立即练习

This tutorial is from open-source community. Access the source code

💡 本教程由 AI 辅助翻译自英文原版。如需查看原文,您可以 切换至英文原版

简介

在本实验中,你将学习如何在Matplotlib中为使用FancyArrowPatch创建的括号箭头样式添加角度注释。角度注释对于在绘图中指示角度的方向和大小很有用。在本实验结束时,你将能够创建带有角度注释的括号箭头样式,并根据你的特定需求对其进行自定义。

虚拟机提示

虚拟机启动完成后,点击左上角切换到“笔记本”标签,以访问Jupyter Notebook进行练习。

有时,你可能需要等待几秒钟让Jupyter Notebook完成加载。由于Jupyter Notebook的限制,操作验证无法自动化。

如果你在学习过程中遇到问题,请随时向Labby提问。课程结束后提供反馈,我们将立即为你解决问题。

导入必要的库并设置绘图

首先,我们需要导入必要的库并设置绘图。我们将使用matplotlib.pyplotnumpy。我们还将创建一个图形和一个轴对象来在上面绘制数据。

import matplotlib.pyplot as plt
import numpy as np

from matplotlib.patches import FancyArrowPatch

fig, ax = plt.subplots()
ax.set(xlim=(0, 6), ylim=(-1, 5))
ax.set_title("Orientation of the bracket arrows relative to angleA and angleB")

定义一个函数来获取旋转后的垂直线的端点

我们将定义一个函数,该函数以原点坐标、线长和角度(以度为单位)作为输入,并返回旋转指定角度后的垂直线端点的xy坐标。

def get_point_of_rotated_vertical(origin, line_length, degrees):
    """Return xy coordinates of the vertical line end rotated by degrees."""
    rad = np.deg2rad(-degrees)
    return [origin[0] + line_length * np.sin(rad),
            origin[1] + line_length * np.cos(rad)]

创建带有角度注释的括号箭头

我们将使用FancyArrowPatch创建三种带有角度注释的括号箭头样式。每个括号箭头的angleAangleB将具有不同的角度值。我们还将添加垂直线来指示角度注释的位置。

style = ']-['
for i, angle in enumerate([-40, 0, 60]):
    y = 2*i
    arrow_centers = ((1, y), (5, y))
    vlines = ((1, y + 0.5), (5, y + 0.5))
    anglesAB = (angle, -angle)
    bracketstyle = f"{style}, angleA={anglesAB[0]}, angleB={anglesAB[1]}"
    bracket = FancyArrowPatch(*arrow_centers, arrowstyle=bracketstyle,
                              mutation_scale=42)
    ax.add_patch(bracket)
    ax.text(3, y + 0.05, bracketstyle, ha="center", va="bottom", fontsize=14)
    ax.vlines([line[0] for line in vlines], [y, y], [line[1] for line in vlines],
              linestyles="--", color="C0")

添加角度注释箭头和文本

我们将为每种括号箭头样式添加角度注释箭头和文本。首先,我们将获取绘制的补丁在angleAangleB处的顶部坐标。然后,我们将定义注释箭头的连接方向。最后,我们将向绘图中添加箭头和注释文本。

    ## Get the top coordinates for the drawn patches at A and B
    patch_tops = [get_point_of_rotated_vertical(center, 0.5, angle)
                  for center, angle in zip(arrow_centers, anglesAB)]
    ## Define the connection directions for the annotation arrows
    connection_dirs = (1, -1) if angle > 0 else (-1, 1)
    ## Add arrows and annotation text
    arrowstyle = "Simple, tail_width=0.5, head_width=4, head_length=8"
    for vline, dir, patch_top, angle in zip(vlines, connection_dirs,
                                            patch_tops, anglesAB):
        kw = dict(connectionstyle=f"arc3,rad={dir * 0.5}",
                  arrowstyle=arrowstyle, color="C0")
        ax.add_patch(FancyArrowPatch(vline, patch_top, **kw))
        ax.text(vline[0] - dir * 0.15, y + 0.7, f'{angle}°', ha="center",
                va="center")

显示绘图

我们将使用plt.show()来显示绘图。

plt.show()

总结

在本实验中,你学习了如何在Matplotlib中为使用FancyArrowPatch创建的括号箭头样式添加角度注释。你还学习了如何根据自己的特定需求自定义括号箭头样式。通过遵循提供的分步说明和示例代码,你现在应该能够在自己的Matplotlib绘图中创建带有角度注释的括号箭头样式。