在Windows Server 2003上运行以下代码时,GetOpenFileName
常用对话框初始化时会出现间歇性减速。启动时间约为30秒左右。下面的代码是一个临时程序,我用它来举例说明我在我的大项目中遇到的问题,但两者都存在问题。
一个重要的注意事项是,当网络接口全部被禁用时,初始化所需的时间更接近正常 - 通常为~2秒。一旦再次启用它们,问题就会恢复。
我已经将初始化时间与其他具有文件打开常用对话框(如记事本)的程序相对应,这些对话框没有相同的问题,无论是否启用了网络接口。
代码:
getNewFileName.h:
#define _tWinMain wWinMain
#include "windows.h"
#include <string>
#include "resource.h"
using std::wstring;
#define ISOLATION_AWARE_ENABLED 1
#if defined _M_IX86
#pragma comment(linker,"/manifestdependency:\"type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' processorArchitecture='X86' publicKeyToken='6595b64144ccf1df' language='*'\"")
#elif defined _M_IA64
#pragma comment(linker,"/manifestdependency:\"type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' processorArchitecture='ia64' publicKeyToken='6595b64144ccf1df' language='*'\"")
#elif defined _M_X64
#pragma comment(linker,"/manifestdependency:\"type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' processorArchitecture='amd64' publicKeyToken='6595b64144ccf1df' language='*'\"")
#else
#pragma comment(linker,"/manifestdependency:\"type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' processorArchitecture='*' publicKeyToken='6595b64144ccf1df' language='*'\"")
#endif
getNewFileName.cpp:
#include "getNewFileName.h"
HINSTANCE hInst;
BOOL InitInstance(HINSTANCE);
HWND hWnd;
wstring lastfile;
BOOL getNewFileName(HWND owner, wstring title, wstring defaultfile, LPWSTR filetypes, OPENFILENAME &ofn, wstring lastdir, wstring lastfile, int mode, wstring extension);
int APIENTRY _tWinMain(HINSTANCE hInstance,
HINSTANCE hPrevInstance,
LPTSTR lpCmdLine,
int nCmdShow)
{
UNREFERENCED_PARAMETER(hPrevInstance);
UNREFERENCED_PARAMETER(lpCmdLine);
MSG msg;
HACCEL hAccelTable;
if (!InitInstance (hInstance))
{
return FALSE;
}
hAccelTable = LoadAccelerators(hInstance, MAKEINTRESOURCE(IDR_ACCELERATOR1));
// Main message loop:
while (GetMessage(&msg, NULL, 0, 0))
{
if (!TranslateAccelerator(hWnd, hAccelTable, &msg))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}
return (int) msg.wParam;
}
BOOL InitInstance(HINSTANCE hInstance)
{
hInst = hInstance;
OPENFILENAME ofn;
wstring newfn;
hWnd = CreateWindow(NULL, L"test", NULL,
0, 0, 0, 0, NULL, NULL, hInst, NULL);
BOOL ret = getNewFileName(hWnd, L"test", L"*.xml", L"XML Files\0*.xml\0", ofn, L"C:\\", lastfile, 1, L"xml");
if (ret) {
newfn = ofn.lpstrFile;
MessageBox(hWnd,newfn.c_str(),L"test",MB_OK);
}
ExitProcess(0);
return TRUE;
}
void addPrefix(wstring &path) {
wstring test = path.substr(0,4);
if (path.substr(0,8) == L"\\\\?\\UNC\\" || path.substr(0,4) == L"\\\\?\\") { return; }
wstring prefix = path.substr(0,2);
if (prefix.compare(L"\\\\") == 0) { path.assign(L"\\\\?\\UNC\\"+path.substr(2,wstring::npos)); } else { path.assign(L"\\\\?\\"+path); }
return;
}
UINT_PTR CALLBACK OFNHookProc(HWND hdlg, UINT uiMsg, WPARAM wParam, LPARAM lParam) {
HICON hIcon;
int width, height, xLeft, yTop;
RECT rectToCenterOn, rectSubDialog;
switch (uiMsg) {
case WM_INITDIALOG:
hIcon = LoadIcon(hInst, MAKEINTRESOURCE(IDI_PMMICO));
SendMessage(GetParent(hdlg), WM_SETICON, ICON_BIG, (LPARAM)hIcon);
SendMessage(GetParent(hdlg), WM_SETICON, ICON_SMALL, (LPARAM)hIcon);
GetWindowRect(GetDesktopWindow(), &rectToCenterOn);
GetWindowRect(GetParent(hdlg), &rectSubDialog);
width = rectSubDialog.right-rectSubDialog.left;
height = rectSubDialog.bottom-rectSubDialog.top;
xLeft = rectToCenterOn.right / 2 -
(width) / 2;
yTop = rectToCenterOn.bottom / 2 -
(height) / 2;
BOOL test = SetWindowPos(GetParent(hdlg), NULL, xLeft, yTop, width, height, SWP_NOSIZE);
return (INT_PTR)FALSE;
break;
}
return (INT_PTR)FALSE;
}
BOOL getNewFileName(HWND owner, wstring title, wstring defaultfile, LPWSTR filetypes, OPENFILENAME &ofn, wstring lastdir, wstring lastfile, int mode, wstring extension) {
wstring lastdir_pre(lastdir);
addPrefix(lastdir_pre);
if (lastfile.compare(L"") == 0) { lastfile = defaultfile; }
BOOL ret = false;
wchar_t Buffer[30000];
ofn.lStructSize = sizeof(OPENFILENAME);
ofn.hwndOwner = owner;
ofn.lpstrFile = Buffer;
lastfile.copy(ofn.lpstrFile,lastfile.size(),0);
ofn.lpstrFile[lastfile.size()] = '\0';
ofn.nMaxFile = 30000;
ofn.Flags = OFN_OVERWRITEPROMPT | OFN_ENABLEHOOK | OFN_EXPLORER;
ofn.lpfnHook = OFNHookProc;
ofn.lpstrFilter = filetypes;
ofn.lpstrCustomFilter = NULL;
ofn.nFilterIndex = 0;
ofn.lpstrInitialDir = lastdir_pre.c_str();
ofn.lpstrFileTitle = NULL;
ofn.lpstrDefExt = extension.c_str();
ofn.lpstrTitle = title.c_str();
if (mode == 1) {
ofn.Flags = ofn.Flags | OFN_PATHMUSTEXIST;
ret = GetOpenFileName(&ofn);
} else if (mode == 2) {
ret = GetSaveFileName(&ofn);
}
if (ret == false) { ofn.lpstrFile[0] = '\0'; }
return ret;
}