Debug Assertion Failed beim Einbinden von Icons in ein ListControl



  • Hallo Forum,
    ich bin neu in MFC, darum bitte ich um Nachsicht falls mein Problem für euch banal erscheinen mag 🙂
    ich versuche in einem List Control (Bericht) ein Icon für das erste Item einzusetzen (anstatt Text).

    void MyDlg1::OnPaint()
    {
      ...
    
      LVITEM lvItem;
      int nItem;
    
      m_lstAll.SetExtendedStyle(LVS_EX_FULLROWSELECT|LVS_EX_GRIDLINES);
    
      CImageList *m_ImgMass = new CImageList;
      HICON m_icon = AfxGetApp()->LoadIcon(IDI_ICON1);
      m_ImgMass->Add(m_icon);
    
      m_lstAll.SetImageList(m_ImgMass, LVSIL_SMALL);
    
      lvItem.mask = LVIF_IMAGE;
      lvItem.iItem = 0;
      lvItem.iSubItem = 0;
      lvItem.iImage = 0;
      nItem = m_lstAll.InsertItem(&lvItem);
    
      ...
    
    }
    

    wobei m_lstAll meine Membervariable für das ListControl ist.
    In der Zeile, in der ich das Icon einbinden will (->LoadIcon) wird der Assertion Failure aufgerufen.
    Jetzt hab ich schon recherchiert dass dort wohl mein Icon, dass ich einbinden will noch nicht geladen wurde. Die Funktion wird im OnPaint aufgerufen, liegt dort mein Fehler?
    Wenn ja, welches Event wäre hierfür geeigneter?
    Vielen Dank für eure Hilfe!



  • Was ich natürlich noch vergessen habe: ich arbeite mit Visual Studio 2003



  • Glaubst du, dass es eine gute Idee ist, bei jedem Zeichnen des Fensters eine neue Imagelist zu erstellen und zu füllen?



  • Wie gesagt, ich bin neu in MFC, das ist mein erstes Projekt. Von daher kann ich schlecht beurteilen ob das eine gute Idee ist.
    Aber deiner Formulierung nach wohl eher nicht 😃
    Das heißt wohl das Problem liegt im OnPaint(), hab ich das richtig verstanden? Welche Meldung wäre demnach besser geeignet?



  • OnInitDialog. Und mach die Imagelist zum Member deiner Dialogklasse (also kein Zeiger), dann kannst du das delete nicht vergessen, weil du keins mehr brauchst.


  • Mod

    Benötigt man eigentlich gar nicht.

    Wenn man SetImageList aufruft wird das ListControl der Eigentümer der Imageliste.

    Also einfach Imaglist lokal erzeugen. Imagelist zuweisen. Detach und gut ists.

    {	
    	CImageList ilIcons;
    	VERIFY(ilIcons.Create(IDB_BMP,16,1,RGB(255, 0, 255)));
    	m_lcData.SetImageList(&ilIcons, LVSIL_SMALL);
    	ilIcons.Detach();
    	}
    

    Die Imagelist wird korrekt entsorgt.

    In der ComCtl32 wurde richtig Aufwand getrieben, um ein doppeltes Löschen zu vermeiden. Also wenn man ein lokales CImageList Objekt noch behält. In diesem Fall wird die Imagelist im ListControl entsorgt und anschließend durch CImageList... Eigentlich ein Bug, aber weil es jeder macht, hat MS es so gedreht, dass man nicht auf die Fresse fliegt.. 🙂



  • Vielen Dank für die schnellen Antworten, jetzt funktioniert es!


Log in to reply