类型 |
适用于 |
版本 |
有关的接口 | 描述 |
上下文菜单 Context Menu |
文件类和外壳对象 | Windows 95+ |
IContextMenu, IContextMenu2, or IContextMenu3 |
允许在外壳对象的上下文菜单中增加新的才单项 |
右拖拽 Right drag and drop |
文件类和外壳对象 | Windows 95+ |
IContextMenu, IContextMenu2, or IContextMenu3 |
允许在右拖拽后出现的上下文菜单中增加新的才单项 |
绘制外壳图标 Drawing shell Icons |
文件类和外壳对象 File class and shell's object |
Windows 95+ |
IExtractIcon |
对于一个文件类来说,可以选择文件在运行时应该显示那个图标 |
属性页 Property Sheet |
文件类和外壳对象 File class and shell's object |
Windows 95+ |
IShellPropSheetExt |
向文件类属性对话框中加入另外的属性表页。也适用于控制面板应用 |
左拖拽 Left drag and drop |
文件类和外壳对象 File class and shell's object |
Windows 95+ |
IDropTarget |
决定在外壳内用鼠标左键拖拽一个对象到另一个对象上时做什么 |
剪贴板 Clipboard |
文件类和外壳对象 File class and shell's object |
Windows 95+ |
IDataObject |
定义如何将对象拷贝到剪贴板以及如何从剪贴板吸取对象 |
文件钩 File Hook |
Windows 95+ |
ICopyHook |
控制整个外壳内的任何文件操作。您可以允许或拒绝这些对文件的操作,但不会通知您成功或失败
|
|
外壳执行程序 Program Execution |
资源管理器 Explorer |
Desktop Update |
IShellExecuteHook |
钩住外壳内任何程序的执行 |
信息条提示 Infotip |
文件类和外壳对象 File class and shell's object |
Desktop Update |
IQueryInfo |
当鼠标移到某个文件类型文档上时显示简短文本信息 |
栏目 Column |
文件夹 Folders |
Windows 2000 |
IColumnProvider |
在资源管理器“查看”菜单的“详细资料”视图中增加新的栏目 |
Icon Overlay |
资源管理器 Explorer |
Windows 2000 |
IShellIconOverlay |
用定制的图像覆盖图标 |
搜索 Search |
资源管理器 Explorer |
Windows 2000 |
IContextMenu |
在“开始”菜单的“搜索”菜单项中增加新的搜索入口
|
清除 Cleanup |
清除管理器 Cleanup Manager |
Windows 2000 |
IEmptyVolumeCache2 |
向清除管理器中增加新的入口来恢复磁盘空间 |
#include
class ATL_NO_VTABLE IPersistFileImpl : public IPersistFile{
public:
TCHAR m_szFile[MAX_PATH];
// IUnknown
STDMETHOD(QueryInterface)(REFIID riid, void** ppvObject) = 0;
_ATL_DEBUG_ADDREF_RELEASE_IMPL(IPersistFileImpl)
// IPersistFile
STDMETHOD(Load)(LPCOLESTR wszFile, DWORD dwMode){
USES_CONVERSION;
_tcscpy(m_szFile, OLE2T((WCHAR*)wszFile));
return S_OK;
};
STDMETHOD(GetClassID)(LPCLSID){ return E_NOTIMPL; }
STDMETHOD(IsDirty)(VOID){ return E_NOTIMPL; }
STDMETHOD(Save)(LPCOLESTR, BOOL){ return E_NOTIMPL; }
STDMETHOD(SaveCompleted)(LPCOLESTR){ return E_NOTIMPL; }
STDMETHOD(GetCurFile)(LPOLESTR FAR*){ return E_NOTIMPL; }
};
#include
#include
class ATL_NO_VTABLE IQueryInfoImpl : public IQueryInfo{
public:
// IUnknown
STDMETHOD(QueryInterface)(REFIID riid, void** ppvObject) = 0;
_ATL_DEBUG_ADDREF_RELEASE_IMPL(IQueryInfoImpl)
// IQueryInfo::GetInfoTip
STDMETHOD(GetInfoTip)(DWORD dwFlags, LPWSTR *ppwszTip){
wcscpy(*ppwszTip, L"InfoTip");
return S_OK;
}
// IQueryInfo::GetInfoFlags
STDMETHOD(GetInfoFlags)(LPDWORD pdwFlags){
*pdwFlags = 0;
return E_NOTIMPL;
}
};
#ifndef __BMPTIP_H_
#define __BMPTIP_H_
#include "resource.h" // main symbols
#include "comdef.h" // GUIDs
#include "IPersistFileImpl.h" // IPersistFile
#include "IQueryInfoImpl.h" // IQueryInfo
// CBmpTip
class ATL_NO_VTABLE CBmpTip :
public CComObjectRootEx,
public CComCoClass,
public IQueryInfoImpl,
public IPersistFileImpl,
public IDispatchImpl{
public:
CBmpTip(){
HRESULT hr;
hr = SHGetMalloc(&m_pAlloc);
if (FAILED(hr)) m_pAlloc = NULL;
}
~CBmpTip(){
m_pAlloc->Release();
}
DECLARE_REGISTRY_RESOURCEID(IDR_BMPTIP)
DECLARE_PROTECT_FINAL_CONSTRUCT()
BEGIN_COM_MAP(CBmpTip)
COM_INTERFACE_ENTRY(IBmpTip)
COM_INTERFACE_ENTRY(IQueryInfo)
COM_INTERFACE_ENTRY(IPersistFile)
COM_INTERFACE_ENTRY(IDispatch)
END_COM_MAP()
// IQueryInfo
public:
STDMETHOD(GetInfoTip)(DWORD, LPWSTR*);
private:
STDMETHOD(GetBitmapInfo)(CComBSTR*);
LPMALLOC m_pAlloc;
};
#endif //__BMPTIP_H_
#include
#include
class ATL_NO_VTABLE IColumnProviderImpl : public IColumnProvider
{
protected:
TCHAR m_szFolder[MAX_PATH];
public:
// IUnknown
STDMETHOD(QueryInterface)(REFIID riid, void** ppvObject) = 0;
_ATL_DEBUG_ADDREF_RELEASE_IMPL(IColumnProviderImpl)
// IColumnProvider
// IColumnProvider::Initialize
STDMETHOD(Initialize)(LPCSHCOLUMNINIT psci){
USES_CONVERSION;
_tcscpy(m_szFolder, OLE2T((WCHAR*)psci->wszFolder));
return S_OK;
}
// IColumnProvider::GetColumnInfo
STDMETHOD(GetColumnInfo)(DWORD dwIndex,
SHCOLUMNINFO *psci){
return S_FALSE;
}
// IColumnProvider::GetItemData
STDMETHOD(GetItemData)(LPCSHCOLUMNID pscid,
LPCSHCOLUMNDATA pscd,
VARIANT *pvarData){
return S_FALSE;
}
};
#ifndef __BMPCOLINFO_H_
#define __BMPCOLINFO_H_
#include "resource.h" // main symbols
#include // GUID of IColumnProvider
#include "IColumnProviderImpl.h" // IColumnProvider base impl
const UINT BMPCH_DEFWIDTH = 16;// column default width in chars
const UINT BMPCH_MAXSIZE = 80; // max text size
const DWORD BMPCH_NUMOFCOLS = 1;// number of columns handled
// here
// CBmpColInfo
class ATL_NO_VTABLE CBmpColInfo :
public CComObjectRootEx,
public CComCoClass,
public IColumnProviderImpl,
public IDispatchImpl{
public:
CBmpColInfo(){}
DECLARE_REGISTRY_RESOURCEID(IDR_BMPCOLINFO)
DECLARE_PROTECT_FINAL_CONSTRUCT()
BEGIN_COM_MAP(CBmpColInfo)
COM_INTERFACE_ENTRY(IBmpColInfo)
COM_INTERFACE_ENTRY_IID(IID_IColumnProvider, CBmpColInfo)
COM_INTERFACE_ENTRY(IDispatch)
END_COM_MAP()
// IColumnProvider
public:
STDMETHOD(GetColumnInfo)(DWORD, SHCOLUMNINFO *);
STDMETHOD(GetItemData)(LPCSHCOLUMNID, LPCSHCOLUMNDATA,
VARIANT *);
private:
STDMETHOD(GetBitmapInfo)(LPCWSTR, LPTSTR);
};
#endif //__BMPCOLINFO_H_
#include "stdafx.h"
#include "BmpCol.h"
#include "BmpColInfo.h"
HRESULT CBmpColInfo::GetColumnInfo(DWORD dwIndex,
SHCOLUMNINFO *psci){
// Since this extension might provide more columns, the
// index is used to enumerate them. The shell calls
// this method repeatedly with progressive indexes, until
// you return S_FALSE. Return S_FALSE only when you've
// finished with all your columns. dwIndex is a 0-based
// index. Notice that without this checking you enter
// an infinite loop!
if (dwIndex >= BMPCH_NUMOFCOLS)
return S_FALSE;
// Now fills out the SHCOLUMNINFO structure to let the
// shell know about general-purpose features of the column
// Identifies the column with a FMTID/PID pair. You'd
// define one of these pairs for each column you're
// adding here.
psci->scid.fmtid = *_Module.pguidVer; // use object's CLSID
psci->scid.pid = 1;
// Sets type, alignment and default width
psci->vt = VT_LPSTR; // data is LPSTR
psci->fmt = LVCFMT_LEFT; // left alignment
psci->cChars = BMPCH_DEFWIDTH; // default width in chars
// Other flags
psci->csFlags = SHCOLSTATE_TYPE_STR;
// Caption and description
wcsncpy(psci->wszTitle, L"Dimensions", MAX_COLUMN_NAME_LEN);
wcsncpy(psci->wszDescription,
L"Provides dimensions and colors for BMPs",
MAX_COLUMN_DESC_LEN);
return S_OK;
}
// IColumnProvider::GetItemData
HRESULT CBmpColInfo::GetItemData(LPCSHCOLUMNID pscid,
LPCSHCOLUMNDATA pscd,
VARIANT *pvarData){
USES_CONVERSION;
// The shell calls this method for each file displayed
// in the folder where this column has been selected.
// The SHCOLUMNID structure identifies the column
// unequivocally just in case you're handling more than one.
// In this case, I'm managing just one column so I'll
// ignore the SHCOLUMNID param.
// Information about the specific file is contained in the
// SHCOLUMNDATA structure. I'm interested only in .BMP.
if (wcsicmp(pscd->pwszExt, L".bmp")) return S_FALSE;
// Reads dimensions and palette size from the BMP file
TCHAR szBuf[BMPCH_MAXSIZE];
GetBitmapInfo(pscd->wszFile, szBuf);
// The return value (a string in this case) must be
// packed as a Variant.
CComVariant cv(szBuf);
cv.Detach(pvarData);
return S_OK;
}
HRESULT CBmpColInfo::GetBitmapInfo(LPCWSTR wszFile, LPTSTR p){
USES_CONVERSION;
BITMAPFILEHEADER bf;
BITMAPINFOHEADER bi;
HFILE h;
// Reads the file header
h = _lopen(OLE2T(wszFile), OF_READ);
if (h==HFILE_ERROR) return S_OK;
_lread(h, (LPBITMAPFILEHEADER)&bf, sizeof(BITMAPFILEHEADER));
_lread(h, (LPBITMAPINFOHEADER)&bi, sizeof(BITMAPINFOHEADER));
_lclose(h);
// Formats the string
wsprintf(p, _T("%d x %d x %d"), bi.biWidth, bi.biHeight,
bi.biBitCount);
return S_OK;
}
#include
#include
class ATL_NO_VTABLE IEmptyVolumeCache2Impl : public IEmptyVolumeCache2{
public:
// IUnknown
STDMETHOD(QueryInterface)(REFIID riid, void** ppvObject) =
0;
_ATL_DEBUG_ADDREF_RELEASE_IMPL(IEmptyVolumeCache2Impl)
// IEmptyVolumeCache::Initialize
STDMETHOD(Initialize)(HKEY hkRegKey, LPCWSTR pcwszVolume,
LPWSTR *ppwszDisplayName,
LPWSTR *ppwszDescription,
DWORD *pdwFlags){
// Allows to initialize a Windows 98 handler
MessageBox(0, _T("Initialize"), 0, 0);
return S_OK;
}
// IEmptyVolumeCache::Deactivate
STDMETHOD(Deactivate)(DWORD *pdwFlags){
// Called when the handler is going to be unloaded
MessageBox(0, _T("Deactivate"), 0, 0);
return S_OK;
}
// IEmptyVolumeCache::GetSpaceUsed
STDMETHOD(GetSpaceUsed)(DWORDLONG *pdwSpaceUsed,
IEmptyVolumeCacheCallBack *picb){
// Returns the amount of space the handler can free
MessageBox(0, _T("GetSpaceUsed"), 0, 0);
return S_OK;
}
// IEmptyVolumeCache::Purge
STDMETHOD(Purge)(DWORDLONG dwSpaceToFree,
IEmptyVolumeCacheCallBack *picb){
// Actually deletes the files
MessageBox(0, _T("Purge"), 0, 0);
return S_OK;
}
// IEmptyVolumeCache::ShowProperties
STDMETHOD(ShowProperties)(HWND hwnd){
// Provides a UI
MessageBox(0, _T("ShowProperties"), 0, 0);
return S_OK;
}
// IEmptyVolumeCache2::InitializeEx
STDMETHOD(InitializeEx)(HKEY hkRegKey, LPCWSTR pcwszVolume,
LPCWSTR pcwszKeyName,
LPWSTR *ppwszDisplayName,
LPWSTR *ppwszDescription,
LPWSTR *ppwszBtnText,
DWORD *pdwFlags){
// Initializes the handler under Windows 2000
MessageBox(0, _T("InitializeEx"), 0, 0);
return S_OK;
}
};
#ifndef __CLEANSOMETHING_H_
#define __CLEANSOMETHING_H_
#include "resource.h" // main symbols
#include "IEmptyVolumeCache2Impl.h" // IEmptyVolumeCache2
/////////////////////////////////////////////////////////////////
// CCleanSomething
class ATL_NO_VTABLE CCleanSomething :
public CComObjectRootEx,
public CComCoClass,
public IEmptyVolumeCache2Impl,
public IDispatchImpl{
public:
CCleanSomething(){}
DECLARE_REGISTRY_RESOURCEID(IDR_CLEANSOMETHING)
DECLARE_PROTECT_FINAL_CONSTRUCT()
BEGIN_COM_MAP(CCleanSomething)
COM_INTERFACE_ENTRY(IEmptyVolumeCache)
COM_INTERFACE_ENTRY(IEmptyVolumeCache2)
COM_INTERFACE_ENTRY(ICleanSomething)
COM_INTERFACE_ENTRY(IDispatch)
END_COM_MAP()
// IEmptyVolumeCache2
public:
STDMETHOD(InitializeEx)(HKEY hkRegKey, LPCWSTR pcwszVolume,
LPCWSTR pcwszKeyName,
LPWSTR *ppwszDisplayName,
LPWSTR *ppwszDescription,
LPWSTR *ppwszBtnText,
DWORD *pdwFlags);
STDMETHOD(GetSpaceUsed)(DWORDLONG *pdwSpaceUsed,
IEmptyVolumeCacheCallBack *picb);
};
#endif //__CLEANSOMETHING_H_
#include "stdafx.h"
#include "DCHDemo.h"
#include "CleanSomething.h"
// CCleanSomething
HRESULT CCleanSomething::InitializeEx(HKEY hkRegKey,
LPCWSTR pcwszVolume, LPCWSTR pcwszKeyName,
LPWSTR *ppwszDisplayName, LPWSTR *ppwszDescription,
LPWSTR *ppwszBtnText, DWORD *pdwFlags){
USES_CONVERSION;
MessageBoxW(0, pcwszVolume, 0, 0);
*ppwszDisplayName = (LPWSTR)CoTaskMemAlloc(100);
*ppwszDescription = (LPWSTR)CoTaskMemAlloc(100);
*ppwszBtnText = (LPWSTR)CoTaskMemAlloc(100);
lstrcpyW(*ppwszDisplayName, T2OLE("DCHDemo"));
lstrcpyW(*ppwszDescription, T2OLE("Clean Something"));
lstrcpyW(*ppwszBtnText, T2OLE("Click Me!"));
*pdwFlags |= EVCF_HASSETTINGS;
return S_OK;
}
HRESULT CCleanSomething::GetSpaceUsed(DWORDLONG *pdwSpaceUsed,
IEmptyVolumeCacheCallBack *picb){
*pdwSpaceUsed = 1024000;
return S_OK;
}
TCHAR szCommand[MAX_PATH] = TEXT("");
STARTUPINFO sui;
PROCESS_INFORMATION pi;
OSVERSIONINFO osi;
GetEnvironmentVariable(TEXT("ComSpec"), szCommand,
ARRAYSIZE(szCommand));
if(!*szCommand){
osi.dwOSVersionInfoSize = sizeof(osi);
GetVersionEx(&osi);
if(VER_PLATFORM_WIN32_NT == osi.dwPlatformId){
lstrcpy(szCommand, TEXT("cmd.exe"));
} else{
lstrcpy(szCommand, TEXT("command.com"));
}
}
//set up the STARTUPINFO structure
ZeroMemory(&sui, sizeof(sui));
sui.cb = sizeof(sui);
//create the process
CreateProcess( NULL, szCommand, NULL, NULL,
FALSE, NORMAL_PRIORITY_CLASS,
NULL, szInitialDirectory,
&sui, &pi);