Anzeigen von Foldern und Files in CListCtrl

pschilling

Erfahrenes Mitglied
Hi Stefan,

du musst des von mir auch richtig lesen/übernehmen ;-)

Ich denke, Init ist eine Methode, welche du in deiner OnInitDialog-Methode aufrufst.

Dort darfst du nur folgenden Code ausführen:

Code:
SHFILEINFO fi;

HIMAGELIST hSysImgList = (HIMAGELIST)SHGetFileInfo("C:\\", 0, &fi, sizeof(SHFILEINFO), SHGFI_SMALLICON|SHGFI_SYSICONINDEX ); // Liefert das Handle der System-Image-List
m_imgList.Attach(hSysImgList); // Diese attachen wir an unser CImageList Objekt
m_fileList.SetImageList(&m_imgList, LVSIL_SMALL); // Und hängen unsere Imagelist an das Listcontrol.

Das führt dazu, dass die System-Image-List in deiner Klassen-Member-Variablen m_imgList gespeichert wird.

Dann hast du sicherlich noch eine Methode, welche dir die Liste mit dem Inhalt eines beliebigen Verzeichnisses gefüllt wird. Ich nenne diese mal fillDirContent(CString path);

die kann dann so in etwa so aussehen:

Code:
    void CMyDlg::fillDirContent(CString path) {
  SHFILEINFO fi;
  CFileFind ff;
  BOOL bContinue = ff.FindFile(path + "\\*");
  while( bContinue ) {
    bContinue = ff.FindNextFile();
    CString fPath = ff.GetFilePath();
    CString fName = ff.GetFileName();
    if( fName == "." || fName == ".." ) {
      continue;
    }
    memset(&fi,0,sizeof(SHFILEINFO));
    SHGetFileInfo(fPath, 0, &fi, sizeof(SHFILEINFO), SHGFI_SMALLICON|SHGFI_SYSICONINDEX );
    UINT attrs = GetFileAttributes(fPath);
    if( (attrs&FILE_ATTRIBUTE_DIRECTORY) == FILE_ATTRIBUTE_DIRECTORY ) {
      // Verzeichnis, vorne Einfügen, sortierung kannst du hier auch einbauen ;-)
      myListCtrl.InsertItem(0,fName);
    }
    else {
      // Datei, hinten einfügen, sortierung kannst du hier auch einbauen ;-)
      myListCtrl.InsertItem(10000,fName);
    }
  }
  ff.Close();


    }

Also die kleine Demo die ich dafür gecoded habe funktioniert super so ;-)
Lese die MSDN zu meinen verwendeten Methoden und probiere etwas rum!

Ich bin sicher du wirst bekommen, was du dir vorgestellt hast ;-)

Grüße,

Pit
 
Zuletzt bearbeitet:

stefan-rw

Mitglied
Hallo Pit..

Also irgendwie will das ganze bei mir nicht so richtig. ich häng mal meine header und die .cpp dran. Vielleicht findest du ja den Fehler.

// test4Dlg.h : Header-Datei
//

#if !defined(AFX_TEST4DLG_H__B0665D22_91EE_47DC_946D_AFB6EDD16044__INCLUDED_)
#define AFX_TEST4DLG_H__B0665D22_91EE_47DC_946D_AFB6EDD16044__INCLUDED_

#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000

/////////////////////////////////////////////////////////////////////////////
// CTest4Dlg Dialogfeld

class CTest4Dlg : public CDialog
{
// Konstruktion
public:
void setList (CString pfad);
void Init();
CImageList m_imgList;
CTest4Dlg(CWnd* pParent = NULL); // Standard-Konstruktor

// Dialogfelddaten
//{{AFX_DATA(CTest4Dlg)
enum { IDD = IDD_TEST4_DIALOG };
CListCtrl m_fileList;
//}}AFX_DATA

// Vom Klassenassistenten generierte Überladungen virtueller Funktionen
//{{AFX_VIRTUAL(CTest4Dlg)
protected:
virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV-Unterstützung
//}}AFX_VIRTUAL

// Implementierung
protected:
HICON m_hIcon;

// Generierte Message-Map-Funktionen
//{{AFX_MSG(CTest4Dlg)
virtual BOOL OnInitDialog();
afx_msg void OnPaint();
afx_msg HCURSOR OnQueryDragIcon();
afx_msg void OnButton1();
//}}AFX_MSG
DECLARE_MESSAGE_MAP()
};

//{{AFX_INSERT_LOCATION}}
// Microsoft Visual C++ fügt unmittelbar vor der vorhergehenden Zeile zusätzliche Deklarationen ein.

#endif // !defined(AFX_TEST4DLG_H__B0665D22_91EE_47DC_946D_AFB6EDD16044__INCLUDED_)


// test4Dlg.cpp : Implementierungsdatei
//

#include "stdafx.h"
#include "test4.h"
#include "test4Dlg.h"

#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif

/////////////////////////////////////////////////////////////////////////////
// CTest4Dlg Dialogfeld

CTest4Dlg::CTest4Dlg(CWnd* pParent /*=NULL*/)
: CDialog(CTest4Dlg::IDD, pParent)
{
//{{AFX_DATA_INIT(CTest4Dlg)
// HINWEIS: Der Klassenassistent fügt hier Member-Initialisierung ein
//}}AFX_DATA_INIT
// Beachten Sie, dass LoadIcon unter Win32 keinen nachfolgenden DestroyIcon-Aufruf benötigt
m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME);
}

void CTest4Dlg::DoDataExchange(CDataExchange* pDX)
{
CDialog::DoDataExchange(pDX);
//{{AFX_DATA_MAP(CTest4Dlg)
DDX_Control(pDX, IDC_flist, m_fileList);
//}}AFX_DATA_MAP
}

BEGIN_MESSAGE_MAP(CTest4Dlg, CDialog)
//{{AFX_MSG_MAP(CTest4Dlg)
ON_WM_PAINT()
ON_WM_QUERYDRAGICON()
ON_BN_CLICKED(IDC_BUTTON1, OnButton1)
//}}AFX_MSG_MAP
END_MESSAGE_MAP()

/////////////////////////////////////////////////////////////////////////////
// CTest4Dlg Nachrichten-Handler

BOOL CTest4Dlg::OnInitDialog()
{
CDialog::OnInitDialog();

// Symbol für dieses Dialogfeld festlegen. Wird automatisch erledigt
// wenn das Hauptfenster der Anwendung kein Dialogfeld ist
SetIcon(m_hIcon, TRUE); // Großes Symbol verwenden
SetIcon(m_hIcon, FALSE); // Kleines Symbol verwenden

// ZU ERLEDIGEN: Hier zusätzliche Initialisierung einfügen
Init();
return TRUE; // Geben Sie TRUE zurück, außer ein Steuerelement soll den Fokus erhalten
}

// Wollen Sie Ihrem Dialogfeld eine Schaltfläche "Minimieren" hinzufügen, benötigen Sie
// den nachstehenden Code, um das Symbol zu zeichnen. Für MFC-Anwendungen, die das
// Dokument/Ansicht-Modell verwenden, wird dies automatisch für Sie erledigt.

void CTest4Dlg::OnPaint()
{
if (IsIconic())
{
CPaintDC dc(this); // Gerätekontext für Zeichnen

SendMessage(WM_ICONERASEBKGND, (WPARAM) dc.GetSafeHdc(), 0);

// Symbol in Client-Rechteck zentrieren
int cxIcon = GetSystemMetrics(SM_CXICON);
int cyIcon = GetSystemMetrics(SM_CYICON);
CRect rect;
GetClientRect(&rect);
int x = (rect.Width() - cxIcon + 1) / 2;
int y = (rect.Height() - cyIcon + 1) / 2;

// Symbol zeichnen
dc.DrawIcon(x, y, m_hIcon);
}
else
{
CDialog::OnPaint();
}
}

// Die Systemaufrufe fragen den Cursorform ab, die angezeigt werden soll, während der Benutzer
// das zum Symbol verkleinerte Fenster mit der Maus zieht.
HCURSOR CTest4Dlg::OnQueryDragIcon()
{
return (HCURSOR) m_hIcon;
}

void CTest4Dlg::Init()
{
SHFILEINFO fi;

HIMAGELIST hSysImgList = (HIMAGELIST)SHGetFileInfo("C:\\", 0, &fi, sizeof(SHFILEINFO), SHGFI_SMALLICON|SHGFI_SYSICONINDEX ); // Liefert das Handle der System-Image-List
m_imgList.Attach(hSysImgList); // Diese attachen wir an unser CImageList Objekt
m_fileList.SetImageList(&m_imgList, LVSIL_SMALL); // Und hängen unsere Imagelist an das Listcontrol.


}


void CTest4Dlg::OnButton1()
{
// TODO: Code für die Behandlungsroutine der Steuerelement-Benachrichtigung hier einfügen
setList("c:");

}

void CTest4Dlg::setList(CString pfad)
{
SHFILEINFO fi;
CFileFind ff;
BOOL bContinue = ff.FindFile(pfad+"\\*");
while (bContinue) {
bContinue=ff.FindNextFile();
CString fPath=ff.GetFilePath();
CString fName=ff.GetFileName();
if (fName=="." || fName=="..") {
continue;
}
memset(&fi,0,sizeof(SHFILEINFO));
SHGetFileInfo(fPath,0,&fi,sizeof(SHFILEINFO),SHGFI_SMALLICON|SHGFI_SYSICONINDEX);
UINT attrs=GetFileAttributes(fPath);
m_fileList.InsertItem(0,fName,fi.iIcon);
}
ff.Close();
}



Danke dir schon mal....

und allen anderen die helfen wollen natürlich auch.

Stefan
 

pschilling

Erfahrenes Mitglied
Hallo Stefan,

du fügst ja auch nirgendwo Spalten in deiner Liste ein ;-)

Erzeuge dir in deiner Init-Methode für jede Information, die du darstellen möchtest eine Spalte!

also ca. so :

Code:
   m_fileList.InsertColumn(0,"Name");
   m_fileList.InsertColumn(1,"Größe");
   m_fileList.InsertColumn(2,"Typ");
// Setze Standardwerte für die Breite der einzelnen Spalten
  m_fileList.SetColumnWidth(0,100);
  m_fileList.SetColumnWidth(1,100);
  m_fileList.SetColumnWidth(2,100);

Nach dem Einfügen eines neuen Elementes setzt du die Werte der weiteren Spalten dann so :

Code:
    int pos = m_fileList.InsertItem(0,fileName, fi.iIcon);
    m_fileList.SetItemText(pos,1, fileSize);
    m_fileList.SetItemText(pos,2, fileType);

Dann funktioniert es auch mit deiner Dateiliste ;-)

Schönen Gruß,

Peter
 
Zuletzt bearbeitet:

stefan-rw

Mitglied
Hallo Pit ...

Stimmt, jetzt wo ich die Spalten hinzugefügt habe funktioniert es. Das ist ja n sch...

Wer soll denn darauf kommen ? Zumal man ja keine Spalten definieren muss, wenn man mit eigenen Images in einer eigenen Imagelist arbeitet.

Vielen vielen Dank ...

Gruss
Stefan
 

pschilling

Erfahrenes Mitglied
Hi und schön, dass es endlich funktioniert ..

Hat ja auch lang genug gedauert ;-)

Vegiss bitte nicht, deinen Beitrag als erledigt zu markieren..

Thx..

Bis zum nächsten Post,

Pit