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

Visual C++ Discussion :

Problème dans la gestion du CTreeCtrl


Sujet :

Visual C++

  1. #1
    Membre éclairé Avatar de vanitom
    Profil pro
    Inscrit en
    Juillet 2004
    Messages
    327
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juillet 2004
    Messages : 327
    Par défaut Problème dans la gestion du CTreeCtrl
    Bonjour,

    Je suis en train de me tirer les cheveux sur un problème à la con avec un CTreeCtrl.

    Alors, je suis en train de créer une interface se composant d'un arbre à gauche et d'une liste à droite. Il faut remplir la liste de droite avec certains éléments de l'arbre de gauche.
    Le principe est qu'au moment d'un double clic sur un élément de l'arbre, cet élément passe dans la liste de droite.
    Le principe est tout simple mais j'ai un gros problème technique.

    Le problème apparait lors de la suppression de l'élément sur lequel je viens de double-cliquer. Ce n'est pas un crash mais juste une boite de dialogue qui rend inutilisable le soft.
    Au bout d'un certain nombre de "DeleteItem" ( 2 ou 3 voir même des fois 1 seul ), j'ai le message suivant qui apparait
    User breakpoint called from code at 0x7c911230
    et je peux en avoir 3-4 de suite. Ce message vient de NTDLL!. Si je remonte dans la pile j'arrive au CTreeCtrl::eleteItem.

    Voici mon code de création de l'élément :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
     
    	TVINSERTSTRUCT tvInsert = {0};
    	tvInsert.hParent = TVI_ROOT; //hParent;
    	tvInsert.hInsertAfter = TVI_SORT;
    	tvInsert.item.mask = TVIF_PARAM | TVIF_TEXT;
    	tvInsert.item.pszText = (LPTSTR)(LPCTSTR)sName;
    	tvInsert.item.cchTextMax = strlen(tvInsert.item.pszText);
    	tvInsert.item.lParam = nIndex;
    	HTREEITEM hItem = m_treeUnused.InsertItem ( &tvInsert );
    Voici mon code de suppression :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
     
    	HTREEITEM hItem = m_treeUnused.GetSelectedItem ( );
    	m_treeUnused.DeleteItem ( hItem );


    Personnellement ça fait un moment que je gallère dessus sans en voir le bout alors si quelqu'un à une idée, je suis preneur.

    Merci d'avance

  2. #2
    Rédacteur
    Avatar de farscape
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Novembre 2003
    Messages
    9 055
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Alpes Maritimes (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Novembre 2003
    Messages : 9 055
    Par défaut
    salut,
    vérifies que hitem est valide (!=NULL) avant l'appel de deletitem...

  3. #3
    Membre éclairé Avatar de vanitom
    Profil pro
    Inscrit en
    Juillet 2004
    Messages
    327
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juillet 2004
    Messages : 327
    Par défaut
    Voici le code exacte de la fonction.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    	HTREEITEM hItem = NULL;
    	hItem = m_treeUnused.GetSelectedItem ( );
    	if ( hItem == NULL )
    		return;
     
     
    	if ( m_treeUnused.ItemHasChildren ( hItem ) == TRUE )
    		return;
     
     
    	m_treeUnused.DeleteItem ( hItem );

  4. #4
    Membre éclairé Avatar de vanitom
    Profil pro
    Inscrit en
    Juillet 2004
    Messages
    327
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juillet 2004
    Messages : 327
    Par défaut
    Je viens de faire un test.

    J'ai remplassé le double clic par le simple clic et maintenant je n'ai plus aucun problème. A part que ce n'est plus le comportement que je veux.

  5. #5
    Rédacteur
    Avatar de farscape
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Novembre 2003
    Messages
    9 055
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Alpes Maritimes (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Novembre 2003
    Messages : 9 055
    Par défaut
    ah double clic, tu dois avoir un probleme de reentrance dans le code ...

  6. #6
    Membre éclairé Avatar de vanitom
    Profil pro
    Inscrit en
    Juillet 2004
    Messages
    327
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juillet 2004
    Messages : 327
    Par défaut
    Ba la en fait j'ai rien compris.

    Qu'est ce que tu entends par "avoir un probleme de reentrance dans le code" ?

  7. #7
    Rédacteur
    Avatar de farscape
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Novembre 2003
    Messages
    9 055
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Alpes Maritimes (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Novembre 2003
    Messages : 9 055
    Par défaut
    tu ne rentres pas deux fois dans la fonction qui fait le deleteitem ?
    met un trace pour le vérifier:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
     
    TRACE("\nHitem %x",hItem);

  8. #8
    Membre éclairé Avatar de vanitom
    Profil pro
    Inscrit en
    Juillet 2004
    Messages
    327
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juillet 2004
    Messages : 327
    Par défaut
    Je n'ai pas eu le temps de tester les traces mais j'ai géré l'expanding.

    Et quand je fais le double clique, je passe dedans. Alors je me dis que ça pourrais venir de là.

  9. #9
    Membre éclairé Avatar de vanitom
    Profil pro
    Inscrit en
    Juillet 2004
    Messages
    327
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Juillet 2004
    Messages : 327
    Par défaut
    Je viens de faire le test et je n'ai pas de "reentrance" dans le code.
    Mais en tout cas, il y a peut être deux indice.

    1 - Quand je double clique je passe à chaque fois par le OnItemexpandingTreeUnused.
    2 - Au moment du message d'erreur j'ai une trace que je n'avais pas vu

    Voici ce que j'ai :
    Hitem 20e950
    Hitem 20e5f8
    Hitem 20e660HEAP[Admin-DC_d.exe]: HEAP: Free Heap block 20e5f0 modified at 20e610 after it was freed

  10. #10
    Membre émérite
    Avatar de Gabrielly
    Inscrit en
    Juin 2004
    Messages
    722
    Détails du profil
    Informations forums :
    Inscription : Juin 2004
    Messages : 722
    Par défaut
    Salut.

    Hitem 20e660HEAP[Admin-DC_d.exe]: HEAP: Free Heap block 20e5f0 modified at 20e610 after it was freed
    Effectivement lors que tu double clic sur ton item il y a deux actions qui se produisent.
    Dans le gestionnaire interceptant le NM_DBLCLK, tu expédies ton ton item vers la listview et tu fais un delete dans ce même gestionnaire,
    et entre temps il y a une autre paire de message TVN_ITEMEXPANDING, TVN_ITEMEXPANDED qui sont lancés simplement à cause du double click. Ce qui est un comportement standard du TreeCtrl.

    Et donc ton item cible n'existe plus et le hItem est certainement invalide dans ton OnItemexpandingTreeUnused()

    Ce que tu pourrais faire s'est simplement expédié ton item vers ta listview dans le gestionnaire du NM_DBLCLK et dans celui du TVN_ITEMEXPANDING tu fais le delete de ton item cible.

    En d'autres termes, si tu prends en charge les TVN_ITEMEXPAND cherche à eviter à supprimer l'item cible dans ton NM_DBLCLK

Discussions similaires

  1. [Débutant] Problème dans la gestion d'exception
    Par LisbethTheWasp dans le forum ASP.NET
    Réponses: 7
    Dernier message: 15/03/2012, 15h05
  2. Problème dans la gestion des conditions
    Par pouchet64 dans le forum Débuter
    Réponses: 4
    Dernier message: 17/05/2010, 19h06
  3. Réponses: 3
    Dernier message: 02/09/2007, 16h53
  4. Problème dans la gestion d'erreur
    Par Tintou dans le forum VBA Access
    Réponses: 2
    Dernier message: 07/06/2007, 10h02
  5. Réponses: 2
    Dernier message: 11/05/2005, 13h23

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