论坛首页 综合技术论坛

提取系统中注册的所有文件的类型名称及其图标

浏览 1570 次
精华帖 (0) :: 良好帖 (0) :: 新手帖 (0) :: 隐藏帖 (0)
作者 正文
   发表时间:2011-09-30  
如何提取系统中注册的所有文件的类型名称及其图标
void GetTypeIcons()
{
HKEY hKey;

int i = 0;

char data[64];

DWORD dwBuf = MAX_PATH;
DWORD dwIndex = 1;
DWORD dataSize = sizeof(data);

SHFILEINFO shInfo;

// Checks to see if Internet Explorer 6.0 Preview is installed and
// if it is then it will by pass the .cdf file which IE6 has either
// registered incorrectly or has an inconsistancy with SHGetFileInfo

if(RegOpenKeyEx(HKEY_LOCAL_MACHINE, "SOFTWARE\\Microsoft\\Internet Explorer", 0,
KEY_ALL_ACCESS, &hKey) == ERROR_SUCCESS)

RegQueryValueEx(hKey, "Version", NULL, NULL,(LPBYTE)&data, &dataSize);

RegCloseKey(hKey);

bool bCDF = false;

char* szCDF = new char[MAX_PATH];

strcpy(szCDF, data);

if(strstr(szCDF, "6.0.") != NULL)
{
bCDF = true;

// Tries to manually grab the icon and information for ".cdf" by checking to
// see if it is a registered file type then by finding the dll which the icon
// is stored at

if(RegOpenKeyEx(HKEY_CLASSES_ROOT,
"CLSID\\{f39a0dc0-9cc8-11d0-a599-00c04fd64433}\\InProcServer32", 0,
KEY_ALL_ACCESS, &hKey) == ERROR_SUCCESS)
{
LONG dwSize = 256;
char szValue[256];

if (RegQueryValue(hKey, "", szValue, &dwSize) == ERROR_SUCCESS)
{
CShellList::LSICON lsIcon;

ExtractIconEx((LPCSTR)szValue, 2, &lsIcon.hLarge, &lsIcon.hSmall, 1);

// 2 = the file type icon index for channel files
// Channel File would be the display name, and .cdf the file type

pSmall->Add(lsIcon.hSmall);

i = pLarge->Add(lsIcon.hLarge);

pszList->Add(".cdf");

// Do whatever you want here

i = pTypeList->InsertItem(0, "Channel File", i);

pTypeList->SetItemText(i, 1, ".cdf");
}
}

RegCloseKey(hKey);
}

delete szCDF;

char* szName = new char[MAX_PATH];

if(RegOpenKeyEx(HKEY_CLASSES_ROOT, "", 0, KEY_ENUMERATE_SUB_KEYS, &hKey) == ERROR_SUCCESS)
{
while (RegEnumKey(hKey, dwIndex++, szName, dwBuf) == 0)
{
if (*szName == '.')
{
if(!(bCDF && strstr(szName, ".cdf") != NULL))
{
// http://support.microsoft.com/support/kb/articles/Q179/1/67.ASP

memset(&shInfo, 0, sizeof(SHFILEINFO));

SHGetFileInfo(szName, FILE_ATTRIBUTE_NORMAL, &shInfo, sizeof(SHFILEINFO),
SHGFI_USEFILEATTRIBUTES | SHGFI_ICON | SHGFI_SMALLICON);

pSmall->Add(shInfo.hIcon);

memset(&shInfo, 0, sizeof(SHFILEINFO));

SHGetFileInfo(szName, FILE_ATTRIBUTE_NORMAL, &shInfo, sizeof(SHFILEINFO),
SHGFI_USEFILEATTRIBUTES | SHGFI_DISPLAYNAME | SHGFI_TYPENAME |
SHGFI_ICON);

i = pLarge->Add(shInfo.hIcon);

pszList->Add((const char*)szName);

// Do whatever you want here

if(pTypeList->m_hWnd != NULL)
{
i = pTypeList->InsertItem(0, shInfo.szTypeName, i);

pTypeList->SetItemText(i, 1, szName);
}
}
}
}
}

RegCloseKey(hKey);

delete szName;

}


下面让我们来看看如何来具体用它们来实现:

1、 提取并显示出图标到左侧列表框中。

代码实现如下:

//读取各种资源内部图标并显示在左侧列表框中


void CIconSnapDlg::OnOK()
{
CFileDialog fileDialog( TRUE,"*.ICO",NULL,NULL,"资源文件(*.ICO,*.BMP,*.EXE,*.DLL,*.ICL)|*.ICO;*.BMP;*.EXE;*.DLL;*.ICL||");
if (fileDialog.DoModal() == IDOK)
{
szOpenFileName=fileDialog.GetPathName();
szOpenFileExtName= fileDialog.GetFileExt ();
szOpenFileExtName.MakeLower ();

m_List.ResetContent (); //选清空左侧图标列表框

//读取并显示ICON文件
if(szOpenFileExtName =="ico")
{
lpIR=pIcons->ReadIconFromICOFile (szOpenFileName);
HICON hIcon;
hIcon=ExtractIcon(AfxGetInstanceHandle(),szOpenFileName,0);
if(hIcon!=NULL)
m_List.AddString (szOpenFileName);
CStatic* pStatic = (CStatic*) GetDlgItem(IDC_ICONS);
pStatic->SetIcon (hIcon);
}
else if(szOpenFileExtName == "bmp") //读取并显示BMP文件
{
pIcons->IconImageFromBMPFile (szOpenFileName,&lpIR->IconImages[0],TRUE);
HICON hIcon;
hIcon=pIcons->MakeIconFromResource (&lpIR->IconImages [0]);
if(hIcon!=NULL)
m_List.AddString (szOpenFileName);
CStatic* pStatic = (CStatic*) GetDlgItem(IDC_ICONS);
pStatic->SetIcon (hIcon);
}
else //读取并显示EXE、DLL等资源文件
{
HINSTANCE hLibrary;

// Load the DLL/EXE - NOTE: must be a 32bit EXE/DLL for this to work
if( (hLibrary = LoadLibraryEx( szOpenFileName, NULL, LOAD_LIBRARY_AS_DATAFILE )) == NULL )
{
// Failed to load - abort
MessageBox( szOpenFileName+ "文件载入错误,必须是WIN32的文件!", "错误", MB_OK );
return;
}
// Store the info
EDII.szFileName =szOpenFileName;
EDII.hInstance = hLibrary;

// Fill in the listbox with the icons available
if( ! EnumResourceNames( EDII.hInstance, RT_GROUP_ICON, (ENUMRESNAMEPROC )MyEnumProcedure, (LPARAM)GetSafeHwnd()) )
{
MessageBox( "列举图标资源名时出错!", "错误", MB_OK );
return;
}
}

m_List.SetCurSel (0);
if( m_List.GetCount() == 0 )
{
MessageBox( "此文件中没有图标资源!", "错误", MB_OK );
//无图标资源,置保存和复制按钮为无效状态
m_Copy.EnableWindow (false);
m_SaveAs.EnableWindow (false);
return;
}
//有图标资源,置保存和复制按钮为有效状态????
m_Copy.EnableWindow (true);
m_SaveAs.EnableWindow (true);

//刷新调用OnPaint来显示图标
InvalidateRect(NULL,TRUE);
}
}


在OnPaint()涵数中加入下面代码用来具体显示提取出的图标或位图资源。
//根据左侧图标列表,利用OnPaint()来更新右侧相应图标



LPTSTR lpIconID;
HICON hIcon;
if((lpIconID=(LPTSTR)m_List.GetItemData(m_List.GetCurSel()))!=(LPTSTR)LB_ERR )
{
if(szOpenFileExtName=="exe"||szOpenFileExtName=="dll"||szOpenFileExtName=="icl")
{
hIcon=pIcons->GetIconFromInstance(EDII.hInstance,lpIconID);
CStatic* pStatic = (CStatic*) GetDlgItem(IDC_ICONS);
pStatic->SetIcon (hIcon);
}
}
---------------------------------------------------------------------------------
SHFILEINFO sfi;

SHGetFileInfo("d:\\smartdrv.exe",0,&sfi,sizeof(sfi),SHGFI_ICON);
HICON hIcon = sfi.hIcon;
CClientDC Clientdc(this);
Clientdc.DrawIcon(10,10,hIcon);
Clientdc.DeleteDC;

也可以使用ExtractIcon()函数,该函数原型为:

HICON ExtractIcon(
HINSTANCE hInst, // 实例句柄
LPCTSTR lpszExeFileName, // 文件名
UINT nIconIndex // 图标索引
);

参数
hInst
[in] 调用该函数的应用程序句柄.
lpszExeFileName
[in] 指向空字符串结尾的可执行文件,DLL,或图标文件名.
nIconIndex
[in] 指定基于0的图标索引.例如,如果值为0,函数返回指定文件开始图标的句柄.
如果值为-1,函数返回指定文件中图标的数量.如果文件是一个可执行文件或DLL,返回值是RT_GROUP_ICON资源号.
如果文件是一个.ICO文件,返回值为1.

必须调用DestroyIcon来销毁由ExtractIcon返回的图标句柄

CClientDC clientDc(this);

HICON hIcon = ExtractIcon(AfxGetApp()->m_hInstance,"C:\\Program Files\\Outlook Express\\msimn.exe",1);
clientDc.DrawIcon(10,10,hIcon);

//返回图标数目
HICON hIcon = ExtractIcon(AfxGetApp()->m_hInstance,"C:\\Program Files\\Outlook Express\\msimn.exe",-1);
CString str;
str.Format("%d",hIcon);
AfxMessageBox(str);

DestroyIcon(hIcon);
------------------------------------------------------------------------------
(1) SDK函数 SHGetFileInfo 或使用 ExtractIcon获得图标资源的 handle,
(2) SDK函数 SHGetFileInfo获得有关文件的 很多信息,如大小图标,属性,
类型等.
Example(1): 在程序窗口左上角显示 NotePad图标.
void CSampleView: OnDraw(CDC * pDC)
{
if( :: SHGetFileInfo(_T("c:\\pwin95\\notepad.exe"),0,
&stFileInfo,sizeof(stFileInfo),SHGFI_ICON))
{
pDC ->DrawIcon(10,10,stFileInfo.hIcon);
}
}

Example(2):同样功能,Use ExtractIcon Function
void CSampleView:: OnDraw(CDC *pDC)
{
HICON hIcon=:: ExtractIcon(AfxGetInstanceHandle(),_T
("NotePad.exe"),0);
if (hIcon &&hIcon!=(HICON)-1)
pDC->DrawIcon(10,10,hIcon);
}
论坛首页 综合技术版

跳转论坛:
Global site tag (gtag.js) - Google Analytics