Forcer les cochage des pères dans une Treeview quand les fils sont cohés

Signaler
Messages postés
32
Date d'inscription
jeudi 10 mai 2007
Statut
Membre
Dernière intervention
27 janvier 2013
-
Messages postés
17286
Date d'inscription
mercredi 2 janvier 2002
Statut
Modérateur
Dernière intervention
23 décembre 2019
-
Salut à tous,
je cherche 2 fonctions pour ma treeview avec checkbox, avec une urgence pour la première :

1) J'aimerai que quand un noeud fils est coché dans le treeview, ses pères soient eux-aussi obligatoirement cochés.

2) Je voudrai aussi que quand la totalité des fils d'un treeview ne sont pas cochés, la checkbox du père est "coché grisée". Et quand la totalité des fils sont cochés, la checkbox du père est "cohée blanche".

Autant on trouve facilement des fonctions pour cocher automatiquement les enfants, autant je n'arrive vraiment pas a trouver de fonction pour forcer le cochage des noeuds parents quand un ou plusieurs des enfants sont cochées, pouvez-vous maider ?

Merci d'avance !

<!-- / message -->
<!-- edit note -->
A voir également:

30 réponses

Messages postés
17286
Date d'inscription
mercredi 2 janvier 2002
Statut
Modérateur
Dernière intervention
23 décembre 2019
69
1/
Private Sub TreeView1_NodeCheck(ByVal Node As MSComctlLib.Node)
If Not Nothing Is Node.Parent And Node.Checked Then
Node.Parent.Checked = True
End If
End Sub

pour le choché grisé faut passer par d'autres biais....
Messages postés
7393
Date d'inscription
mercredi 23 avril 2003
Statut
Membre
Dernière intervention
6 avril 2012
56
Salut,

1- dans l'événement NodeCheck Appelle une procédure récursive qui utilise ceci : Node.Parent.Checked = True

2- Il te suffit pour une node donnée, de compté le nombre d'enfant coché et de coché ou décoché le node en fonction non?

@+: Ju£i?n
Pensez: Réponse acceptée
Messages postés
7393
Date d'inscription
mercredi 23 avril 2003
Statut
Membre
Dernière intervention
6 avril 2012
56
Re,[auteur/RENFIELD/2359.aspx ]

> [auteur/RENFIELD/2359.aspx Renfield]:('lut) OUILLE OUILLE 11 minutes (de pire en pire)... bah je ferais miueux de faire des refresh après avoir testé des codes....

@+: Ju£i?n
Pensez: Réponse acceptée
Messages postés
32
Date d'inscription
jeudi 10 mai 2007
Statut
Membre
Dernière intervention
27 janvier 2013

Salut et merci !


J'obtiens maintenant le message d'erreur : "L'expression MouseMove entrée comme paramètre de lapropriété de type évènement est à l'origine d'une erreur. La déclaration de la procédure ne corespond pas à la déscription de l'évènement ou de la procédure du même nom."


Autre question qui a peut-ete un rapport : comment voir la treeview au lancement du formulaire ? (je n'ai pas trouvé pour l'instant du coup je l'affiche avec un clique sur un bouton )

Merci d'avance
Messages postés
17286
Date d'inscription
mercredi 2 janvier 2002
Statut
Modérateur
Dernière intervention
23 décembre 2019
69
MouseMove ???

où as tu mis MouseMove, je ne le vois nulle part dans le code qui t'a été proposé.

comment voir le treeview ? ben, en le mettant sa proprété Visible à True....
si la question était en fait "Quel evenement utiliser pour remplir le treeview au chargement de la UserForm ?"
la réponse est alors UserForm_Activate
Messages postés
7393
Date d'inscription
mercredi 23 avril 2003
Statut
Membre
Dernière intervention
6 avril 2012
56
Re,

Pourrait on voir le code que tu utilises?

Tu as du modifier le code et modifier les parametres d'une procédure évènementielle (pas le droit)

Pour "voir" la treeview il suffit de mettre sa propriété Visible à True en mode design ou au chragement du formulaire (événeemnt Form_Load)

@+: Ju£i?n
Pensez: Réponse acceptée
Messages postés
17286
Date d'inscription
mercredi 2 janvier 2002
Statut
Modérateur
Dernière intervention
23 décembre 2019
69
13 secondes.... nette amélioration :p
Messages postés
7393
Date d'inscription
mercredi 23 avril 2003
Statut
Membre
Dernière intervention
6 avril 2012
56
Re,
t'as vu... c'est le jour et la nuit.

@+: Ju£i?n
Pensez: Réponse acceptée
Messages postés
32
Date d'inscription
jeudi 10 mai 2007
Statut
Membre
Dernière intervention
27 janvier 2013

Bon, ça à marché 2 seconde (j'ai crée ma treeview dans le form_load plutot que dans un click) et maintenant c'est la catastrophe il y a des messages d'erreur de partout comme celui que je vous ai écri ci-dessou sauf qu'il y a aussi la même chose avec l'expression "Sur Chargement" quand je démarre, "mousedown", "mouseup", "click entrée" quand je clique sur la treeview...et la treeview n'affiche biensur plus rien
Votre code marche sous excel avec les macro mais moi je suis sous ACCESS.
Dans mon code c'est simple il n'y a rien : crétion de la treeview dans le form_load et ensuite vote code.
Merci d'avance !
Messages postés
32
Date d'inscription
jeudi 10 mai 2007
Statut
Membre
Dernière intervention
27 janvier 2013

Bon ca marche, j'ai remplacé votre fonction :

'Private Sub TreeView1_NodeCheck(ByVal Node As MSComctlLib.Node)


'    If Not Nothing Is Node.Parent And Node.Checked Then
'        Node.Parent.Checked = True
'    End If
    
'End Sub


par :

Private Sub Treeview1_NodeCheck(ByVal Node As Object)
If Not Nothing Is Node.Parent And Node.Checked Then
        Node.Parent.Checked = True
End If
End Sub


OUF ! Merci !

Sinon, pouvez-vous m'aider à optimiser ce code sur 2 aspects :
- je voudrai aussi cocher le grand-père automatiquement (ma treeview est sur 3 niveaux
- je voudrai interdir la possiblité de décocher les cases père et grand-père lorqu'un fils est coché.


Merci d'avance !
Messages postés
17286
Date d'inscription
mercredi 2 janvier 2002
Statut
Modérateur
Dernière intervention
23 décembre 2019
69
aïe, je pensais que le Treeview était mieux concu, et qu'il déclencherai l'evenement NodeCheck pour tous les noeuds cochés, et remonterait mécaniquement dans l'arborescence....

pas de panique, je vois :

Private Sub TreeView1_NodeCheck(ByVal Node As Node)
Do While Not Nothing Is Node.Parent And Node.Checked
Node.Parent.Checked = True
Set Node = Node.Parent
Loop
End Sub

pour le reste, l'algorythem parait fort simple :

Private Sub TreeView1_NodeCheck(ByVal Node As Node)
Dim oChild As Node
'# On a demandé à cocher un noeud...
If Node.Checked Then
'# On coche les ancètres
Do While Not Nothing Is Node.Parent
Node.Parent.Checked = True
Set Node = Node.Parent
Loop
ElseIf Node.Children Then
'# Tentative de décochage d'un noeud qui a des noeuds fils...
'# On récupère le premier de ses fils...
Set oChild = Node.Child
Do
'# S'il est coché...
If oChild.Checked Then
'# On recoche le noeud
Node.Checked = True
'# Et on sort de la boucle
Exit Do
End If
'# Sinon, on prend le noeud suivant
Set oChild = oChild.Next
'# enfin, tant qu'il y en a...
Loop Until Nothing Is oChild
End If
TreeView1.Refresh
End Sub
Messages postés
17286
Date d'inscription
mercredi 2 janvier 2002
Statut
Modérateur
Dernière intervention
23 décembre 2019
69
j'ai employé "parait" car en réalité, ce code ne fonctionne pas. l'algo est bon, mais le treeview redécoche la case, en réalité...
le treeview est mal concu et fait, en gros :


bCoché = Node.Checked
Raiseevent NodeCheck (Node)
Node.Checked = bCoché

donc, c'est cool, il faut lui forcer la main
Messages postés
32
Date d'inscription
jeudi 10 mai 2007
Statut
Membre
Dernière intervention
27 janvier 2013

Ok j'ai réalisé ce code qui fonctionne :

Private Sub Treeview1_NodeCheck(ByVal Node As Object)
If Not Nothing Is Node.Parent And Node.Checked Then
        If Not Nothing Is Node.Parent.Parent And Node.Checked Then
            Node.Parent.Parent.Checked = True
        End If
        Node.Parent.Checked = True
End If
End Sub

Par contre je n'arrive pas à interdir le décochage, quelqu'un a une piste ?
Messages postés
17286
Date d'inscription
mercredi 2 janvier 2002
Statut
Modérateur
Dernière intervention
23 décembre 2019
69
si tu as un jour davantage de niveaux, ce sera ingérable, sans boucle :

If Not Nothing Is Node.Parent And Node.Checked Then
If Not Nothing Is Node.Parent.Parent And Node.Checked Then
If Not Nothing Is Node.Parent.Parent.Parent And Node.Checked Then
If Not Nothing Is Node.Parent.Parent.Parent.Parent And Node.Checked Then
If Not Nothing Is Node.Parent.Parent.Parent.Parent.Parent And Node.Checked Then
Node.Parent.Parent.Parent.Parent.Parent.Checked = True
End If
Node.Parent.Parent.Parent.Parent.Checked = True
End If
Node.Parent.Parent.Parent.Checked = True
End If
Node.Parent.Parent.Checked = True
End If
Node.Parent.Checked = True
End If
Messages postés
17286
Date d'inscription
mercredi 2 janvier 2002
Statut
Modérateur
Dernière intervention
23 décembre 2019
69
enfin, on pourrais simplifier, hein ^^ (pas bon: toujours pas de boucle)

If Not Nothing Is Node.Parent And Node.Checked Then
If Not Nothing Is Node.Parent.Parent Then
If Not Nothing Is Node.Parent.Parent.Parent Then
If Not Nothing Is Node.Parent.Parent.Parent.Parent Then
If Not Nothing Is Node.Parent.Parent.Parent.Parent.Parent Then
Node.Parent.Parent.Parent.Parent.Parent.Checked = True
End If
Node.Parent.Parent.Parent.Parent.Checked = True
End If
Node.Parent.Parent.Parent.Checked = True
End If
Node.Parent.Parent.Checked = True
End If
Node.Parent.Checked = True
End If
Messages postés
32
Date d'inscription
jeudi 10 mai 2007
Statut
Membre
Dernière intervention
27 janvier 2013

Merci Renfield, je n'avais pas actualisé assez tôt moi non plus
Concernant l'interdiction de décochage, des suggestions ?
Messages postés
7393
Date d'inscription
mercredi 23 avril 2003
Statut
Membre
Dernière intervention
6 avril 2012
56
Re,
bah ca à été traité l'interdiction de décochage => il faut lui forcer la main

@+: Ju£i?n
Pensez: Réponse acceptée
Messages postés
32
Date d'inscription
jeudi 10 mai 2007
Statut
Membre
Dernière intervention
27 janvier 2013

Je ne pige pas, que veux-tu dire par forcer la main ?
Pour l'instant j'ai recopié ton code :

Dim oChild As Node
    If Node.Checked Then
        Do While Not Nothing Is Node.Parent
            Node.Parent.Checked = True
            Set Node = Node.Parent
        Loop

    ElseIf Node.Children Then
        Set oChild = Node.Child
        Do
            If oChild.Checked Then
                Node.Checked = True
                Exit Do
            End If
            Set oChild = oChild.Next
 
        Loop Until Nothing Is oChild
    End If
    Treeview1.Refresh
End Sub

..et je peux toujuors décocher
Messages postés
17286
Date d'inscription
mercredi 2 janvier 2002
Statut
Modérateur
Dernière intervention
23 décembre 2019
69
tu pourras pas dire que je ne te l'avais pas dit, pourtant...
Messages postés
32
Date d'inscription
jeudi 10 mai 2007
Statut
Membre
Dernière intervention
27 janvier 2013

Oui justement je ne comprend pas ce que tu as expliqué apres :

bCoché = Node.Checked

Raiseevent NodeCheck (Node)

Node.Checked = bCoché

??