我一直在研究如何实现命名空间扩展。
NSE应该显示文件和文件夹(它们是物理文件和文件夹,但位于磁盘上的其他位置)。
此外,NSE必须尽可能接近正常的资源管理器视图,例如它必须有:
所以,基本上任何资源管理器视图都可以这样做。
看看资源管理器可以做的所有事情(我以前认为理所当然),我感到有些不知所措。
因为我既懒惰又是现实主义者(我意识到在没有问题的情况下复制所有这些功能几乎是不可能的),我的计划是在我的NSE中重用资源管理器视图的功能
我查看了各种NSE样本。其中大多数使用虚拟数据,但正如我所说,我在磁盘上的其他地方表示物理文件和文件夹。我还阅读了SHCreateShellFolderView
方法。
有了这些信息,我认为提供PIDL
我的根文件夹然后使用IShellFolder::CreateViewObject
调用SHCreateShellFolder
方法是一个相对简单的案例。这是方法:
STDMETHODIMP CShellFolderImpl::CreateViewObject(
HWND hwndOwner,
REFIID riid,
void** ppvOut )
{
HRESULT hr=E_NOINTERFACE;
if ( NULL == ppvOut )
return E_POINTER;
*ppvOut = NULL;
if (riid == IID_IShellView)
{
SFV_CREATE SfvCreate =
{
sizeof(SFV_CREATE)
};
if (SUCCEEDED(hr = QueryInterface(IID_PPV_ARGS(&SfvCreate.pshf))))
{
hr = ::SHCreateShellFolderView(
&SfvCreate,
reinterpret_cast<IShellView **>(ppvOut));
}
SfvCreate.pshf->Release();
}
else if (riid == IID_ITransferSource)
{
}
return hr;
}
没有这样的运气。 SHCreateShellFolderView
始终返回E_NOTIMPL
。事实证明这是因为它需要指向实现IShellFolder2
(和IPersist2
GetCurFolder
的内容的指针,我可以提供PIDL
。我的文件夹刚刚实施了IShellFolder
和IPerist
。
因此,在更改这些以实现更新的接口后,我得到了......没有! NSE将由Explorer加载,构造函数将被调用,但紧接着之后,将调用析构函数。如果我将接口更改回原来的样式,它会启动(但仍然存在同样的问题)。
我一直在寻找一个实现IShellFolder2
的示例,但同样,文档与其他API一样糟糕。
如何使用SHCreateShellFolderView
以便我不必重新实现Explorer已经执行的所有操作?
答案 0 :(得分:2)
即使您能够为命名空间扩展使用和嵌入Windows资源管理器窗口,问题在于您不再能够控制它的功能。例如,如果用户双击文件夹,将浏览实际的文件系统文件夹,而不是代表文件系统文件夹的命名空间扩展节点。
您唯一的选择就是自己实施。查看EZNamespaceExtensionsMFC,这使得开发命名空间扩展变得非常容易。它有一个“FileSystemBrowser”示例,您可以将其用作起点。
免责声明:我为LogicNP工作,这是EZNamespaceExtensionsMFC的开发者。