Desk Top を List View に表示する

SHGetSpecialFolderPath() で DeskTop を取得して List View に表示します。
SHGetFileInfo() でアイコンを取得します。

前田稔(Maeda Minoru)の超初心者のプログラム入門

プロジェクトの設定

  1. 新規プロジェクトで(DeskTop)を作成します。
    プロジェクトの作成は Directry を List View に表示する を参照して下さい。
  2. DeskTop.cpp の説明です。
    commctrl.h と shlobj.h をインクルードして #pragma で "comctl32.lib" をリンクします。
    dir[MAX_PATH] が表示するフォルダーで、このまま実行すると Windows のフォルダーが表示されます。
    ここには WM_INITDIALOG: で Desk Top のフォルダーを格納します。
    hList は List View のハンドルです。
    g_hSmall は ListView に表示するアイコンの領域です。
        /**********************************************************/
        /*★ DeskTop を検索して List View に表示する    前田 稔 ★*/
        /**********************************************************/
        #include    <windows.h>
        #include    <commctrl.h>
        #include    <shlobj.h>
        #include    "resource.h"
        #pragma     comment(lib,"comctl32.lib")
    
        char        dir[MAX_PATH]= "C:\\WINDOWS\\*.*";
        HWND        hList;
        HIMAGELIST  g_hSmall= NULL;
        char        HEAD[][16]= { "名前", "サイズ", "更新日付"  };
        int         CX[]=       {  240, 80, 120 };
        
  3. WinMain() では DialogBox を表示するだけです。
  4. WM_INITDIALOG: で dir[] に Desk Top のフォルダーを格納します。
    この行をコメントにすると Windows のフォルダーが表示されます。
    hList に ListView のハンドルを格納して SetLView() 関数を呼び出します。
    WM_CLOSE: では、プログラムを終了する前にアイコンの領域を開放して下さい。
        //★ Dialog Box CallBack
        LRESULT CALLBACK DialogProc(HWND hDlg,UINT msg,WPARAM wParam,LPARAM lParam)
        {
            switch(msg)
            {   case WM_INITDIALOG:
                    SHGetSpecialFolderPath(NULL,dir,CSIDL_DESKTOP,0);
                    strcat(dir,"\\*.*");
        //MessageBox(NULL,dir,"Desk Top Folder",MB_OK);
                    hList= GetDlgItem(hDlg,IDC_LIST1);
                    SetLView();
                    break;
                case WM_CLOSE:
                    if (g_hSmall)   ImageList_Destroy(g_hSmall);
                    EndDialog(hDlg, TRUE); 
                    break;
            }
            return FALSE;
        }
        
  5. ListView にフォルダーを格納する SetLView() 関数です。
    フォルダーを検索して List View に表示する方法は Directry を List View に表示する を参照して下さい。
    アイコンを表示するには SHGetFileInfo() 関数で SHFILEINFO を取得します。
    関数の第一引数には、ファイル名をフルパスで設定して下さい。
    item.mask に LVIF_TEXT と LVIF_IMAGE を設定します。
    item.iImage = sfi.iIcon; が表示するアイコンの値です。
        //★ Search Directry
        void  SetLView()
        {   WIN32_FIND_DATA fd;
            HANDLE          hFind;
            BOOL            bRet= TRUE;
            LV_ITEM         item;
            FILETIME        ft;
            SYSTEMTIME      sTime;
            int             i,pos;
            char            buf[32];
            SHFILEINFO      sfi; 
            char            name[MAX_PATH];
    
            // List View に Column を設定
            SetColumn();
            // dir を name にコピーして、wild card を除いた位置をセット
            strcpy(name,dir);
            for(pos=strlen(name)-1; pos>=0 && name[pos]!='\\' && name[pos]!=':'; pos--);
            pos++;
    
            ListView_DeleteAllItems(hList);
            hFind= FindFirstFile(dir,&fd);
            item.mask= LVIF_TEXT | LVIF_IMAGE;
            for(i=0; hFind!=INVALID_HANDLE_VALUE && bRet; i++)
            {   // フォルダー(ファイル)名を表示
                        :
                // フォルダー(ファイル)情報を取得
                name[pos]= 0;
                strcat(name,fd.cFileName);
                SHGetFileInfo(name,0,&sfi,sizeof(SHFILEINFO),
                     SHGFI_SYSICONINDEX | SHGFI_SMALLICON | SHGFI_TYPENAME);
                item.iImage   = sfi.iIcon;
                ListView_InsertItem(hList, &item);
                // ファイルサイズを表示
                        :
                // 日付と作成時刻を表示
                        :
                ListView_SetItem(hList, &item);
                bRet= FindNextFile(hFind,&fd);
            }
            FindClose(hFind);
        }
        
  6. List View に Column を設定して、SHGetFileInfo() でアイコンの INDEX を取得します。
        //★ List View に Column を設定する
        void  SetColumn()
        {   LV_COLUMN       lvcol;
            int             i;
            SHFILEINFO      sfi;
    
            // ImageList の設定
            g_hSmall= (HIMAGELIST)SHGetFileInfo((LPCSTR)"C:\\",0,&sfi,sizeof(SHFILEINFO),
                                  SHGFI_SYSICONINDEX | SHGFI_SMALLICON);
            if (g_hSmall)   ListView_SetImageList(hList,g_hSmall,LVSIL_SMALL);
    
            // Column の項目設定
            lvcol.mask = LVCF_FMT | LVCF_WIDTH | LVCF_TEXT | LVCF_SUBITEM;
            lvcol.fmt = LVCFMT_LEFT;
            for(i=0; i<3; i++)
            {   lvcol.cx = CX[i];
                lvcol.pszText = HEAD[i];
                lvcol.iSubItem = i;
                ListView_InsertColumn(hList,i,&lvcol);
            }
        }
        

【ヒント】

WinBase.h で定義されている WIN32_FIND_DATA 構造体の定義です。
typedef struct _WIN32_FIND_DATA {
    DWORD       dwFileAttributes;
    FILETIME    ftCreationTime;
    FILETIME    ftLastAccessTime;
    FILETIME    ftLastWriteTime;
    DWORD       nFileSizeHigh;
    DWORD       nFileSizeLow;
    DWORD       dwReserved0;
    DWORD       dwReserved1;
    CHAR        cFileName[ MAX_PATH ];
    CHAR        cAlternateFileName[ 16 ];
} WIN32_FIND_DATA, *PWIN32_FIND_DATA, *LPWIN32_FIND_DATA;

SHFILEINFO 構造体です。
typedef struct _SHFILEINFOW
{       HICON       hIcon;                      // out: icon
        int         iIcon;                      // out: icon index
        DWORD       dwAttributes;               // out: SFGAO_ flags
        WCHAR       szDisplayName[MAX_PATH];    // out: display name (or path)
        WCHAR       szTypeName[80];             // out: type name
} SHFILEINFOW;

超初心者のプログラム入門(Win32API C++)