OUJOOD.COM
Le widget Combobox fait partie du module ttk (Themed Tk) — il n'existe pas dans le module tkinter classique. Il combine un champ texte et un menu déroulant : l'utilisateur peut soit choisir parmi les options proposées, soit saisir sa propre valeur si on le permet. Son apparence est nettement plus moderne que les widgets classiques.
Combobox de base
import tkinter as tk from tkinter import ttk # Combobox est dans ttk fenetre = tk.Tk() fenetre.title("Combobox") fenetre.geometry("320x180") pays = ["France", "Belgique", "Suisse", "Canada", "Maroc", "Tunisie", "Algérie", "Sénégal", "Côte d'Ivoire"] tk.Label(fenetre, text="Pays :").pack(pady=(20, 4)) combo = ttk.Combobox(fenetre, values=pays, width=22) combo.set("Choisissez un pays") # texte affiché par défaut combo.pack() def afficher(): label.config(text=f"Pays sélectionné : {combo.get()}") tk.Button(fenetre, text="Valider", command=afficher).pack(pady=10) label = tk.Label(fenetre, text="") label.pack() fenetre.mainloop()
combo.get() retourne la valeur affichée dans le champ — que l'utilisateur l'ait saisie ou sélectionnée dans la liste. combo.set() définit la valeur affichée sans la lier à la liste. Pour sélectionner un élément de la liste par indice : combo.current(0) sélectionne le premier.
Mode readonly — liste fermée
Par défaut, l'utilisateur peut saisir n'importe quoi dans le champ. Le mode readonly restreint la saisie aux éléments de la liste :
import tkinter as tk
from tkinter import ttk
fenetre = tk.Tk()
fenetre.geometry("340x200")
niveaux = ["Débutant", "Intermédiaire", "Avancé", "Expert"]
langues = ["Français", "Anglais", "Arabe", "Espagnol", "Allemand"]
frame = tk.Frame(fenetre)
frame.pack(pady=20)
tk.Label(frame, text="Niveau :").grid(row=0, column=0, sticky="e", padx=10, pady=6)
combo_niv = ttk.Combobox(frame, values=niveaux, state="readonly", width=16)
combo_niv.current(0) # sélectionne "Débutant" par défaut
combo_niv.grid(row=0, column=1)
tk.Label(frame, text="Langue :").grid(row=1, column=0, sticky="e", padx=10, pady=6)
combo_lang = ttk.Combobox(frame, values=langues, state="readonly", width=16)
combo_lang.current(0)
combo_lang.grid(row=1, column=1)
def valider():
label.config(text=f"{combo_niv.get()} en {combo_lang.get()}")
tk.Button(fenetre, text="Valider", command=valider).pack()
label = tk.Label(fenetre, text="")
label.pack(pady=6)
fenetre.mainloop()
En mode readonly, le champ est verrouillé mais le menu déroulant reste actif. C'est le comportement attendu pour les formulaires où la valeur doit appartenir à une liste prédéfinie — identique à ce que fait Spinbox en mode readonly, mais avec un menu déroulant plutôt que des flèches.
Réagir à la sélection avec StringVar et bind
Deux façons de détecter un changement : lier le Combobox à une StringVar, ou utiliser l'événement <<ComboboxSelected>> via bind() :
import tkinter as tk
from tkinter import ttk
capitales = {
"France": "Paris",
"Espagne": "Madrid",
"Italie": "Rome",
"Maroc": "Rabat",
"Allemagne":"Berlin",
}
fenetre = tk.Tk()
fenetre.title("Combobox avec événement")
fenetre.geometry("320x160")
tk.Label(fenetre, text="Pays :").pack(pady=(20, 4))
combo = ttk.Combobox(fenetre, values=list(capitales.keys()),
state="readonly", width=20)
combo.pack()
label_cap = tk.Label(fenetre, text="Sélectionnez un pays", fg="#555")
label_cap.pack(pady=12)
def sur_selection(event):
pays = combo.get()
label_cap.config(text=f"Capitale : {capitales[pays]}")
# <> est déclenché à chaque sélection dans la liste
combo.bind("<>", sur_selection)
fenetre.mainloop()
L'événement virtuel <<ComboboxSelected>> ne se déclenche que quand l'utilisateur choisit un élément dans le menu déroulant — pas quand on appelle combo.set() ou combo.current() par programme. Si vous avez besoin de détecter les deux cas, trace_add sur une StringVar liée avec textvariable est plus fiable.
Pour les listes très longues où la navigation par menu déroulant devient pénible, une Listbox avec champ de filtrage est plus ergonomique.
Par carabde | Mis à jour le 30 avril 2025