Noter
Cliquez ici pour télécharger l'exemple de code complet
Annotation #
Annotation de texte avec Matplotlib.
from matplotlib import pyplot as plt
Annotation de base #
Les utilisations de la base text()
placeront le texte à une position arbitraire sur les Axes. Un cas d'utilisation courant du texte consiste à annoter certaines caractéristiques du tracé, et la
annotate()
méthode fournit une fonctionnalité d'assistance pour faciliter les annotations. Dans une annotation, il y a deux points à considérer : l'emplacement annoté représenté par l'argument
xy et l'emplacement du texte xytext . Ces deux arguments sont des tuples.(x, y)
Dans cet exemple, les emplacements xy (pointe de flèche) et xytext (emplacement du texte) sont en coordonnées de données. Il existe une variété d'autres systèmes de coordonnées que l'on peut choisir - vous pouvez spécifier le système de coordonnées de xy et xytext avec l'une des chaînes suivantes pour xycoords et textcoords (la valeur par défaut est 'data')
dispute |
système de coordonnées |
---|---|
'points de chiffres' |
points du coin inférieur gauche de la figure |
'chiffre pixels' |
pixels du coin inférieur gauche de la figure |
'fraction de chiffres' |
(0, 0) est en bas à gauche de la figure et (1, 1) est en haut à droite |
'points d'axes' |
points du coin inférieur gauche des axes |
'axes pixels' |
pixels du coin inférieur gauche des axes |
'fraction d'axes' |
(0, 0) est en bas à gauche des axes et (1, 1) est en haut à droite |
'Les données' |
utiliser le système de coordonnées des données des axes |
Par exemple pour placer les coordonnées du texte en coordonnées d'axes fractionnaires, on pourrait faire :
ax.annotate('local max', xy=(3, 1), xycoords='data',
xytext=(0.8, 0.95), textcoords='axes fraction',
arrowprops=dict(facecolor='black', shrink=0.05),
horizontalalignment='right', verticalalignment='top',
)
Pour les systèmes de coordonnées physiques (points ou pixels), l'origine est le coin inférieur gauche de la figure ou des axes.
Facultativement, vous pouvez activer le dessin d'une flèche du texte au point annoté en donnant un dictionnaire des propriétés de la flèche dans l'argument mot-clé facultatif arrowprops .
clé d'accessoires de flèche |
la description |
---|---|
largeur |
la largeur de la flèche en points |
frac |
la fraction de la longueur de la flèche occupée par la tête |
largeur de tête |
la largeur de la base de la tête de flèche en points |
rétrécir |
éloignez la pointe et la base de quelques pour cent du point et du texte annotés |
**kwargs |
n'importe quelle clé pour |
Dans l'exemple ci-dessous, le point xy est en coordonnées natives ( xycoords par défaut est 'data'). Pour un axe polaire, c'est dans l'espace (thêta, rayon). Le texte de cet exemple est placé dans le système de coordonnées des chiffres fractionnaires. matplotlib.text.Text
les arguments de mot-clé comme horizontalalignment , verticalalignment et
fontsize sont passés de annotate
à l'
Text
instance.
Pour en savoir plus sur toutes les choses folles et merveilleuses que vous pouvez faire avec les annotations, y compris les flèches fantaisie, voir Annotations avancées et annotation de tracés .
Ne continuez que si vous avez déjà lu l' annotation de
base text()
et annotate()
!
Annotations avancées #
Annoter avec du texte avec Box #
Commençons par un exemple simple.
text
prend un argument de mot-clé bbox , qui dessine une boîte autour du texte :
t = ax.text(
0, 0, "Direction", ha="center", va="center", rotation=45, size=15,
bbox=dict(boxstyle="rarrow,pad=0.3", fc="cyan", ec="b", lw=2))
L'objet patch associé au texte est accessible par :
bb = t.get_bbox_patch()
La valeur de retour est un FancyBboxPatch
; les propriétés du patch (facecolor, edgewidth, etc.) peuvent être consultées et modifiées comme d'habitude.
FancyBboxPatch.set_boxstyle
définit la forme de la boîte :
bb.set_boxstyle("rarrow", pad=0.6)
Les arguments sont le nom du style de boîte avec ses attributs comme arguments de mots-clés. Actuellement, les styles de boîte suivants sont implémentés.
Classer
Nom
Attrs
Cercle
circle
pad=0.3
DFlèche
darrow
pad=0.3
LA Flèche
larrow
pad=0.3
RFlèche
rarrow
pad=0.3
Tour
round
pad=0.3,rounding_size=Aucun
Tour4
round4
pad=0.3,rounding_size=Aucun
Dent ronde
roundtooth
pad=0.3,tooth_size=Aucun
Dent de scie
sawtooth
pad=0.3,tooth_size=Aucun
Carré
square
pad=0.3
Notez que les arguments d'attribut peuvent être spécifiés dans le nom du style avec une virgule de séparation (cette forme peut être utilisée comme valeur "boxstyle" de l'argument bbox lors de l'initialisation de l'instance de texte)
bb.set_boxstyle("rarrow,pad=0.6")
Annoter avec la flèche #
annotate
dessine une flèche reliant deux points dans un Axes :
ax.annotate("Annotation",
xy=(x1, y1), xycoords='data',
xytext=(x2, y2), textcoords='offset points',
)
Cela annote un point à xy dans la coordonnée donnée ( xycoords ) avec le texte à xytext donné dans textcoords . Souvent, le point annoté est spécifié dans les coordonnées des données et le texte d'annotation dans les points de décalage . Voir annotate
pour les systèmes de coordonnées disponibles.
Une flèche reliant xy à xytext peut éventuellement être dessinée en spécifiant l' argument arrowprops . Pour dessiner uniquement une flèche, utilisez une chaîne vide comme premier argument.
ax.annotate("",
xy=(0.2, 0.2), xycoords='data',
xytext=(0.8, 0.8), textcoords='data',
arrowprops=dict(arrowstyle="->",
connectionstyle="arc3"),
)
La flèche est tracée comme suit :
Un chemin reliant les deux points est créé, comme spécifié par le paramètre connectionstyle .
Le chemin est coupé pour éviter les patchs patchA et patchB , s'ils sont définis.
Le chemin est encore rétréci par rétrécissementA et rétrécissementB (en pixels).
Le chemin est transmuté en patch de flèche, comme spécifié par le paramètre arrowstyle .
La création du chemin de connexion entre deux points est contrôlée par
connectionstyle
clé et les styles suivants sont disponibles.
Nom
Attrs
angle
angleA=90,angleB=0,rad=0.0
angle3
angleA=90,angleB=0
arc
angleA=0,angleB=0,brasA=Aucun,brasB=Aucun,rad=0.0
arc3
rad=0.0
bar
brasA=0.0,brasB=0.0,fraction=0.3,angle=Aucun
Notez que "3" dans angle3
et arc3
est destiné à indiquer que le chemin résultant est un segment de spline quadratique (trois points de contrôle). Comme nous le verrons ci-dessous, certaines options de style de flèche ne peuvent être utilisées que lorsque le chemin de connexion est une spline quadratique.
Le comportement de chaque style de connexion est (limité) démontré dans l'exemple ci-dessous. (Attention : Le comportement du bar
style n'est actuellement pas bien défini, il pourra être modifié dans le futur).
Le chemin de connexion (après découpage et rétrécissement) est ensuite muté en un patch de flèche, selon le arrowstyle
.
Nom
Attrs
-
Aucun
->
head_length=0.4,head_width=0.2
-[
largeurB=1.0,longueurB=0.2,angleB=Aucun
|-|
largeurA=1.0,largeurB=1.0
-|>
head_length=0.4,head_width=0.2
<-
head_length=0.4,head_width=0.2
<->
head_length=0.4,head_width=0.2
<|-
head_length=0.4,head_width=0.2
<|-|>
head_length=0.4,head_width=0.2
fancy
head_length=0.4,head_width=0.4,tail_width=0.4
simple
head_length=0.5,head_width=0.5,tail_width=0.2
wedge
tail_width=0.3,shrink_factor=0.5
Certains styles de flèche ne fonctionnent qu'avec des styles de connexion qui génèrent un segment de spline quadratique. Ce sont fancy
, simple
et wedge
. Pour ces styles de flèche, vous devez utiliser le style de connexion "angle3" ou "arc3".
Si la chaîne d'annotation est donnée, le patchA est défini sur le patch bbox du texte par défaut.
Comme avec text
, une boîte autour du texte peut être dessinée en utilisant l'
argument bbox .
Par défaut, le point de départ est défini au centre de l'étendue du texte. Ceci peut être ajusté avec relpos
la valeur clé. Les valeurs sont normalisées à l'étendue du texte. Par exemple, (0, 0) signifie coin inférieur gauche et (1, 1) signifie coin supérieur droit.
Placer l'artiste aux emplacements Axes ancrés #
Il existe des classes d'artistes qui peuvent être placées à un emplacement ancré dans les Axes. Un exemple courant est la légende. Ce type d'artiste peut être créé en utilisant la OffsetBox
classe. Quelques classes prédéfinies sont disponibles dans matplotlib.offsetbox
et dans
mpl_toolkits.axes_grid1.anchored_artists
.
from matplotlib.offsetbox import AnchoredText
fig, ax = plt.subplots()
at = AnchoredText(
"Figure 1a", prop=dict(size=15), frameon=True, loc='upper left')
at.patch.set_boxstyle("round,pad=0.,rounding_size=0.2")
ax.add_artist(at)
<matplotlib.offsetbox.AnchoredText object at 0x7f2cdd7d9cf0>
Le mot-clé loc a la même signification que dans la commande legend.
Une application simple est lorsque la taille de l'artiste (ou de la collection d'artistes) est connue en taille de pixel au moment de la création. Par exemple, si vous souhaitez dessiner un cercle de taille fixe de 20 pixels x 20 pixels (rayon = 10 pixels), vous pouvez utiliser
AnchoredDrawingArea
. L'instance est créée avec une taille de la zone de dessin (en pixels), et des artistes arbitraires peuvent être ajoutés à la zone de dessin. Notez que l'étendue des artistes ajoutés à la zone de dessin n'est pas liée au placement de la zone de dessin elle-même. Seule la taille initiale compte.
Les artistes ajoutés à la zone de dessin ne doivent pas avoir de jeu de transformation (il sera remplacé) et les dimensions de ces artistes sont interprétées comme une coordonnée de pixels, c'est-à-dire que le rayon des cercles dans l'exemple ci-dessus est de 10 pixels et 5 pixels , respectivement.
from matplotlib.patches import Circle
from mpl_toolkits.axes_grid1.anchored_artists import AnchoredDrawingArea
fig, ax = plt.subplots()
ada = AnchoredDrawingArea(40, 20, 0, 0,
loc='upper right', pad=0., frameon=False)
p1 = Circle((10, 10), 10)
ada.drawing_area.add_artist(p1)
p2 = Circle((30, 10), 5, fc="r")
ada.drawing_area.add_artist(p2)
ax.add_artist(ada)
<mpl_toolkits.axes_grid1.anchored_artists.AnchoredDrawingArea object at 0x7f2cde0e07f0>
Parfois, vous souhaitez que vos artistes soient mis à l'échelle avec les coordonnées des données (ou des coordonnées autres que les pixels du canevas). Vous pouvez utiliser
AnchoredAuxTransformBox
la classe. Ceci est similaire à
AnchoredDrawingArea
sauf que l'étendue de l'artiste est déterminée pendant le temps de dessin en respectant la transformation spécifiée.
L'ellipse dans l'exemple ci-dessous aura une largeur et une hauteur correspondant à 0,1 et 0,4 en coordonnées de données et sera automatiquement mise à l'échelle lorsque les limites de vue des axes changent.
from matplotlib.patches import Ellipse
from mpl_toolkits.axes_grid1.anchored_artists import AnchoredAuxTransformBox
fig, ax = plt.subplots()
box = AnchoredAuxTransformBox(ax.transData, loc='upper left')
el = Ellipse((0, 0), width=0.1, height=0.4, angle=30) # in data coordinates!
box.drawing_area.add_artist(el)
ax.add_artist(box)
<mpl_toolkits.axes_grid1.anchored_artists.AnchoredAuxTransformBox object at 0x7f2cde48dea0>
Comme dans la légende, l'argument bbox_to_anchor peut être défini. En utilisant HPacker et VPacker, vous pouvez avoir un arrangement (?) d'artiste comme dans la légende (en fait, c'est ainsi que la légende est créée).
Notez que contrairement à la légende, le bbox_transform
est défini sur IdentityTransform par défaut.
Systèmes de coordonnées pour les annotations #
Les annotations Matplotlib prennent en charge plusieurs types de coordonnées. Certains sont décrits dans Annotation de base ; des options plus avancées sont
Un
Transform
exemple. Par exemple,ax.annotate("Test", xy=(0.5, 0.5), xycoords=ax.transAxes)
est identique à
ax.annotate("Test", xy=(0.5, 0.5), xycoords="axes fraction")
Cela permet d'annoter un point dans un autre axe :
fig, (ax1, ax2) = plt.subplots(1, 2) ax2.annotate("Test", xy=(0.5, 0.5), xycoords=ax1.transData, xytext=(0.5, 0.5), textcoords=ax2.transData, arrowprops=dict(arrowstyle="->"))
Un
Artist
exemple. La valeur xy (ou xytext ) est interprétée comme une coordonnée fractionnaire de la bbox (valeur de retour de get_window_extent ) de l'artiste :an1 = ax.annotate("Test 1", xy=(0.5, 0.5), xycoords="data", va="center", ha="center", bbox=dict(boxstyle="round", fc="w")) an2 = ax.annotate("Test 2", xy=(1, 0.5), xycoords=an1, # (1, 0.5) of the an1's bbox xytext=(30, 0), textcoords="offset points", va="center", ha="left", bbox=dict(boxstyle="round", fc="w"), arrowprops=dict(arrowstyle="->"))
Notez que vous devez vous assurer que l'étendue de l'artiste de coordonnées ( an1 dans l'exemple ci-dessus) est déterminée avant que an2 ne soit dessiné. Habituellement, cela signifie que an2 doit être dessiné après an1 .
Un objet appelable qui prend l'instance de moteur de rendu comme argument unique et renvoie soit a,
Transform
soit aBboxBase
. La valeur de retour est alors traitée comme dans (1), pour les transformations, ou dans (2), pour les bboxes. Par exemple,an2 = ax.annotate("Test 2", xy=(1, 0.5), xycoords=an1, xytext=(30, 0), textcoords="offset points")
est identique à :
an2 = ax.annotate("Test 2", xy=(1, 0.5), xycoords=an1.get_window_extent, xytext=(30, 0), textcoords="offset points")
Une paire de spécifications de coordonnées -- la première pour la coordonnée x et la seconde pour la coordonnée y ; par exemple
annotate("Test", xy=(0.5, 1), xycoords=("data", "axes fraction"))
Ici, 0,5 est en coordonnées de données et 1 en coordonnées d'axes normalisés. Chacune des spécifications de coordonnées peut également être un artiste ou une transformation. Par exemple,
Parfois, vous souhaitez que votre annotation comporte des "points décalés", non pas à partir du point annoté mais à partir d'un autre point.
text.OffsetFrom
est une aide pour de tels cas.Vous pouvez jeter un œil à cet exemple Annotating Plots .
Utilisation de ConnectionPatch #
ConnectionPatch
est comme une annotation sans texte. S'il annotate
est suffisant dans la plupart des situations, ConnectionPatch
il est utile lorsque vous souhaitez connecter des points sur des axes différents.
from matplotlib.patches import ConnectionPatch
xy = (0.2, 0.2)
con = ConnectionPatch(xyA=xy, coordsA=ax1.transData,
xyB=xy, coordsB=ax2.transData)
fig.add_artist(con)
Le code ci-dessus relie le point xy dans les coordonnées de données de ax1
au point xy dans les coordonnées de données de ax2
. Voici un exemple simple.
Ici, nous avons ajouté le ConnectionPatch
à la figure (avec add_artist
) plutôt qu'à l'un ou l'autre des axes : cela garantit qu'il est dessiné au-dessus des deux axes, et est également nécessaire si vous utilisez Constrained_layout pour positionner les axes.
Sujets avancés #
Effet Zoom entre Axes #
mpl_toolkits.axes_grid1.inset_locator
définit certaines classes de patch utiles pour interconnecter deux axes. Comprendre le code nécessite une certaine connaissance du système de transformation de Matplotlib.
Définir le style de boîte personnalisé #
Vous pouvez utiliser un style de boîte personnalisé. La valeur de boxstyle
peut être un objet appelable sous les formes suivantes :
def __call__(self, x0, y0, width, height, mutation_size,
aspect_ratio=1.):
'''
Given the location and size of the box, return the path of
the box around it.
- *x0*, *y0*, *width*, *height* : location and size of the box
- *mutation_size* : a reference scale for the mutation.
- *aspect_ratio* : aspect-ratio for the mutation.
'''
path = ...
return path
Voici un exemple complet.
De même, vous pouvez définir un ConnectionStyle personnalisé et un ArrowStyle personnalisé. Consultez le code source de lib/matplotlib/patches.py
et vérifiez comment chaque classe de style est définie.