【问题标题】:Issues with CFileDialog for multiple file selection多文件选择的 CFileDialog 问题
【发布时间】:2014-07-23 23:58:15
【问题描述】:

我正在使用以下代码通过 UI 检索多个文件选择:

CFileDialog fd(TRUE, NULL, NULL, OFN_HIDEREADONLY | OFN_OVERWRITEPROMPT | OFN_EXPLORER, 
    NULL, hParentWnd ? CWnd::FromHandle(hParentWnd) : NULL);

fd.m_pOFN->Flags |= OFN_FILEMUSTEXIST | OFN_ALLOWMULTISELECT | OFN_NODEREFERENCELINKS;

int nLnBuff = 32767;
TCHAR* pBuffFileSelect = new TCHAR[nLnBuff];

memset(pBuffFileSelect, 0, nLnBuff * sizeof(TCHAR));

fd.m_ofn.lpstrFile = pBuffFileSelect;
fd.m_ofn.nMaxFile = nLnBuff;

if(fd.DoModal() == IDOK)
{
    POSITION fileNamesPosition = fd.GetStartPosition();
    while(fileNamesPosition != NULL)
    {
        CString strSelPath = fd.GetNextPathName(fileNamesPosition);
        TRACE("path: %s\n", CStringA(strSelPath));
    }  
}


delete[] pBuffFileSelect;

所以当我在我的电脑上尝试它时,我运行上面的方法,当“打开文件”对话框打开时,作为测试,我导航到我的桌面并使用 Ctrl+A 快捷方式选择所有文件,然后单击打开。结果我开始得到以下路径:

The first path is a link, which is correct (it exists on my Public desktop):
"C:\Users\Public\Desktop\avp.lnk"

But then the second path is wrong. It gives me:
"C:\Users\Public\Desktop\1.txt"
when it's supposed to be (for the desktop that I picked):
"C:\Users\UserName\Desktop\1.txt"

然后每个连续路径都有“公共”而不是“用户名”。

我应该指出,我在这台 PC 上设置了多个用户帐户,而我正在测试此方法的用户帐户是标准用户帐户。我运行此方法的应用程序没有运行提升(或具有常规用户权限),因此它不应该访问其他用户帐户。

那么我在这里做错了什么?

【问题讨论】:

  • 您确定这些文件不在在公共部分吗?如果你右击1.txt并查看属性,它会显示什么路径?
  • @RogerRowland:是的,我确定。第一个链接确实位于C:\Users\Public\Desktop\avp.lnk,但下一个文件位于C:\Users\UserName\Desktop\1.txt。这几乎就像第一个路径中的某些东西“搞砸”了后面的路径。
  • 桌面合并来自不同路径的项目。 CFileDialog 可能假设所有项目都在同一路径中,并盲目地将第一个路径应用于所有后续项目。
  • @EricBrown 是的,我认为你一针见血。因为它可能在下面使用OPENFILENAME,请参阅OFN_ALLOWMULTISELECT 的 cmets - "...lpstrFile 缓冲区返回当前目录的路径,后跟所选文件的文件名"

标签: c++ winapi mfc windows-shell


【解决方案1】:

检查了来源,GetOpenFileName 假设所有项目实际上都在同一个文件路径中。这不适用于桌面(不同路径中的项目合并到一个 shell 视图中),因此您会看到不良行为。

解决方案是使用Common Item dialogs,它使用shell 命名空间而不是文件系统路径。所有桌面项都在一个公共的shell路径下,然后可以使用IShellItem::GetDisplayName转换为文件系统路径。

不幸的是,MFC 没有通用项对话框的包装器,因此您必须自己管理它。

【讨论】:

  • 谢谢。它回答了我的问题。尽管微软无法直接获得他们的*#$%,这很糟糕。不幸的是,CLSID_FileOpenDialog 仅在 Vista 之后可用。所以我必须同时做这两件事才能让它在 XP 上工作。当我们不得不浪费时间修复本来应该工作的东西时,这总是让我很生气......“谢谢”,微软!
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2015-01-18
  • 1970-01-01
  • 2018-07-29
  • 2021-12-11
  • 2015-10-13
  • 1970-01-01
  • 2011-10-05
相关资源
最近更新 更多