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

Python Discussion :

Glisser-déposer entre deux treeview tkinter


Sujet :

Python

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre confirmé
    Homme Profil pro
    Inscrit en
    Février 2013
    Messages
    55
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Février 2013
    Messages : 55
    Par défaut Glisser-déposer entre deux treeview tkinter
    Bonjour à tous,

    Je recherche un moyen d'effectuer un drag and drop entre 2 treeview
    Je trouve des tutos pour le faire à l’intérieur d’un treeview mais pas entre deux diffèrent





    Merci d’avance


    J'utilise ce code pour mes tests.

    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
     
    from tkinter import *
    from tkinter import ttk
     
    def bDown_Shift(event):
        tv = event.widget
        select = [tv.index(s) for s in tv.selection()]
        select.append(tv.index(tv.identify_row(event.y)))
        select.sort()
        for i in range(select[0],select[-1]+1,1):
            tv.selection_add(tv.get_children()[i])
     
    def bDown(event):
        tv = event.widget
     
        if tv.identify_row(event.y) not in tv.selection():
            tv.selection_set(tv.identify_row(event.y))
     
    def bUp(event):
        tv = event.widget
        if tv.identify_row(event.y) in tv.selection():
            tv.selection_set(tv.identify_row(event.y))
     
    def bUp_Shift(event):
        pass
     
    def bMove(event):
        tv = event.widget
        print(tv)
        moveto = tv.index(tv.identify_row(event.y))
        for s in tv.selection():
            tv.move(s, '', moveto)
     
    root = Tk()
     
    tree = ttk.Treeview(columns=("col1","col2"),
                        displaycolumns="col2",
                        selectmode='none')
     
    # insert some items into the tree
    for i in range(10):
        tree.insert('', 'end',iid='line%i' % i, text='line:%s' % i, values=('', i))
     
    tree2 = ttk.Treeview (columns=("col1", "col2"),
                         displaycolumns="col2",
                         selectmode='none')
     
    # insert some items into the tree
    for i in range (10) :
        tree2.insert ('', 'end', iid='line%i' % i, text='line:%s' % i, values=('', i))
     
     
     
     
     
    tree.pack()
    tree2.pack()
     
    tree.bind("<ButtonPress-1>",bDown)
    tree.bind("<ButtonRelease-1>",bUp, add='+')
    tree.bind("<B1-Motion>",bMove, add='+')
     
    tree.bind("<Shift-ButtonPress-1>",bDown_Shift, add='+')
    tree.bind("<Shift-ButtonRelease-1>",bUp_Shift, add='+')
     
     
    tree2.bind("<ButtonPress-1>",bDown)
    tree2.bind("<ButtonRelease-1>",bUp, add='+')
    tree2.bind("<B1-Motion>",bMove, add='+')
     
     
    tree2.bind("<Shift-ButtonPress-1>",bDown_Shift, add='+')
    tree2.bind("<Shift-ButtonRelease-1>",bUp_Shift, add='+')
     
     
     
    root.mainloop()

  2. #2
    Expert éminent
    Homme Profil pro
    Architecte technique retraité
    Inscrit en
    Juin 2008
    Messages
    21 738
    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 738
    Par défaut
    Salut,

    Vous avez un module de tkinter qui fournit une base "adaptable" modulo avoir passé du temps à comprendre comment ça fonctionne et avoir appris à l'utiliser.

    Après si vous voulez coder une solution originale, il y a un gros travail de conception à faire car il faut faire "avec" tkinter (et bien le maîtriser).

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

  3. #3
    Expert confirmé
    Avatar de jurassic pork
    Homme Profil pro
    Bidouilleur
    Inscrit en
    Décembre 2008
    Messages
    4 211
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Bidouilleur
    Secteur : Industrie

    Informations forums :
    Inscription : Décembre 2008
    Messages : 4 211
    Par défaut
    hello,
    vad92, dans le code que tu as mis c'est un "faux" drag n drop qui n'utilise pas le mécanisme de drag n drop. Comme l'indique Wiztrick dans tkinter pour faire un "vrai" drag and drop il faut installer un module de tkinter tkdnd. Voici le genre de chose que l'on pourrait faire :

    Nom : pytkdnd2.gif
Affichages : 1049
Taille : 32,1 Ko

    Mais ce n'est pas si simple que cela à gérer surtout pour un treeview.

    Ami calmant, J.P

  4. #4
    Expert éminent
    Homme Profil pro
    Architecte technique retraité
    Inscrit en
    Juin 2008
    Messages
    21 738
    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 738
    Par défaut
    Citation Envoyé par jurassic pork Voir le message
    il faut installer un module de tkinter tkdnd.
    Il n'y a rien à installer: c'est en standard depuis la version 3.9.

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

  5. #5
    Membre confirmé
    Homme Profil pro
    Inscrit en
    Février 2013
    Messages
    55
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Février 2013
    Messages : 55
    Par défaut
    Bonjour,
    Merci pour vos réponses, l’exemple de jurassic pork est exactement ce que je recherche, si tu un code exemple qui va avec ça serai top,
    dans tous les cas je me lance dans l'apprentissage dans ce module tkdnd

    Merci Encore

  6. #6
    Expert confirmé
    Avatar de jurassic pork
    Homme Profil pro
    Bidouilleur
    Inscrit en
    Décembre 2008
    Messages
    4 211
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Bidouilleur
    Secteur : Industrie

    Informations forums :
    Inscription : Décembre 2008
    Messages : 4 211
    Par défaut
    hello,
    Citation Envoyé par wiztricks Voir le message
    Il n'y a rien à installer: c'est en standard depuis la version 3.9.

    - W
    Il me semble que ce dnd n'est toujours pas un Dnd natif à l'O.S (pas possible de l'utiliser avec une autre application que tkinter). Wiztricks peux-tu nous montrer comment tu transfères un élément d'un treeview vers un autre treeview avec le dnd de tkinter présent depuis la 3.9 ?


    Vader, En attendant la réponse de wiztricks voici mon code qui utilise le module tkinterdnd2 (présent dans Pypi). Attention le paquet ne contient que les binaires pour les versions python 64 bits de linux, windows, macOSX. Pour les versions python 32 bits, il y a quelques manipulations à faire et fichiers à récupérer.
    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
    # Démo DnD entre 2 Treeviews Tkinter J.P Février 2022
    from tkinter import ttk
    from tkinterdnd2 import *
    import json
     
     
    def drop_enter(event):
        event.widget.focus_force()
        #print('On entre dans la zone :  %s' % event.widget)
        return event.action
     
     
    def drop_position(event):
        #print('Position: x %d, y %d' %(event.x_root, event.y_root))
        return event.action
     
     
    def drop_leave(event):
        #print('On quitte %s' % event.widget)
        return event.action
     
     
    def drop(event):
        if event.data:
            #print(event.data)
            # conversion des data en format json
            json_string = event.data.replace("'", "\"")
            # conversion json en dictionnaire
            dict = json.loads(json_string)
            print(dict["text"])
        tv = event.widget
        tv.insert('', 'end', iid=dict['text'], text=dict['text'], values=dict['values'])
        return event.action
     
     
    def drag_init(event):
        tv = event.widget
        curItem = tv.focus()
        print(tv.item(curItem))
        data = tv.item(curItem)
        return (COPY, DND_TEXT, data)
     
     
    #Créer une liste de fruits
    f_name=['Pommes','Poires','Bananes','Prunes','Oranges','Pêches','Abricots','Kiwis']
    #Créer une liste de prix de fruits
    f_price_num=[2.24,3.31,1.69,3.78,2.05,3.69,4.20,3.53]
    #Créer une liste de numéros de séquence
    f_list=[1,2,3,4,5,6,7,8]
     
     
    root = TkinterDnD.Tk()
    style = ttk.Style(root)
    # utilisation du thème "clam" qui supporte l'option fieldbackground
    style.theme_use("clam")
    style.configure('Treeview.Heading', background="white")
    style.configure("Treeview",
                    background="#E8FFFF",
                    foreground="black",
                    rowheight=25,
                    fieldbackground="silver",
                    )
    style.map('Treeview', background=[('selected', 'blue')])
    #Créer un tableau
    columns=("Fruit","Prix","Numéro")
    tree=ttk.Treeview(height=10,show="headings",columns=columns)
    tree.heading("Fruit",text="Fruit") # Afficher l'en - tête
    tree.heading("Prix",text="Prix")
    tree.heading("Numéro",text="Numéro")
    #Définir la largeur
    tree.column("Fruit", width=130, anchor='center')
    tree.column("Prix", width=100, anchor='center')
    tree.column("Numéro", width=100, anchor='center')
    # Insérer des données de fonction avec couleur alternée par ligne
    tree.tag_configure('paire', background="#FFFFFF")
    tree.tag_configure('impaire', background="#E8FFFF")
    for i in range(min(len(f_name),len(f_price_num),len(f_list))):
        motag = 'paire' if i%2 else  'impaire'
        tree.insert('',i,text=f_name[i],values=(f_name[i],f_price_num[i],f_list[i]),tags = (motag,))
     
     
    # deuxième treeview vide
    tree2=ttk.Treeview(height=10,show="headings",columns=columns)
    tree2.heading("Fruit",text="Fruit") # Afficher l'en - tête
    tree2.heading("Prix",text="Prix")
    tree2.heading("Numéro",text="Numéro")
    #Définir la largeur
    tree2.column("Fruit", width=130, anchor='center')
    tree2.column("Prix", width=100, anchor='center')
    tree2.column("Numéro", width=100, anchor='center')
     
     
    tree.pack()
    tree2.pack()
     
     
    # gestion des événements
    tree.drag_source_register(DND_TEXT)
    tree.dnd_bind('<<DragInitCmd>>', drag_init)
     
     
    tree2.drop_target_register(DND_TEXT)
    tree2.dnd_bind('<<DropEnter>>', drop_enter)
    tree2.dnd_bind('<<DropPosition>>', drop_position)
    tree2.dnd_bind('<<DropLeave>>', drop_leave)
    tree2.dnd_bind('<<Drop>>', drop)
     
     
    root.mainloop()
    Nom : tkdnd2.gif
Affichages : 994
Taille : 42,9 Ko



    Comme on ne peut apparemment pas transférer d'objets python par ce drag and drop mais une chaine, j'ai utilisé la représentation chaine des éléments du treeview pour faire le transfert. A la réception, je convertis cette chaine en objet json et je convertis le json en dictionnaire. Si quelqu'un a une idée plus simple pour faire le transfert ?


    Sinon, il y a aussi possibilité d'utiliser comme interface graphique pyqt au lieu de tkinter car le drag and drop fonctionne complétement sous qt.


    Ami calmant, J.P

  7. #7
    Expert éminent
    Homme Profil pro
    Architecte technique retraité
    Inscrit en
    Juin 2008
    Messages
    21 738
    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 738
    Par défaut
    Citation Envoyé par jurassic pork Voir le message
    Il me semble que ce dnd n'est toujours pas un Dnd natif à l'O.S (pas possible de l'utiliser avec une autre application que tkinter).
    Certes mais le sujet était entre Treeview.

    Citation Envoyé par jurassic pork Voir le message
    Wiztricks peux-tu nous montrer comment tu transfères un élément d'un treeview vers un autre treeview avec le dnd de tkinter présent depuis la 3.9 ?
    Si j'ai du temps, je dois pouvoir repartir de codes que j'ai, mais ce ne sera pas avant la fin de la semaine prochaine, désolé.


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

Discussions similaires

  1. Glisser-déposer entre deux QTableWidget
    Par ApproxDev dans le forum Qt
    Réponses: 2
    Dernier message: 12/10/2015, 09h41
  2. Glisser-déposer entre deux QTreeView
    Par sfarc dans le forum Débuter
    Réponses: 21
    Dernier message: 16/05/2012, 10h59
  3. Glisser-déposer entre deux zones de listes
    Par Arkham46 dans le forum Contribuez
    Réponses: 2
    Dernier message: 13/04/2012, 12h20
  4. Réponses: 1
    Dernier message: 16/09/2011, 17h28
  5. Transfert de données entre deux treeview
    Par stefsas dans le forum ASP.NET
    Réponses: 0
    Dernier message: 05/07/2010, 16h21

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