03 Dash - Rappels
As-tu bien terminé ces quêtes ?
Introduction
Bienvenue dans ce module de formation consacré aux rappels (callbacks) dans Dash, un élément clé pour créer des applications web interactives. Les rappels sont essentiels pour gérer l'interaction entre l'utilisateur et l'application, permettant de mettre à jour les données et de modifier le comportement de l'application en temps réel. Ce cours se concentre sur l'apprentissage de la syntaxe des rappels, la compréhension des notions importantes comme Input, Output et State, et la mise en pratique à travers des exemples détaillés. Vous apprendrez comment manipuler les interactions utilisateur pour créer des expériences dynamiques et engageantes dans vos applications Dash.
Objectifs
À la fin de cette quête, vous serez capable de :
✅ Comprendre la mécanique des rappels ✅ Maîtriser la syntaxe des rappels ✅ Gérer les Input et Output ✅ Utiliser le State pour des données complémentaires ✅ Créer des rappels complexes ✅ Mettre en pratique avec des exemples réels
Sommaire
Définition
Les rappels d'une application Dash gèrent l'interaction entre l'utilisateur et le tableau de bord. Ils sont déclenchés lorsqu'un événement se produit dans l'application, tel qu'un utilisateur sélectionne une valeur dans un curseur ou clique sur un bouton. Les rappels peuvent mettre à jour les données affichées dans le tableau de bord ou modifier le comportement de l'application.
Syntaxe des rappels
La syntaxe générale d'un rappel Dash est la suivante :
@app.callback(
Output('élément-sortie', 'propriété'),
[Input('élément-entrée', 'propriété')],
[Input('élément-entrée2', 'propriété2')],
...
)
def fonction_rappel(*args):
# Code de la fonction rappel
return nouvelle-valeur
app.callback: Déclare le rappelOutput('élément-sortie', 'propriété'): Définit la propriété de l'élément de sortie qui sera mise à jour par le rappelInput('élément-entrée', 'propriété'): Définit l'élément d'entrée et la propriété qui déclenchera le rappel[Input('élément-entrée2', 'propriété2')], ...: Définit d'autres éléments d'entrée et leurs propriétés si nécessaire*args: Contient les arguments supplémentaires passés à la fonction rappelfonction_rappel: La fonction rappel proprement ditenouvelle-valeur: La valeur à retourner par la fonction rappel
Notions importantes
Dans les applications Dash, les callbacks sont essentiels pour créer des interactions dynamiques. Ils se composent généralement de trois parties : Input, Output, et State.
Input :
Les Input sont les déclencheurs des callbacks. Quand un utilisateur interagit avec un élément d'entrée (comme cliquer sur un bouton, changer la valeur d'un curseur), le callback associé est exécuté.
Exemple : Un bouton sur lequel l'utilisateur clique pour soumettre des informations.
Output :
Les Output définissent où les résultats du callback seront affichés ou modifiés dans l'interface utilisateur.
Exemple : Un paragraphe de texte qui change en fonction des actions de l'utilisateur.
State :
State permet d'inclure des données supplémentaires dans un callback sans déclencher l'exécution de celui-ci. Les données des composants State sont passées au callback, mais ne provoquent pas le callback par elles-mêmes.
Exemple : Un champ de saisie texte dont la valeur est nécessaire pour le traitement d'un callback, mais sa modification seule ne doit pas déclencher le callback.
Exemple de rappel
Voici un exemple détaillé de rappel qui met à jour un graphique en fonction de la valeur d'un curseur :
@app.callback(
Output('mon-graphique', 'figure'),
[Input('mon-curseur', 'value')]
)
def update_graph(value):
# Filtrez les données pour inclure toutes les valeurs <= 'value'
data_filtered = data[data['x'] <= value]
# Créez le graphique
fig = px.scatter(data_filtered, x='y', y='z')
fig.update_layout(title='Mon graphique', xaxis_title='Y', yaxis_title='Z')
return fig
1. Décorateur de callback :
La fonction update_graph est définie comme un callback à l'aide du décorateur @app.callback
Output('mon-graphique', 'figure'): Cela indique que le résultat du callback affectera la propriété figure du composant Dash avec l'identifiant mon-graphique. C'est la partie de l'interface utilisateur où le graphique est affiché.[Input('mon-curseur', 'value')]: Cela spécifie que le déclencheur du callback est la valeur (value) du composant Dash avec l'identifiant mon-curseur. C'est le curseur qui permet à l'utilisateur de sélectionner une valeur.
2. Fonction de Callback update_graph :
Cette fonction est appelée chaque fois que la valeur du curseur change.
-
Filtrage des données : La ligne
data_filtered = data[data['x'] <= value]filtre les données pour inclure toutes les lignes où la valeur de la colonne 'x' est inférieure ou égale à celle sélectionnée par le curseur. -
Création du graphique : Un graphique de dispersion est créé à l'aide de Plotly Express, affichant les données filtrées. Les axes sont définis avec 'y' sur l'axe des abscisses et 'z' sur l'axe des ordonnées.
-
Mise à jour de la mise en page du graphique : La mise en page du graphique est personnalisée avec un titre et des titres d'axes pour améliorer la lisibilité et l'esthétique.
3. Retour du graphique :
La figure graphique est retournée par la fonction, ce qui met à jour le graphique dans l'application Dash.
Code en situation
import dash
from dash import dcc, html
from dash.dependencies import Input, Output
import plotly.express as px
import pandas as pd
# Création d'un DataFrame de données fictives
data = pd.DataFrame({
'x': range(100), # Générer des valeurs pour 'x'
'y': [val * 2 for val in range(100)], # Générer des valeurs pour 'y'
'z': [val ** 2 for val in range(100)] # Générer des valeurs pour 'z'
})
# Initialisation de l'application Dash
app = dash.Dash(__name__)
# Définition de la mise en page de l'application
app.layout = html.Div([
# Curseur pour la sélection de la valeur 'x'
dcc.Slider(
id='mon-curseur',
min=0, # Définir le minimum de la plage de valeurs
max=99, # Définir le maximum de la plage de valeurs
step=1, # Pas du curseur
value=50, # Valeur initiale
marks={i: str(i) for i in range(0, 100, 10)} # Marques sur le curseur
),
# Espace pour le graphique mis à jour
dcc.Graph(id='mon-graphique')
])
# La fonction de rappel
@app.callback(
Output('mon-graphique', 'figure'),
[Input('mon-curseur', 'value')]
)
def update_graph(value):
# Filtrer les données pour inclure toutes les valeurs <= 'value'
data_filtered = data[data['x'] <= value]
# Créer le graphique
fig = px.scatter(data_filtered, x='y', y='z')
fig.update_layout(title='Mon graphique', xaxis_title='Y', yaxis_title='Z')
return fig
# Exécution de l'application
if __name__ == '__main__':
app.run_server(debug=True)
Autres exemples
Modifier un texte en fonction d'une saisie utilisateur
############ Importations et initialisation
import dash
from dash import dcc, html
from dash.dependencies import Input, Output
app = dash.Dash(__name__)
############ Callback et Layout
@app.callback(
Output('text-output', 'children'),
[Input('text-input', 'value')]
)
def update_text(input_value):
return f'Vous avez écrit : {input_value}'
app.layout = html.Div([
dcc.Input(id='text-input', type='text', value=''),
html.Div(id='text-output')
])
############ Execution de l'application
if __name__ == '__main__':
app.run_server(debug=True)
1. Le décorateur de callback :
@app.callbackest utilisé pour déclarer une fonction comme callback dans Dash.Output('text-output', 'children')spécifie que la sortie du callback sera la propriétéchildrendu composant avec l'identifianttext-output. Dans Dash,childrenreprésente le contenu d'un composant, du texte ou des éléments HTML (icihtml.Div).[Input('text-input', 'value')]indique que le déclencheur du callback est la propriété value du composant avec l'identifianttext-input. Ce composant est un champ de saisie (input field) dans lequel l'utilisateur peut écrire du texte.
2. La fonction de callback update_text :
- Cette fonction est appelée chaque fois que la valeur du champ de saisie (
text-input) change. input_valueest le paramètre de la fonction qui reçoit la valeur actuelle du champ de saisie.- La fonction retourne une chaîne de caractères formatée qui sera affichée dans le composant
text-output. Le format estVous avez écrit : {input_value}, où{input_value}est remplacé par le texte saisi par l'utilisateur.
3. La mise en page (Layout) de l'application :
app.layoutdéfinit la structure de l'interface utilisateur de l'application Dash.dcc.Input(id='text-input', type='text', value='')crée un champ de saisie oùidest l'identifiant du composant, type est le type de champ (texte), et value est la valeur initiale (vide dans ce cas).html.Div(id='text-output')crée un élément HTML div qui servira à afficher le texte mis à jour. L'identifiant text-output est utilisé dans le callback.
Exemple complet illustrant le fonctionnement de State :
Imaginons une application simple avec un champ de saisie texte et un bouton. Lorsque l'utilisateur clique sur le bouton, le texte saisi est affiché.
############ Importations et initialisation
import dash
from dash import dcc, html
from dash.dependencies import Input, Output, State
app = dash.Dash(__name__)
############ Callback
############ et
############ Layout
# Définition de la mise en page de l'application
app.layout = html.Div([
dcc.Input(id='input-text', type='text', value=''),
html.Button('Soumettre', id='submit-button'),
html.Div(id='output-div')
])
# Définition du callback
@app.callback(
Output('output-div', 'children'),
[Input('submit-button', 'n_clicks')],
[State('input-text', 'value')]
)
def update_output(n_clicks, input_value):
if n_clicks is None:
return "Cliquez sur le bouton pour afficher le texte."
else:
return f'Le texte saisi est : {input_value}'
############ Execution de l'application
if __name__ == '__main__':
app.run_server(debug=True)
Explication du Code :
Mise en Page :
La mise en page contient un champ de saisie (dcc.Input), un bouton (html.Button) et un div pour afficher le résultat.
Callback :
- Le bouton est l'
Input. Quand il est cliqué, le callback est déclenché. - Le champ de saisie est un
State. Sa valeur est utilisée dans le callback, mais sa modification seule ne déclenche pas le callback. - Le div (
output-div) est l'Output, où le résultat du callback est affiché.
Quand l'utilisateur entre du texte et clique sur le bouton, le texte est affiché dans le div de sortie.
Cet exemple montre comment State peut être utilisé pour inclure des données supplémentaires dans le traitement d'un callback sans être le déclencheur direct de ce callback.
Ressources
Core Components - Documentation
HTML Components - Documentation
Data Components - Documentation
Challenge
Améliorer l'application Dash existante (de la quête précédente) en ajoutant des fonctionnalités interactives grâce à des callbacks.
L'objectif est de permettre aux utilisateurs de filtrer les données affichées dans le graphique en fonction de l'auteur sélectionné et du nombre maximal de pages.
Filtrage par auteur :
- Ajoutez un callback qui met à jour le graphique en fonction de l'auteur sélectionné dans le menu déroulant.
- Le graphique doit afficher uniquement les livres de l'auteur choisi.
Filtrage par nombre de pages :
Intégrez un autre callback qui ajuste le graphique pour montrer uniquement les livres dont le nombre de pages est inférieur ou égal au nombre entré dans le champ page-input.
Combinaison des filtres :
Assurez-vous que les deux filtres (auteur et nombre de pages) peuvent fonctionner ensemble pour affiner les résultats affichés dans le graphique.
Solution proposée
Dans ce fichier vous allez trouver une solution possible au challenge.