通過瀏覽器載入程式選擇檔案路徑方法
阿新 • • 發佈:2018-12-20
通過瀏覽器瀏覽器選擇預覽檔案儲存路徑
在工作中遇到這個需求,需要選擇檔案的儲存這裡我列舉兩種方法供大家參考:
1、通過SHBrowseForFolder實現具體程式碼和講解如下:
2、通過GetOpenFileName函式實現,這個實現方法需要增加對話方塊和訊息鉤子進行處理wchar_t szPath[MAX_PATH]; //存放選擇的目錄路徑 ZeroMemory(szPath, sizeof(szPath)); BROWSEINFO bi; memset(&bi, 0, sizeof(BROWSEINFO)); DWORD dwPid = GetPidByProcessName(_T("firefox.exe"));//這個更具不用設定不同父類控制代碼,我不想在工作列中顯示出來,所以我把他的父類控制代碼設定稱瀏覽器 HWND hWnd = GetHwndByPid(dwPid); bi.hwndOwner = hWnd; bi.pidlRoot = NULL; bi.pszDisplayName =szPath; bi.lpszTitle = L"儲存的目錄:"; bi.ulFlags = 0; bi.lpfn = NULL; bi.lParam = 0; bi.iImage = 0; LPITEMIDLIST lp = SHBrowseForFolder(&bi); if (lp) { bool list = SHGetPathFromIDList(lp, szPath); //開啟成功 } else { //開啟失敗 }
OPENFILENAMEW openFile; memset(&openFile, 0, sizeof(openFile)); openFile.lStructSize = sizeof(openFile); wchar_t szFileName[MAX_PATH] = { 0 }; OPENFILENAME openFileName = { 0 }; openFile.lStructSize = sizeof(OPENFILENAME); openFile.nMaxFile = MAX_PATH; openFile.lpstrFilter = L"資料夾\0..\0\0"; openFile.lpstrFile = szFileName; openFile.nFilterIndex = 1; openFile.Flags = OFN_EXPLORER | OFN_PATHMUSTEXIST | OFN_ENABLEHOOK | OFN_HIDEREADONLY | OFN_CREATEPROMPT | OFN_SHAREAWARE | OFN_ENABLESIZING; openFile.hInstance = (HMODULE)GetCurrentProcess(); openFile.lpfnHook = MyFolderProc; if (GetOpenFileName(&openFile)) { strDir = wstring2string(szFileName); } else { DWORD ret = CommDlgExtendedError(); strDir = str; }
通過以上兩種方式都可以瀏覽資料夾去儲存檔案LRESULT static __stdcall _WndProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM lParam) { switch (uMsg) { case WM_COMMAND: { if (wParam == IDOK) { wchar_t wcDirPath[MAX_PATH] = { 0 }; HWND hComboAddr = GetDlgItem(hwnd, ID_COMBO_ADDR); if (hComboAddr != NULL) { GetWindowText(hComboAddr, wcDirPath, MAX_PATH); } if (!wcslen(wcDirPath)) { break; } DWORD dwAttr = GetFileAttributes(wcDirPath); if (dwAttr != -1 && (FILE_ATTRIBUTE_DIRECTORY & dwAttr)) { LPOPENFILENAMEW oFn = (LPOPENFILENAME)GetProp(hwnd, L"OPENFILENAME"); if (oFn) { int size = oFn->nMaxFile > MAX_PATH ? MAX_PATH : oFn->nMaxFile; memcpy(oFn->lpstrFile, wcDirPath, size * sizeof(wchar_t)); RemoveProp(hwnd, L"OPENFILENAME"); EndDialog(hwnd, 1); } else { EndDialog(hwnd, 0); } } break; } ////////////////////////////////////////////////////////////////////////// //如果是左邊toolbar發出的WM_COMMOND訊息(即點選左邊的toolbar), 則清空OK按鈕旁的組合框。 HWND hCtrl = (HWND)lParam; if (hCtrl == NULL) { break; } int ctrlId = GetDlgCtrlID(hCtrl); if (ctrlId == ID_LEFT_TOOBAR) { HWND hComboAddr = GetDlgItem(hwnd, ID_COMBO_ADDR); if (hComboAddr != NULL) { SetWindowTextW(hComboAddr, L""); } } } break; } int i = CallWindowProc((WNDPROC)g_lOriWndProc, hwnd, uMsg, wParam, lParam); return i; } UINT_PTR static __stdcall MyFolderProc(HWND hdlg, UINT uiMsg, WPARAM wParam, LPARAM lParam) { //參考reactos可知,hdlg 是一個隱藏的對話方塊,其父視窗為開啟檔案對話方塊, OK,CANCEL按鈕等控制元件的訊息在父視窗處理。 LogInfo("MyFolderProc\n"); if (uiMsg == WM_NOTIFY) { LPOFNOTIFY lpOfNotify = (LPOFNOTIFY)lParam; if (lpOfNotify->hdr.code == CDN_INITDONE) { SetPropW(GetParent(hdlg), L"OPENFILENAME", (HANDLE)(lpOfNotify->lpOFN)); g_lOriWndProc = ::SetWindowLongW(::GetParent(hdlg), GWL_WNDPROC, (LONG)_WndProc); } if (lpOfNotify->hdr.code == CDN_SELCHANGE) { wchar_t wcDirPath[MAX_PATH] = { 0 }; CommDlg_OpenSave_GetFilePathW(GetParent(hdlg), wcDirPath, sizeof(wcDirPath)); HWND hComboAddr = GetDlgItem(GetParent(hdlg), ID_COMBO_ADDR); if (hComboAddr != NULL) { if (wcslen(wcDirPath)) { //去掉資料夾快捷方式的字尾名。 int pathSize = wcslen(wcDirPath); if (pathSize >= 4) { wchar_t* wcExtension = PathFindExtensionW(wcDirPath); if (wcslen(wcExtension)) { wcExtension = CharLowerW(wcExtension); if (!wcscmp(wcExtension, L".lnk")) { wcDirPath[pathSize - 4] = L'\0'; } } } SetWindowTextW(hComboAddr, wcDirPath); } else { SetWindowTextW(hComboAddr, L""); } } } } return 1; }