IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Tkinter Python Discussion :

création d'une fenêtre modale


Sujet :

Tkinter Python

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre éprouvé
    Profil pro
    Inscrit en
    Février 2003
    Messages
    926
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2003
    Messages : 926
    Par défaut création d'une fenêtre modale
    Bonjour, je cherche à créer une fenêtre modale qui apparait lorsqu'on clique sur le bouton droit de la souris. Je veux réaliser quelque chose du genre :

    Nom : modal.png
Affichages : 2877
Taille : 34,1 Ko

    Pour l'instant, mon code est le suivant :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    92
    93
    94
    95
    96
    97
    98
    99
    100
    101
    102
    103
    104
    105
    106
    107
    108
    109
    110
    111
    112
    113
    114
    115
    116
    117
    118
    119
    120
    121
    122
    123
    124
    125
    126
    127
    128
    129
    130
    131
    132
    133
    134
    135
    136
    137
    138
    139
    140
    141
    142
    143
    144
    145
    146
    147
    148
    149
    150
    151
    152
    153
    154
    155
     
    from tkinter import *
    from PIL import Image, ImageTk
    from tkinter import filedialog, ttk
    from tkinter.filedialog import askopenfile
    import os
    from os.path import basename
     
    class AutoScrollbar(Scrollbar):
        # a scrollbar that hides itself if it's not needed.  only
        # works if you use the grid geometry manager.
        def set(self, lo, hi):
            if float(lo) <= 0.0 and float(hi) >= 1.0:
                self.grid_remove()
            else:
                self.grid()
            Scrollbar.set(self, lo, hi)
        def pack(self, **kw):
            raise TclError ("cannot use pack with this widget")
        def place(self, **kw):
            raise TclError ("cannot use place with this widget")
     
    def openFile():
        global filename
        file = askopenfile(parent=root,title='Select a File')
        filename = file.name
        t = file.read()
     
        #print(nb.index('current'))
     
        basename(filename)
     
        frame1 = create_frame(nb, t)
        nb.add(frame1, text=basename(filename))
        tbox1 = Text(frame1, wrap=WORD)    
        #print(tbox1)
        print(nb.index(frame1))
        #print(nb.select(nb.index("current")))
     
        nb.select(nb.index(frame1))
     
        file.close()
     
    def callback():
        frame.focus_set()
        print ("clicked at", event.x, event.y)
     
    def create_frame(master, t):
        frame = Frame(master, bd=2, relief=SUNKEN)
        yscrollbar = AutoScrollbar(frame)
        yscrollbar.grid(row=0, column=1, sticky=N+S)
        text = Text(frame, 
                    yscrollcommand=yscrollbar.set, background="beige")
     
        #print ("Mon Onglet : "+str(text))
     
        text.grid(row=0, column=0, sticky='nwse') # expansion du widget Text
     
        frame.grid_columnconfigure(0, weight=1) # expansion de la colonne
        frame.grid_rowconfigure(0, weight=1) # expansion de la colonne
     
        text.insert(0.0, t)
     
        #print(text.grid)
     
        return frame
     
     
    if __name__ == '__main__':
        root = Tk()
     
        root.title("MonkeyCode Editor")
     
        menubar = Menu(root)
        filemenu = Menu(menubar)
        EditMenu = Menu(menubar)
     
        filemenu.add_command(label="Ouvrir", command=openFile)
        menubar.add_cascade(label="Fichier", menu=filemenu)
     
     
        EditMenu.add_command(label="Couper", \
                         accelerator="Ctrl+X", \
                         command=lambda: \
                                 root.focus_get().event_generate('<<Cut>>'))
     
        EditMenu.add_command(label="Copier", \
                         accelerator="Ctrl+C", \
                         command=lambda: \
                                 root.focus_get().event_generate('<<Copy>>'))
     
        EditMenu.add_command(label="Coller", \
                             accelerator="Ctrl+V", \
                             command=lambda: \
                                     root.focus_get().event_generate('<<Paste>>'))
     
        menubar.add_cascade(label="Édition",menu=EditMenu)
     
        root.config(menu=menubar)   
     
        nb = ttk.Notebook(root)    
     
        root.update()
     
        def fonc3(event):
     
     
            cadre = Frame(root, width =200, height =150, bg="yellow")
            #cadre.pack()
            #chaine = Label(cadre, text = "VIDE")
            #chaine.pack()
     
     
            #cadre = Frame(root, bg='green', width=300, height=200)
            cadre.pack(fill=X, expand=Y)
            #cadre.grid_propagate(0)
            cadre.rowconfigure(0, weight=1)
            cadre.columnconfigure(0, weight=1)
            Label(cadre, text='Couper').grid(row=1, column=0, sticky='nesw')
            Label(cadre, text='Copier').grid(row=2, column=1, sticky='ne')
            Label(cadre, text='Coller').grid(row=3, column=1)
     
            modale = TopLevel()
            fermer = Button(modale, text="Fermer", command=modale.destroy)
            fermer.pack()
     
     
        def fonc2(event):
            print("Molette")
     
     
        def fonc1(event):
            print("Bouton gauche")
     
        cadre = Frame(root, width =200, height =150, bg="yellow")
     
        root.bind("<Button-1>", fonc1)
        root.bind("<Button-2>", fonc2)
        root.bind("<Button-3>", fonc3)
     
        #frame1 = create_frame(nb)
        #nb.add(frame1, text="Text1")
        #tbox1 = Text(frame1, wrap=WORD)    
        #print(tbox1)
     
        t=""
     
        frame2 = create_frame(nb, t)
        nb.add(frame2, text="new 1")
        tbox2 = Text(frame2, wrap=WORD)
        print(tbox2)  
     
        nb.pack(expand=YES, fill=BOTH)
     
        mainloop()
    Lorsqu'on clique sur le bouton droit, la fenêtre qui apparaît n''est pas modale. C'est ce problème que je veux résoudre en priorité.
    Auriez-vous une solution à me proposer, svp?
    Je vous en remercie d'avance.
    Arsène

  2. #2
    Expert éminent
    Homme Profil pro
    Architecte technique retraité
    Inscrit en
    Juin 2008
    Messages
    21 741
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Manche (Basse Normandie)

    Informations professionnelles :
    Activité : Architecte technique retraité
    Secteur : Industrie

    Informations forums :
    Inscription : Juin 2008
    Messages : 21 741
    Par défaut
    Salut,

    Citation Envoyé par Arsene12 Voir le message
    Lorsqu'on clique sur le bouton droit, la fenêtre qui apparaît n''est pas modale. C'est ce problème que je veux résoudre en priorité.
    Auriez-vous une solution à me proposer, svp?
    Et si vous commenciez par chercher un peu sur Internet? Vous auriez trouvé le petit tuto. d'effbot sur le sujet qui, comme pour la Scrollbar, est un bon point de départ.

    - W
    Architectures post-modernes.
    Python sur DVP c'est aussi des FAQs, des cours et tutoriels

  3. #3
    Membre éprouvé
    Profil pro
    Inscrit en
    Février 2003
    Messages
    926
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2003
    Messages : 926
    Par défaut
    Merci pour ce lien. En réfléchissant je me suis dis que c'est peut-être pas une fenêtre modale qu'il me faut car je veux pas qu'elle ait de bordure ni une croix en haut à droite.
    J'ai vu un autre lien : coursPython. Ça doit être un peu compliqué à réaliser. Je vais devoir installer un binding, je crois que c'est comme ça que ça s'appelle : PyQt5 ou PyQt4. J'ai téléchargé le fichier PyQt5-5.10.1-5.10.1-cp35.cp36.cp37.cp38-none-win_amd64 mais je sais pas encore comment l'installer.
    Je viens aussi de voir un sujet intéressante dans le forum d'ici : fenêtre sans bord
    Je vais l'étudier car je crois que ce que je veux faire, c'est peut-être ça, avec une fenêtre Toplevel.

  4. #4
    Expert éminent
    Homme Profil pro
    Architecte technique retraité
    Inscrit en
    Juin 2008
    Messages
    21 741
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Manche (Basse Normandie)

    Informations professionnelles :
    Activité : Architecte technique retraité
    Secteur : Industrie

    Informations forums :
    Inscription : Juin 2008
    Messages : 21 741
    Par défaut
    Citation Envoyé par Arsene12 Voir le message
    Je vais l'étudier car je crois que ce que je veux faire, c'est peut-être ça, avec une fenêtre Toplevel.
    Ah ben si vous ne savez pas trop exprimer ce que vous voulez (une interface graphique c'est tout un vocabulaire!) pas facile de savoir quoi coder avec tkinter et c'est pas changer de GUI qui vous aidera.

    - W
    Architectures post-modernes.
    Python sur DVP c'est aussi des FAQs, des cours et tutoriels

  5. #5
    Membre éprouvé
    Profil pro
    Inscrit en
    Février 2003
    Messages
    926
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2003
    Messages : 926
    Par défaut
    J'ai installé PyQt5-5 et utilisé top.overrideredirect(1). Tout a bien marché. J'ai maintenant une fenêtre sans bord qui ressemble à celle que je voulais faire. Elle contient des labels et il me reste à régler un dernier point :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    L1=Label(top, text='Couper', activebackground="blue").grid(row=1, column=0, padx=20, sticky='w')
    Lorsque je survole mon label, la couleur de fond reste la même (activebackground="blue" ne marche pas).

    ça ne marche pas non plus si je met un bouton à la place du label. Auriez-vous une idée pour régler ce problème svp?

    Je vous donne le code :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    92
    93
    94
    95
    96
    97
    98
    99
    100
    101
    102
    103
    104
    105
    106
    107
    108
    109
    110
    111
    112
    113
    114
    115
    116
    117
    118
    119
    120
    121
    122
    123
    124
    125
    126
    127
    128
    129
    130
    131
    132
    133
    134
    135
    136
    137
    138
    139
    140
    141
    142
    143
    144
    145
    146
    147
    148
    149
    150
    151
    152
    153
    154
    155
     
    from tkinter import *
    from PIL import Image, ImageTk
    from tkinter import filedialog, ttk
    from tkinter.filedialog import askopenfile
    import os
    from os.path import basename
     
    varGlobal = 0
     
    class AutoScrollbar(Scrollbar):
        # a scrollbar that hides itself if it's not needed.  only
        # works if you use the grid geometry manager.
        def set(self, lo, hi):
            if float(lo) <= 0.0 and float(hi) >= 1.0:
                self.grid_remove()
            else:
                self.grid()
            Scrollbar.set(self, lo, hi)
        def pack(self, **kw):
            raise TclError ("cannot use pack with this widget")
        def place(self, **kw):
            raise TclError ("cannot use place with this widget")
     
    def openFile():
        global filename
        file = askopenfile(parent=root,title='Select a File')
        filename = file.name
        t = file.read()
     
        #print(nb.index('current'))
     
        basename(filename)
     
        frame1 = create_frame(nb, t)
        nb.add(frame1, text=basename(filename))
        tbox1 = Text(frame1, wrap=WORD)    
        #print(tbox1)
        #print(nb.index(frame1))
        #print(nb.select(nb.index("current")))
     
        nb.select(nb.index(frame1))
     
        file.close()
     
    def callback():
        frame.focus_set()
        print ("clicked at", event.x, event.y)
     
    def create_frame(master, t):
        frame = Frame(master, bd=2, relief=SUNKEN)
        yscrollbar = AutoScrollbar(frame)
        yscrollbar.grid(row=0, column=1, sticky=N+S)
        text = Text(frame, 
                    yscrollcommand=yscrollbar.set, background="beige")
     
        #print ("Mon Onglet : "+str(text))
     
        text.grid(row=0, column=0, sticky='nwse') # expansion du widget Text
     
        frame.grid_columnconfigure(0, weight=1) # expansion de la colonne
        frame.grid_rowconfigure(0, weight=1) # expansion de la colonne
     
        text.insert(0.0, t)
        #print(text.grid) 
        return frame
     
    if __name__ == '__main__':
        root = Tk()
     
        root.title("MonkeyCode Editor")    
     
        menubar = Menu(root)
        filemenu = Menu(menubar)
        EditMenu = Menu(menubar)
     
        filemenu.add_command(label="Ouvrir", command=openFile)
        menubar.add_cascade(label="Fichier", menu=filemenu)    
     
        EditMenu.add_command(label="Couper", \
                         accelerator="Ctrl+X", \
                         command=lambda: \
                                 root.focus_get().event_generate('<<Cut>>'))
     
        EditMenu.add_command(label="Copier", \
                         accelerator="Ctrl+C", \
                         command=lambda: \
                                 root.focus_get().event_generate('<<Copy>>'))
     
        EditMenu.add_command(label="Coller", \
                             accelerator="Ctrl+V", \
                             command=lambda: \
                                     root.focus_get().event_generate('<<Paste>>'))
     
        menubar.add_cascade(label="Édition",menu=EditMenu)
        root.config(menu=menubar)    
        nb = ttk.Notebook(root)    
     
        root.update()
     
        def ferme():
            global varGlobal
            for widget in root.winfo_children():
                if isinstance(widget,Toplevel):
                    widget.destroy()
                    varGlobal = 0
     
        def fonc4(event):
            print ("TOP FENETRE")                
     
        def fonc3(event):
            global varGlobal
            if varGlobal == 0 :
                print ("EXISTE PAS")            
                varGlobal = 1        
                top = Toplevel(root)
                separator = ttk.Separator(top, orient="horizontal")
                top.overrideredirect(1)
                #print(top.geometry(), root.geometry()) # Affiche 1x1+0+0 1x1+0+0
                top.geometry("{}x{}+{}+{}".format(200, 120, 400, 400))
     
                L1=Label(top, text='Couper', activebackground="blue").grid(row=1, column=0, padx=20, sticky='w')
                L2=Label(top, text='Copier', activebackground="blue").grid(row=2, column=0, padx=20, sticky='w')
                L3=Label(top, text='Coller', activebackground="blue").grid(row=3, column=0, padx=20, sticky='w')
                separator.grid(row=4, column=0, sticky="nwse")
                L4=Label(top, text='Rechercher', activebackground="blue").grid(row=5, column=0, padx=20, sticky='w')            
                B1=Button(top, text='Quitter', activebackground="blue", command=ferme).grid(row=6, column=0, padx=20, sticky='w')
     
                top.configure(bd=1, relief=RAISED)
                top.rowconfigure(7, weight=0)
                top.columnconfigure(0, weight=0)
                top.bind("<Button-1>", fonc4)
     
            else :
                print ("EXISTE")            
                ferme() 
     
        #print(top.geometry()) # Affiche 1x1+400+400
     
        def fonc1(event):
            ferme()                  
     
        root.bind("<Button-3>", fonc3)
        root.bind("<Button-1>", fonc1)
     
        t=""
     
        frame2 = create_frame(nb, t)
        nb.add(frame2, text="new 1")
        tbox2 = Text(frame2, wrap=WORD)
        #print(tbox2)  
     
        nb.pack(expand=YES, fill=BOTH)
     
        mainloop()

  6. #6
    Membre très actif

    Homme Profil pro
    Bidouilleur
    Inscrit en
    Avril 2016
    Messages
    721
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Bidouilleur

    Informations forums :
    Inscription : Avril 2016
    Messages : 721
    Billets dans le blog
    1
    Par défaut


    Sur les labels il n'y a aucun événement par défaut reliés à ces actions de survol par la souris et de focus.

    C'est à toi de les définir, un exemple.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    import tkinter as tk
     
    root = tk.Tk()
    root.geometry('200x200')
     
    lbl = tk.Label(
        root,
        text="coucou",
        background="black",
        foreground="white",
        activebackground="yellow",
        activeforeground="red",
        takefocus=1,
        state=tk.NORMAL,
        highlightthickness=2,
        highlightbackground="orange",
        highlightcolor="green",
    )
    lbl.grid()
     
    bt = tk.Button(root, text='bout 2')
    bt.grid()
     
    lbl.bind('<FocusIn>', lambda e: lbl.config(state='active'))
    lbl.bind('<Enter>', lambda e: lbl.config(state='active'))
    lbl.bind('<FocusOut>', lambda e: lbl.config(state='normal'))
    lbl.bind('<Leave>', lambda e: lbl.config(state='normal'))
     
    root.bind('<KeyPress-Tab>', lambda e: print(root.focus_lastfor()))
     
    root.mainloop()
    Évidemment comme tu as plusieurs labels nécessitant d'avoir cette fonctionnalité, il va falloir créer une classe héritant de Label pour gérer ça.

    Mais ça ne serait pas mieux de faire ce que tu souhaites avec un widget menu ? Pour moi ce serait quand même plus approprié de se servir de ce widget.

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. [GTK+ 3] Création d'une fenêtre modale / Modal Dialog
    Par TANITE dans le forum GTK+ avec C & C++
    Réponses: 1
    Dernier message: 13/10/2014, 08h29
  2. Modifier un champ à partir d'une fenêtre modale
    Par ahoyeau dans le forum Général JavaScript
    Réponses: 2
    Dernier message: 08/03/2005, 16h53
  3. Formulaire dans une fenêtre modale
    Par Amnesiak dans le forum Général JavaScript
    Réponses: 8
    Dernier message: 28/02/2005, 14h25
  4. Supprimer la croix dans une fenêtre modale
    Par AnneOlga dans le forum C++Builder
    Réponses: 3
    Dernier message: 15/01/2004, 14h52
  5. Rendre une fenêtre modale non modale
    Par Smortex dans le forum Composants VCL
    Réponses: 2
    Dernier message: 30/03/2003, 17h56

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo