首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> C語言 >> VC >> 關於VC++

CFileDialog 多選檔案失效問題根因分析與解決方案

     編輯:關於VC++

讀者回報:《線上雜誌》第 26 期「再談 CFileDialog 對話框的定制」範例存在 Bug:多選檔案過多時,後選檔案無效、點擊「確定」無反應。本文深入分析根因並提供解決方案。

問題重現與根因追蹤

標準多選 CFileDialog 使用方式:


CFileDialog mFileDlg(TRUE, NULL, NULL,
    OFN_ALLOWMULTISELECT,
    _T("Text Files (*.txt)|*.txt|All Files (*.*)|*.*||"),
    AfxGetMainWnd());
CString pathName;
if (mFileDlg.DoModal() == IDOK) {
    POSITION mPos = mFileDlg.GetStartPosition();
    while (mPos != NULL) {
        pathName = mFileDlg.GetNextPathName(mPos);
        TRACE("%s\n", pathName);
    }
}

加入追蹤 mFileDlg.m_ofn.nMaxFile 發現預設值為 260(字元數)。

MSDN 文件說明

nMaxFile 指定 lpstrFile 緩衝區大小(以 TCHAR 為單位)。多選時所有檔案完整路徑串聯存放於此緩衝區,若超過大小,GetOpenFileName 回傳 FALSE,導致後選檔案遺失、對話框無反應。緩衝區至少需 256 字元。

解決方案:擴大緩衝區


#define NAMEBUF 1024  // 依需求調整,如 4096、8192

// 建立 CFileDialog 實例後、呼叫 DoModal 前:
mFileDlg.m_ofn.lpstrFile = new TCHAR[NAMEBUF];
memset(mFileDlg.m_ofn.lpstrFile, 0, NAMEBUF);
mFileDlg.m_ofn.nMaxFile = NAMEBUF;

// 使用完畢後釋放:
delete[] mFileDlg.m_ofn.lpstrFile;

完整修正範例


CFileDialog mFileDlg(TRUE, NULL, NULL,
    OFN_ALLOWMULTISELECT,
    _T("Text Files (*.txt)|*.txt|All Files (*.*)|*.*||"),
    AfxGetMainWnd());

// 擴大緩衝區
#define NAMEBUF 4096
mFileDlg.m_ofn.lpstrFile = new TCHAR[NAMEBUF];
memset(mFileDlg.m_ofn.lpstrFile, 0, NAMEBUF);
mFileDlg.m_ofn.nMaxFile = NAMEBUF;

if (mFileDlg.DoModal() == IDOK) {
    POSITION mPos = mFileDlg.GetStartPosition();
    while (mPos != NULL) {
        CString pathName = mFileDlg.GetNextPathName(mPos);
        TRACE("%s\n", pathName);
    }
}
delete[] mFileDlg.m_ofn.lpstrFile;  // 記得釋放

總結

多選檔案路徑總長度超過預設 260 字元緩衝區是導致失效的根本原因。依專案實際需求適當擴大 nMaxFile 並重新配置 lpstrFile 緩衝區即可徹底解決。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved