Windows下的shell扩展的种类以及相关的实例
2005-06-24 17:57
519 查看
表一
Windows 外壳扩展
类型 | 适用于 | 版本 | 有关的接口 | 描述 |
上下文菜单 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 | 向清除管理器中增加新的入口来恢复磁盘空间 |
Figure 3
Implementing the BMP Infotip
// IPersistFileImpl.h
#include <AtlCom.h> class ATL_NO_ c69b 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; } };
// IQueryInfoImpl.h
#include <AtlCom.h> #include <ShlObj.h> 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; } };
// BmpTip.h : Declaration of the CBmpTip coclass
#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<CComSingleThreadModel>, public CComCoClass<CBmpTip, &CLSID_BmpTip>, public IQueryInfoImpl, public IPersistFileImpl, public IDispatchImpl<IBmpTip, &IID_IBmpTip, &LIBID_BMPEXTLib>{ 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_
Figure 7
A Column Handler Extension
// IColumnProviderImpl.h
#include <AtlCom.h> #include <ShlObj.h> 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; } };
// BmpColInfo.h : Declaration of the CBmpColInfo
#ifndef __BMPCOLINFO_H_ #define __BMPCOLINFO_H_ #include "resource.h" // main symbols #include <shlguid.h> // 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<CComSingleThreadModel>, public CComCoClass<CBmpColInfo, &CLSID_BmpColInfo>, public IColumnProviderImpl, public IDispatchImpl<IBmpColInfo, &IID_IBmpColInfo, &LIBID_BMPCOLLib>{ 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_
// BmpColInfo.cpp : Implementation of CBmpColInfo
#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; }
Figure 11
Cleanup Extension
// IEmptyVolumeCache2Impl.h
#include <AtlCom.h> #include <emptyvc.h> 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; } };
// CleanSomething.h : Declaration of the CCleanSomething
#ifndef __CLEANSOMETHING_H_ #define __CLEANSOMETHING_H_ #include "resource.h" // main symbols #include "IEmptyVolumeCache2Impl.h" // IEmptyVolumeCache2 ///////////////////////////////////////////////////////////////// // CCleanSomething class ATL_NO_VTABLE CCleanSomething : public CComObjectRootEx<CComSingleThreadModel>, public CComCoClass<CCleanSomething, &CLSID_CleanSomething>, public IEmptyVolumeCache2Impl, public IDispatchImpl<ICleanSomething, &IID_ICleanSomething, &LIBID_DCHDEMOLib>{ 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_
// CleanSomething.cpp : Implementation of CCleanSomething
#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; }
Figure 16
Invoking the Command Prompt
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);参照msdn,vckbase
相关文章推荐
- windows查看端口被占用以及关闭相关的进程
- windows下安装redis 以及phpredis的扩展 (windows redis php&php7)
- Java 多线程(Thread) 同步(synchronized) 以及 wait, notify 相关 [实例介绍]
- 【Boolean类型】JavaScript中的原生对象以及Microsoft AJAX Library中的相关扩展
- ThinkPHP3.2.2 Widget扩展以及widget demo实例
- asp.net中XML文档的写入和读取,以及转化数据集相关实例
- 自己动手写一个简单的Windows shell扩展程序
- Windows Shell编程-第十五章.SHELL扩展
- Shell 脚本之循环语句(for,while,until)以及case,select,break,continue实例详解
- 实例展示elasticsearch集群生态,分片以及水平扩展.
- windows下安装mongodb以及node.js连接mongodb实例
- windows客户端开发--文件以及文件夹相关操作(windows api)
- 支付宝API接口开发相关文档以及实例
- 转: Windows下和程序员相关小工具 from coolshell.cn
- 安装mongo以及相关扩展
- Asp.Net Ajax 学习笔记9 JavaScript的原生类型以及Microsoft AJAX Library的相关扩展(上)
- 嵌入式 shell相关经典解释如变量以及赋值和特殊符号
- [转] shell字符串操作方法,以及实例
- linux下shell中if的相关参数以及$位置参数的数量
- Windows下使用Java调用ElasticSearch提供的相关API进行数据搜索完整实例演示