Cours
Plotly est l'une des bibliothèques Python les plus puissantes et les plus populaires pour créer des graphiques interactifs. Si la création de graphiques de base avec Plotly est simple, les visualisations de données vraiment percutantes nécessitent souvent des éléments supplémentaires qui guident l'attention de l'observateur et fournissent un contexte important. C'est là que les formes de Plotly deviennent précieuses.
Les formes sont des éléments graphiques tels que des rectangles, des lignes et des cercles que vous pouvez dessiner au-dessus de vos figures Plotly pour les annoter, les mettre en évidence et ajouter un contexte crucial. Ils sont la clé pour transformer un graphique standard en une visualisation riche, perspicace et de qualité.
Image par l'auteur
Dans cet article, nous verrons tout ce que vous devez savoir sur les formes graphiques, de la mise en œuvre de base aux techniques de personnalisation avancées. Pour ceux qui découvrent Plotly, se familiariser avec son interface de haut niveau est une excellente première étape, et ce... Introduction à la visualisation de données avec Plotly en Python peut vous aider à maîtriser les principes fondamentaux avant de vous lancer dans des personnalisations plus profondes telles que les formes.
Que sont les formes graphiques ?
Les formes graphiques sont des graphiques vectoriels dessinés sur une figure pour fournir un contexte supplémentaire ou mettre en évidence des zones spécifiques. Ces annotations sont importantes pour construire des graphiques qui sont non seulement visuellement attrayants mais aussi riches en informations.
L'importance des formes dans la visualisation des données
En matière de visualisation de données, la clarté est importante. Alors que les graphiques tels que les diagrammes de dispersion ou les diagrammes à barres présentent les données, les formes aident à raconter l'histoire qui se cache derrière les données. Ils remplissent deux fonctions principales :
- Mettre en évidence les tendances des données : Les formes peuvent attirer l'attention sur des périodes ou des événements clés dans vos données. Par exemple, vous pouvez utiliser un rectangle pour ombrer une période de récession sur un graphique de séries chronologiques du PIB ou tracer une ligne pour marquer un changement de politique important. Ce repère visuel permet à l'observateur de comprendre immédiatement l'impact des facteurs externes sur les données.
- Fournir des annotations contextuelles : Les formes peuvent encercler ou pointer vers des points ou des groupes de données spécifiques, tels que des valeurs aberrantes, des groupes d'intérêt ou des seuils critiques. Imaginez un tableau de contrôle de la qualité dans lequel vous utilisez des cercles pour signaler les mesures qui sortent des limites acceptables. L'interprétation des données est ainsi plus rapide et plus intuitive.
Si vous souhaitez avoir un aperçu rapide des visualisations de données les plus courantes, savoir quand les utiliser et quels sont les cas d'utilisation les plus fréquents, consultez notre Aide-mémoire sur la visualisation de données.
Vue d'ensemble des types de formes dans Plotly
Plotly prend en charge plusieurs types de formes géométriques qui peuvent être ajoutées à la disposition d'une figure. Chacun d'eux est défini par son site type
et des paramètres de coordonnées spécifiques.
Voici un bref aperçu des formes primaires :
- Rectangle (
type: 'rect'
) : Défini par deux angles opposés (x0
,y0
) et (x1
,y1
). Les rectangles sont parfaits pour ombrer des régions d'intérêt ou mettre en évidence une fenêtre de données spécifique. - Ligne (
type: 'line'
) : Défini par un point de départ (x0
,y0
) et un point d'arrivée (x1
,y1
). Les lignes sont excellentes pour créer des lignes de tendance, des seuils ou des repères. - Cercle (
type: 'circle'
) : Défini par un centre (x0
,y0
) et un rayon. Les cercles sont idéaux pour mettre en valeur des points de données individuels ou de petits groupes. Notez que la création d'un cercle implique souvent la définition d'un rapport d'aspect égal pour les axes (fig.update_layout(yaxis_scaleanchor="x")
) afin d'éviter que le cercle ne ressemble à un ovale. - Chemin (
type: 'path'
) : Défini par une chaîne de chemin SVG. Les chemins vous permettent de dessiner des formes complexes et libres, y compris des polygones. Vous fournissez une séquence de commandes (commeM
pour move,L
pour line to,Z
pour close path) pour dessiner n'importe quelle forme dont vous avez besoin. Il s'agit de l'option la plus polyvalente pour créer des annotations géométriques personnalisées.
Comprendre ces types de base est la première étape vers la maîtrise des annotations visuelles dans vos graphiques Plotly.
Ajouter des formes aux graphiques Plotly
La mise en œuvre de formes graphiques dans vos visualisations implique la compréhension de deux approches principales : la méthode add_shape()
pour les formes individuelles et l'approche update_layout()
pour les formes multiples. Les deux méthodes offrent des avantages uniques en fonction de votre cas d'utilisation spécifique et de vos préférences en matière de flux de travail. Voyons comment ajouter des formes à l'aide de la méthode add_shape()
.
Comment ajouter des formes en utilisant add_shape() ?
La principale méthode pour ajouter une forme unique à une figure Plotly est fig.add_shape()
. La méthode add_shape()
est une fonction de l'objet plotly.graph_objects.Figure
. Vous créez d'abord votre figure de base (par exemple, un graphique de dispersion ou un graphique linéaire), puis vous appelez cette méthode pour superposer la forme.
Cette fonction est particulièrement utile lorsque vous devez ajouter des formes par programme en fonction de certaines conditions ou valeurs de données. Prenons un exemple de base où nous mettons en évidence une région spécifique sur un graphique de séries temporelles.
import plotly.graph_objects as go
import numpy as np
# Create sample data
x = np.linspace(0, 10, 100)
y = np.sin(x) + np.random.normal(0, 0.1, 100)
# Create base figure
fig = go.Figure()
fig.add_trace(go.Scatter(x=x, y=y, mode='lines', name='Signal'))
# Add a shape using add_shape method
fig.add_shape(
type="rect", # Shape type
x0=2, x1=4, # X coordinates
y0=-2, y1=2, # Y coordinates
fillcolor="rgba(255, 0, 0, 0.3)", # Fill color with transparency
line=dict(color="red", width=2) # Border styling
)
fig.show()
Sortie:
La fonctionnalité du graphique add_shape()
devient particulièrement puissante lorsque vous comprenez le système de coordonnées. Les formes peuvent faire référence à différents systèmes de coordonnées à l'aide des paramètres xref
et yref
. Modifions le graphique ci-dessus en utilisant ces paramètres comme indiqué ci-dessous :
# Shape referenced to data coordinates (default)
fig.add_shape(type="line", x0=1, x1=9, y0=0, y1=0,
line=dict(color="green", width=3))
# Shape referenced to paper coordinates (0-1 scale)
fig.add_shape(type="rect", xref="paper", yref="paper",
x0=0.1, x1=0.9, y0=0.1, y1=0.9,
fillcolor="rgba(0, 0, 255, 0.1)")
Sortie:
Personnalisation des rectangles et des lignes
Les rectangles et les lignes sont les formes les plus couramment utilisées pour les annotations. Plotly propose des options de personnalisation étendues pour contrôler leur apparence. Pour une référence rapide sur la syntaxe courante de Plotly, l' aide-mémoire de Plotly Express est une ressource inestimable. Voyons comment personnaliser ces formes.
Personnalisation de la forme du rectangle
Les rectangles sont définis par deux points (x0
,y0
et x1
, y1
). Vous pouvez styliser le remplissage et la bordure séparément.
# Advanced rectangle customization
fig.add_shape(
type="rect",
x0=3, x1=7,
y0=-1.5, y1=1.5,
# Fill properties
fillcolor="rgba(50, 171, 96, 0.4)",
# Line properties
line=dict(
color="darkgreen",
width=3,
dash="dashdot" # Options: solid, dot, dash, longdash, dashdot
),
# Layer control
layer="below" # Options: above, below
)
Sortie :
Personnalisation de la forme des lignes
Les lignes peuvent être ajoutées à l'aide des méthodes spécialisées "add_hline" et "add_vline" pour les lignes horizontales et verticales qui couvrent l'ensemble du graphique, ou à l'aide de la méthode générale "add_shape" pour un contrôle plus précis. Prenons un exemple :
# Horizontal threshold lines
fig.add_hline(y=1.0, line_dash="dash", line_color="red",
annotation_text="Upper Threshold")
fig.add_hline(y=-1.0, line_dash="dash", line_color="red",
annotation_text="Lower Threshold")
# Custom diagonal line
fig.add_shape(
type="line",
x0=0, x1=10,
y0=-2, y1=2,
line=dict(
color="purple",
width=4,
dash="longdashdot"
)
)
Sortie :
Ces exemples démontrent la facilité avec laquelle vous pouvez ajouter et styliser des formes fondamentales de Plotly pour rendre vos graphiques plus informatifs.
Configuration et personnalisation avancées
Au-delà de l'ajout de formes de base, Plotly offre des outils puissants pour gérer plusieurs formes et contrôler leur hiérarchie visuelle. Ces fonctions avancées sont essentielles pour créer des visualisations complexes, superposées et dynamiques. Voyons comment configurer et personnaliser les graphiques.
Utilisation de plotly.update_layout pour les mises à jour dynamiques
Alors que la méthode add_shape()
est parfaite pour ajouter des formes une par une, la méthode update_layout()
est plus efficace pour gérer une collection de formes, en particulier lorsqu'elles sont générées par programme. Au lieu d'appeler une fonction pour chaque forme, vous pouvez transmettre une liste de dictionnaires de formes directement à l'argument shapes
dans update_layout()
.
Voyons un exemple d'utilisation de cette méthode :
import plotly.graph_objects as go
import numpy as np
# Sample scatter plot data
x_data = np.linspace(0, 10, 50)
y_data = np.sin(x_data) + np.random.normal(0, 0.1, 50)
fig = go.Figure(data=go.Scatter(x=x_data, y=y_data, mode='markers', name='Data Points'))
# Define a list of shapes to add
shapes_to_add = [
# A rectangle highlighting a peak area
dict(
type="rect",
x0=1, x1=2.5, y0=0.8, y1=1.2,
fillcolor="rgba(255, 165, 0, 0.4)",
line_width=0
),
# A vertical line marking an event
dict(
type="line",
x0=7.5, x1=7.5, y0=0, y1=1,
yref="paper", # Span the full plot height
line=dict(color="red", width=2, dash="dot")
)
]
# Add all shapes at once using update_layout
fig.update_layout(
shapes=shapes_to_add
)
fig.show()
Sortie :
Cette méthode est particulièrement efficace pour les applications dynamiques, telles qu'un tableau de bord Dash, où les formes doivent changer en fonction des données saisies par l'utilisateur. Vous pouvez générer une nouvelle liste d'objets de forme et mettre à jour la mise en page en une seule opération propre. Cette approche permet d'organiser votre code et est généralement plus performante pour l'ajout d'un grand nombre de formes à la fois.
Superposition et contrôle de l'indice z
Lorsque vous ajoutez des formes à un graphique, il est important de contrôler si elles apparaissent au-dessus ou derrière vos données. Plotly gère cela par le biais de la propriété de couche. Bien qu'il ne s'agisse pas d'un z-index
granulaire comme en CSS, il offre un contrôle essentiel sur l'empilement visuel.
La propriété layer
peut prendre l'une des deux valeurs suivantes :
'above'
: La forme est dessinée au-dessus des traces de données. Il s'agit du paramètre par défaut, utile pour les annotations qui doivent être clairement visibles.'below'
: La forme est dessinée sous les traces de données et les lignes de grille. C'est la solution idéale pour ombrer l'arrière-plan ou mettre en évidence des régions sans masquer les points de données eux-mêmes.
L'ordre des formes dans le champ formes a également son importance : les formes définies plus loin dans la liste seront dessinées au-dessus de celles définies plus tôt (dans le même calque).
Voici un exemple illustrant l'effet de la superposition :
import plotly.graph_objects as go
fig = go.Figure(data=go.Scatter(x=[1, 2, 3, 4, 5], y=[5, 3, 4, 2, 6], mode='markers', marker_size=20, name='Data'))
# Add a shape BELOW the data points
fig.add_shape(
type="rect",
x0=2.5, y0=2.5, x1=4.5, y1=4.5,
fillcolor="LightPink",
opacity=0.8,
layer="below", # Key parameter
line_width=0
)
# Add a shape ABOVE the data points
fig.add_shape(
type="circle",
x0=0.5, y0=4.5, x1=1.5, y1=5.5,
fillcolor="LightSeaGreen",
opacity=0.6,
layer="above", # Key parameter
line_width=0
)
fig.update_layout(
xaxis=dict(showgrid=False), # Turn off gridlines to see effect clearly
yaxis=dict(showgrid=False)
)
fig.show()
Sortie :
Comme vous pouvez le voir, le rectangle rose se trouve derrière les marqueurs, tandis que le cercle vert recouvre le point de données.
La maîtrise de ces techniques de mise en page et de superposition est un élément clé de la création de visualisations de données plus avancées et interactives avec Plotly. Pour ceux qui travaillent en R, des concepts similaires s'appliquent, comme exploré dans Intermediate Interactive Data Visualization with Plotly in R.
Édition interactive de formes
L'une des fonctionnalités les plus puissantes de Plotly est son interactivité. Vous pouvez rendre les formes Plotly modifiables, ce qui permet aux utilisateurs de les faire glisser, de les redimensionner et de les faire pivoter directement sur le graphique. Cette fonction est activée en définissant editable=True
dans la définition de la forme. Voyons un exemple de la manière de procéder :
import plotly.graph_objects as go
import numpy as np
# Create a scatter plot
fig = go.Figure(go.Scatter(
x=np.random.rand(100),
y=np.random.rand(100),
mode='markers'
))
# Add a draggable rectangle
fig.add_shape(
type="rect",
x0=0.2, y0=0.2, x1=0.5, y1=0.5,
line=dict(color="RoyalBlue", width=2),
fillcolor="LightSkyBlue",
opacity=0.5,
editable=True # This makes the shape interactive
)
fig.update_layout(
xaxis=dict(range=[0, 1]),
yaxis=dict(range=[0, 1]),
# The 'newshape' button in the modebar allows drawing new shapes
# The config dictionary enables editing of existing shapes
dragmode='select'
)
# To enable editing, the modebar must be visible (default)
# and the plot's config can ensure editing tools are available.
fig.show(config={'edits': {'shapePosition': True}})
Sortie:
Les formes interactives sont extrêmement utiles pour l'analyse exploratoire des données. Par exemple, un utilisateur peut faire glisser un rectangle sur différentes périodes pour voir les statistiques récapitulatives correspondantes mises à jour en temps réel dans une application Dash. Ils peuvent également redimensionner un cercle afin de sélectionner un autre groupe de points pour une étude plus approfondie.
Bien que puissant, n'oubliez pas que l'utilisation intensive de formes modifiables peut avoir des conséquences sur les performances des applications web complexes. Cependant, ils sont indispensables pour créer des outils véritablement dynamiques et orientés vers l'utilisateur.
L'exploration de l'interactivité est une partie importante de la visualisation moderne des données, un sujet bien couvert dans des cours tels que Visualisation interactive des données avec Plotly en R, qui partage de nombreux principes avec son homologue Python.
Intégration de Plotly avec d'autres bibliothèques
Bien que les formes intégrées de Plotly soient polyvalentes, vous devez parfois créer des géométries très complexes ou personnalisées. En intégrant des bibliothèques spécialisées comme Shapely, vous pouvez définir des polygones sophistiqués et les ajouter à vos visualisations en tant que formes Plotly personnalisées.
Utiliser Shapely pour les formes géométriques avancées
Shapely est une puissante bibliothèque Python pour la manipulation et l'analyse d'objets géométriques planaires. Il s'agit de l'outil de référence pour la géométrie informatique, souvent utilisé dans l'analyse géospatiale. Vous pouvez l'utiliser pour créer des formes complexes, comme l'union de deux cercles qui se chevauchent ou un polygone percé d'un trou, puis les visualiser dans Plotly.
Le processus comporte deux étapes principales :
- Définissez la forme complexe à l'aide de Shapely.
- Extrayez les coordonnées de l'objet Shapely et formatez-les en tant que chaîne de chemin SVG, que Plotly peut rendre à l'aide de
type: 'path'
.
Une chaîne de chemin SVG est un mini-langage de dessin. Il utilise des commandes telles que M
(moveto) pour définir un point de départ, L
(lineto) pour tracer une ligne jusqu'à un nouveau point, et Z
pour fermer le chemin en traçant une ligne jusqu'au point de départ.
Voyons comment créer un polygone avec une découpe et l'ajouter à une figure Plotly.
import plotly.graph_objects as go
from shapely.geometry import Polygon
# 1. Create a complex shape using Shapely
# An outer rectangle
outer_coords = [(1, 1), (1, 5), (8, 5), (8, 1)]
# An inner rectangle (this will be the "hole")
inner_coords = [(3, 2), (3, 4), (6, 4), (6, 2)]
# Define the polygon with a hole
polygon_with_hole = Polygon(outer_coords, [inner_coords])
# 2. Extract coordinates and build the SVG path string
# The exterior path
exterior_x, exterior_y = polygon_with_hole.exterior.xy
path = f"M {exterior_x[0]} {exterior_y[0]}"
for x, y in zip(exterior_x[1:], exterior_y[1:]):
path += f" L {x} {y}"
path += " Z" # Close the exterior path
# The interior path (the hole)
interior_x, interior_y = polygon_with_hole.interiors[0].xy
path += f" M {interior_x[0]} {interior_y[0]}"
for x, y in zip(interior_x[1:], interior_y[1:]):
path += f" L {x} {y}"
path += " Z" # Close the interior path
# Create a figure
fig = go.Figure()
# Add the complex shape to the figure
fig.add_shape(
type="path",
path=path,
fillcolor="LightSeaGreen",
opacity=0.7,
line_color="DarkSlateGray"
)
# You can add data to see how the shape interacts with it
fig.add_trace(go.Scatter(
x=[2, 7, 4.5],
y=[3, 3, 1.5],
mode='markers',
marker=dict(size=15, color='DarkRed')
))
# Use scaleanchor to ensure the shape's aspect ratio is preserved
fig.update_yaxes(scaleanchor="x", scaleratio=1)
fig.show()
Sortie:
Cette technique est très utile pour les applications géospatiales, telles que le traçage de territoires de vente personnalisés, ou dans des contextes scientifiques où vous pourriez avoir besoin de mettre en évidence des zones d'intérêt irrégulières.
Comprendre comment les différents types de graphiques de données sont créés et comment ils peuvent être améliorés avec de tels outils est une compétence fondamentale pour tout praticien des données. Vous pouvez en savoir plus sur les différents types de graphiques dans ce guide sur la façon de les créer en Python.
Personnalisation du style et de l'esthétique
L'apparence par défaut des formes Plotly est fonctionnelle, mais la personnalisation de leur style est importante pour créer une visualisation soignée et d'aspect professionnel. Une utilisation réfléchie des couleurs, de l'opacité et des remplissages peut améliorer considérablement la lisibilité et l'attrait esthétique.
Couleur, opacité et remplissage des motifs
Plotly vous permet de contrôler finement l'apparence des formes, ce qui vous permet de les faire correspondre à la palette de couleurs et au langage de conception de votre graphique.
Pour un contrôle précis des couleurs et de la transparence, il est fortement recommandé d'utiliser la spécification RGBA (Rouge, Vert, Bleu, Alpha). Le canal a
(alpha) contrôle l'opacité, une valeur de 1
étant totalement opaque et 0
totalement transparente .
C'est essentiel pour créer des mises en évidence discrètes, où la forme ajoute un contexte sans cacher complètement les données sous-jacentes. Vous pouvez fournir les valeurs RGBA sous la forme d'une chaîne de caractères comme 'rgba(255, 99, 71, 0.5)'
. Prenons un exemple :
import plotly.graph_objects as go
import numpy as np
# Create sample data for styling demonstration
x = np.linspace(0, 10, 100)
y1 = np.sin(x) + np.random.normal(0, 0.1, 100)
y2 = np.cos(x) + np.random.normal(0, 0.1, 100)
fig = go.Figure()
fig.add_trace(go.Scatter(x=x, y=y1, name='Signal 1', line=dict(color='blue')))
fig.add_trace(go.Scatter(x=x, y=y2, name='Signal 2', line=dict(color='red')))
# RGBA Color Technique 1: Graduated opacity for depth
opacity_levels = [0.15, 0.25, 0.35]
colors = ['255,0,0', '0,255,0', '0,0,255']
for i, (opacity, color) in enumerate(zip(opacity_levels, colors)):
fig.add_shape(
type="rect",
x0=i*2.5, x1=(i+1)*2.5,
y0=-3, y1=3,
fillcolor=f"rgba({color},{opacity})",
line=dict(color=f"rgb({color})", width=2),
layer="below"
)
# RGBA Technique 2: Color blending for overlapping regions
fig.add_shape(
type="circle",
x0=7.5, x1=9.5,
y0=-1, y1=1,
fillcolor="rgba(255, 255, 0, 0.4)", # Semi-transparent yellow
line=dict(color="orange", width=3),
layer="below"
)
fig.update_layout(
title="Advanced RGBA Color Techniques in Plotly Shapes",
showlegend=True
)
fig.show()
Sortie:
Stratégies de simulation de remplissage de motifs
Bien que Plotly ne prenne pas nativement en charge les remplissages de motifs, les praticiens des données peuvent simuler des motifs de remplissage complexes à l'aide de techniques créatives. Par exemple, nous pouvons créer des motifs dans le graphique à l'aide d'une fonction, comme indiqué ci-dessous :
def create_pattern_fill_simulation(fig, x0, x1, y0, y1, pattern_type='diagonal'):
"""Simulate pattern fills using multiple overlapping shapes"""
if pattern_type == 'diagonal':
# Create diagonal line pattern
line_spacing = 0.2
line_width = 1
# Calculate diagonal lines
range_x = x1 - x0
range_y = y1 - y0
num_lines = int((range_x + range_y) / line_spacing)
for i in range(num_lines):
offset = i * line_spacing
# Calculate line endpoints for diagonal pattern
start_x = max(x0, x0 + offset - range_y)
start_y = max(y0, y1 - offset)
end_x = min(x1, x0 + offset)
end_y = min(y1, y1 - offset + range_x)
fig.add_shape(
type="line",
x0=start_x, x1=end_x,
y0=start_y, y1=end_y,
line=dict(color="rgba(0, 0, 0, 0.3)", width=line_width),
layer="above"
)
elif pattern_type == 'crosshatch':
# Create crosshatch pattern
spacing = 0.3
# Vertical lines
x_lines = np.arange(x0, x1, spacing)
for x_line in x_lines:
fig.add_shape(
type="line",
x0=x_line, x1=x_line,
y0=y0, y1=y1,
line=dict(color="rgba(100, 100, 100, 0.4)", width=1),
layer="above"
)
# Horizontal lines
y_lines = np.arange(y0, y1, spacing)
for y_line in y_lines:
fig.add_shape(
type="line",
x0=x0, x1=x1,
y0=y_line, y1=y_line,
line=dict(color="rgba(100, 100, 100, 0.4)", width=1),
layer="above"
)
return fig
# Demonstration of pattern fill simulation
pattern_fig = go.Figure()
pattern_fig.add_trace(go.Scatter(x=[1, 2, 3, 4, 5], y=[2, 4, 3, 5, 1],
mode='lines+markers', name='Data'))
# Add base rectangle
pattern_fig.add_shape(
type="rect",
x0=1.5, x1=3.5,
y0=1, y1=5,
fillcolor="rgba(200, 200, 255, 0.3)",
line=dict(color="blue", width=2),
layer="below"
)
# Apply pattern fill simulation
pattern_fig = create_pattern_fill_simulation(pattern_fig, 1.5, 3.5, 1, 5, 'diagonal')
pattern_fig.show()
Simulation de l'effet de gradient
La création d'effets de dégradé nécessite la superposition stratégique de plusieurs formes avec une opacité variable. Nous pouvons créer des motifs en utilisant la même stratégie que celle utilisée pour créer les motifs, comme indiqué ci-dessous :
def create_gradient_effect(fig, x0, x1, y0, y1, start_color, end_color, num_bands=20):
"""Simulate gradient fill using multiple rectangular bands"""
# Parse RGB values from color strings
def parse_rgb(color_str):
if color_str.startswith('rgb('):
values = color_str[4:-1].split(',')
return [int(v.strip()) for v in values]
return [0, 0, 0] # Default to black if parsing fails
start_rgb = parse_rgb(start_color) if isinstance(start_color, str) else start_color
end_rgb = parse_rgb(end_color) if isinstance(end_color, str) else end_color
band_height = (y1 - y0) / num_bands
for i in range(num_bands):
# Calculate interpolated color
ratio = i / (num_bands - 1)
r = int(start_rgb[0] + (end_rgb[0] - start_rgb[0]) * ratio)
g = int(start_rgb[1] + (end_rgb[1] - start_rgb[1]) * ratio)
b = int(start_rgb[2] + (end_rgb[2] - start_rgb[2]) * ratio)
# Calculate band position
band_y0 = y0 + i * band_height
band_y1 = band_y0 + band_height
fig.add_shape(
type="rect",
x0=x0, x1=x1,
y0=band_y0, y1=band_y1,
fillcolor=f"rgba({r}, {g}, {b}, 0.7)",
line=dict(width=0), # No border for seamless gradient
layer="below"
)
return fig
# Apply gradient effect
gradient_fig = go.Figure()
gradient_fig.add_trace(go.Scatter(x=list(range(10)),
y=np.random.randn(10).cumsum(),
mode='lines', name='Time Series'))
gradient_fig = create_gradient_effect(
gradient_fig, 2, 8, -3, 3,
[255, 0, 0], [0, 0, 255], # Red to blue gradient
num_bands=30
)
gradient_fig.show()
Sortie:
Dépannage et optimisation
Bien que l'ajout de formes Plotly soit généralement simple, vous pouvez rencontrer des problèmes d'alignement ou de performance, en particulier dans les graphiques complexes. En comprenant ces pièges courants et en sachant comment y remédier, vous économiserez beaucoup de temps et d'efforts.
Problèmes courants liés à l'alignement des formes
L'un des défis les plus fréquents consiste à faire apparaître les formes exactement là où vous le souhaitez. Une ligne censée couvrir toute la largeur du graphique peut être insuffisante, ou un rectangle peut ne pas s'aligner sur les lignes de la grille comme prévu. Ces problèmes découlent presque toujours d'un mauvais référencement des coordonnées.
Plotly utilise deux systèmes de coordonnées pour placer les formes :
- Coordonnées des données (
xref: 'x', yref: 'y'
): Il s'agit de la valeur par défaut. La position de la forme est liée aux valeurs des axes x et y. Par exemple,x0=50
place le point à la marque 50 sur l'axe des x. - Coordonnées du papier (
xref: 'paper', yref: 'paper'
): La position est relative à la zone de graphique elle-même, où 0 est le début (bord gauche/bas) et 1 est la fin (bord droit/haut). Ce système est indépendant des valeurs de données ou des plages d'axes.
Le problème : Vous souhaitez tracer une ligne horizontale sur l'ensemble du graphique à l'adresse y=10
. Si vous le définissez avec x0
et x1
en utilisant des coordonnées de données, il ne couvrira que la plage de l'axe actuel. Si l'utilisateur effectue un zoom ou un panoramique, la ligne ne s'étendra pas jusqu'aux nouveaux bords.
La solution : Pour qu'une forme s'étende sur toute la largeur ou la hauteur de la zone de graphique, utilisez les coordonnées 'paper'
pour l'axe que vous souhaitez couvrir.
import plotly.graph_objects as go
fig = go.Figure(data=go.Scatter(x=[0, 10], y=[0, 20]))
# Incorrect: Vertical line that might not span the full height if the user zooms out.
# This line is drawn from y=0 to y=20 in DATA units.
fig.add_shape(
type="line",
x0=5, y0=0, x1=5, y1=20,
line=dict(color="Red", width=2, dash="dash"),
name="Incorrect Line" # Name for legend
)
# Correct: Vertical line that ALWAYS spans the full plot height.
# It is drawn from the bottom edge (0) to the top edge (1) of the PLOT area.
fig.add_shape(
type="line",
x0=8, y0=0, x1=8, y1=1,
yref="paper", # The key to spanning the full height
line=dict(color="Green", width=3),
name="Correct Line"
)
fig.update_layout(title_text="Correctly Spanning the Plot Area")
fig.show()
Sortie:
Vérifiez toujours les propriétés xref
et yref
pour vous assurer que vos formes se comportent comme prévu lors de l'interaction avec l'utilisateur, par exemple lors d'un zoom ou d'un panoramique.
Considérations sur les performances
Si vous ajoutez une poignée de formes à un graphique, l'impact sur les performances est négligeable. Cependant, l'ajout de centaines ou de milliers de formes peut ralentir considérablement le rendu et l'interactivité. Chaque forme est un élément SVG (Scalable Vector Graphics) individuel ajouté au DOM de la page web. Un grand nombre d'éléments DOM pèse sur le navigateur.
Voici des stratégies pour optimiser les performances :
- Limitez le nombre de formes : La solution la plus simple. Si vous avez besoin de visualiser des milliers de zones rectangulaires, demandez-vous si un autre type de graphique, comme
go.Heatmap
, ne pourrait pas représenter les mêmes informations plus efficacement sous la forme d'une seule trace plutôt que de milliers d'objets de forme. - Utilisez
update_layout
pour les ajouts en vrac: Comme indiqué précédemment, l'ajout d'une liste de formes viafig.update_layout(shapes=...)
est plus performant que l'appel àfig.add_shape()
dans une boucle. - Considérez les traces WebGL pour les données : Bien que les formes elles-mêmes soient rendues sous forme de SVG, vous pouvez améliorer les performances globales d'un graphique complexe en utilisant des traces basées sur WebGL (par exemple,
go.Scattergl
) pour vos données principales. Cela permet de décharger le rendu des données sur le GPU, libérant ainsi l'unité centrale pour qu'elle puisse traiter les formes SVG de manière plus fluide. Ceci est utile lorsque vous avez un grand nombre de points de données et un nombre modéré de formes.
Pour la plupart des cas d'utilisation, l'essentiel est de faire attention au nombre d'éléments de forme uniques que vous créez. Avant d'ajouter des milliers de formes Plotly en boucle, faites une pause et demandez-vous s'il n'existe pas une stratégie de visualisation plus performante.
Conclusion
La maîtrise des formes de Plotly transforme vos graphiques de simples représentations de données en histoires convaincantes et riches en contexte. Nous avons étudié le dessin de lignes et de rectangles de base jusqu'à la superposition de géométries complexes et interactives.
En appliquant ces techniques, vous pouvez orienter l'attention de votre public, mettre en évidence les informations essentielles et créer des visualisations plus intuitives qui communiquent avec clarté et impact.
Prêt à mettre ces compétences en pratique ? Commencez à construire des visualisations plus puissantes dès aujourd'hui en explorant la page d'accueil de Plotly. Introduction à la visualisation de données avec Plotly en Python et mettez vos connaissances à l'épreuve.
FAQ sur les formes de Plotly
À quoi servent les formes de Plotly ?
Les formes graphiques sont utilisées pour ajouter des annotations telles que des lignes, des rectangles et des cercles afin de mettre en évidence des zones de données clés sur un graphique.
Comment ajouter plusieurs formes dans Plotly ?
Vous pouvez ajouter plusieurs formes de manière efficace en passant une liste de dictionnaires de formes à l'attribut shapes
dans l'attribut fig.update_layout()
.
Comment dessiner une ligne verticale dans Plotly ?
Vous pouvez tracer une ligne verticale complète en utilisant type='line'
et en définissant la propriété yref='paper'
pour qu'elle couvre toute la hauteur du graphique.
Pouvez-vous mettre une forme derrière les données dans Plotly ?
Oui, vous pouvez placer une forme derrière des traces de données en définissant sa propriété layer
à 'below'
.
Comment ajouter une forme à une seule sous-partie dans Plotly ?
Vous pouvez ajouter une forme à un sous-graphe spécifique en fournissant les paramètres xref
et yref
dans sa définition.
Je suis rédacteur de contenu en science des données. J'aime créer du contenu sur des sujets liés à l'IA/ML/DS. J'explore également de nouveaux outils d'intelligence artificielle et j'écris à leur sujet.