Private Sub Worksheet_Change(ByVal Target As Range)
Dim TS As ListObject 'déclare la variable TS (Tableau Structuré)
Dim TV As Variant 'déclare la variable TV (Tableau des Valeurs)
Dim L As String 'déclare la variable L (Liste)
If Target.Address <> "$H$12" Then Exit Sub 'si le changement a lieu ailleurs que dans H12 (la cible) , sort de la procédure
Set TS = Me.ListObjects(1) 'définit le tableau structuré TS
TV = TS.HeaderRowRange 'définit le tableau des valeurs TV (les en-têtes de TS)
L = "" 'vide la liste L
If Target.Value = "" Then 'condition 1 : si la cellule cible est effacée
Target.Offset(0, 1).Value = "" 'efface la cellule à droite de la cible
Target.Offset(0, 1).Validation.Delete 'supprime la validation de données de la cellule à droite de la cible
Exit Sub 'sort de la procédure
Else 'sinon
Target.Offset(0, 1).Value = "" 'efface le contenu de la cellule à droite de la cible
For J = 1 To UBound(TV, 2) 'boucle sur toutes les colonnes J du tableau des valeurs TV (toutes les en-têtes)
If TV(1, J) = Target.Value Then 'condition 2 : si la donnée ligne 1 colonne J de TV est égale à la cellule cible
'définit la liste L (regroupe les données de la colonne J de TS en les séparant par une virgule)
L = Join(Application.Transpose(TS.DataBodyRange.Columns(J)), ",")
Exit For 'sort de la boucle
End If 'fin de la condition 2
Next J 'prochaine colonne de la boucle
With Target.Offset(0, 1).Validation 'prend en compte la validation de données de la cellule à droite de la cible
.Delete 'supprime la validation existante
'condition : si le nombre de valeurs de la colonne est égal à 1
If Application.WorksheetFunction.CountA(TS.DataBodyRange.Columns(J)) = 1 Then
Target.Offset(0, 1).Value = TS.DataBodyRange(1, J) 'renvoie la valeur unique dans la cellule à droite de la cible
GoTo fin 'va à l'étiquette "fin"
End If 'fin de la condition
.Add xlValidateList, Formula1:=L 'redéfinit la validation de données avec la liste L
End With 'fin de la prise en compte de la validation de données de la cellule à droite de la cible
End If 'fin de la condition 1
fin: 'étiquette
Target.Offset(0, 1).Select 'sélectionne la cellule à drote de la cible
End Sub