Создавал ProgressBar. Получилось. После того как в пример Iczelion'a посмотрел. Вопросы появились следующие: 1) Почему после mov InitCtrls.dwSize, sizeof INITCOMMONCONTROLSEX mov InitCtrls.dwICC, ICC_PROGRESS_CLASS invoke InitCommonControlsEx, ADDR InitCtrls Винда отвечает, что класс уже существует? Я его до этих строк не регистрировал. 2) Почему пример Microsoft из MSDN InitCommonControls(); hwndPB = CreateWindowEx(0, PROGRESS_CLASS, (LPSTR) NULL, WS_CHILD | WS_VISIBLE, Вариант С++ rcClient.left, rcClient.bottom cyVScroll, rcClient.right, cyVScroll, hwndParent, (HMENU) 0, g_hinst, NULL); pbProgressIndClass db "PROGRESS_CLASS", 0 invoke InitCommonControls invoke CreateWindowEx, NULL, ADDR pbProgressIndClass, NULL,\ WS_CHILD or WS_VISIBLE,\ Вариант Asm 8, 160, 425, 17, hWin, NULL, hInstance, NULL mov hpbProgressInd, eax не работает? А работает только тогда, если PROGRESS_CLASS заменить на msctls_progress32, как у Iczelion'a? Получается, что MSDN врёт?
#define PROGRESS_CLASSA "msctls_progress32" Это GetLastError отвечает? А ты его когда вызываешь, всегда или только если InitCommonControlsEx возвращает 0?
Вряд ли. Описание значений поля dwICC: dwICC Set of bit flags that indicate which common control classes will be loaded from the DLL. This value can be a combination of the following: ICC_ANIMATE_CLASS Load animate control class. ICC_BAR_CLASSES Load toolbar, status bar, trackbar, and ToolTip control classes. ICC_COOL_CLASSES Load rebar control class. ICC_DATE_CLASSES Load date and time picker control class. ICC_HOTKEY_CLASS Load hot key control class. ICC_INTERNET_CLASSES Load IP address class. ICC_LINK_CLASS Load a hyperlink control class. ICC_LISTVIEW_CLASSES Load list-view and header control classes. ICC_NATIVEFNTCTL_CLASS Load a native font control class. ICC_PAGESCROLLER_CLASS Load pager control class. ICC_PROGRESS_CLASS Load progress bar control class. ICC_STANDARD_CLASSES Load one of the intrinsic User32 control classes. The user controls include button, edit, static, listbox, combobox, and scrollbar. ICC_TAB_CLASSES Load tab and ToolTip control classes. ICC_TREEVIEW_CLASSES Load tree-view and ToolTip control classes. ICC_UPDOWN_CLASS Load up-down control class. ICC_USEREX_CLASSES Load ComboBoxEx class. ICC_WIN95_CLASSES Load animate control, header, hot key, list-view, progress bar, status bar, tab, ToolTip, toolbar, trackbar, tree-view, and up-down control classes. IceStudent Вот полный текст программы из MSDN. Здесь нет #define PROGRESS_CLASSA "msctls_progress32". Код (Text): // ParseALargeFile - parses a large file and uses a // progress bar to indicate the progress of the // parsing operation. // Returns TRUE if successful, or FALSE otherwise. // hwndParent - parent window of the progress bar. // lpszFileName - name of the file to parse. // // Global variable // g_hinst - instance handle extern HINSTANCE g_hinst; BOOL ParseALargeFile(HWND hwndParent, LPSTR lpszFileName) { RECT rcClient; // Client area of parent window int cyVScroll; // Height of scroll bar arrow HWND hwndPB; // Handle of progress bar HANDLE hFile; // Handle of file DWORD cb; // Size of file and count of // bytes read LPCH pch; // Address of data read from // file LPCH pchTmp; // Temporary pointer // Ensure that the common control DLL is loaded // and create a progress bar along the bottom of // the client area of the parent window. // Base the height of the progress bar on the // height of a scroll bar arrow. InitCommonControls(); GetClientRect(hwndParent, &rcClient); cyVScroll = GetSystemMetrics(SM_CYVSCROLL); hwndPB = CreateWindowEx(0, PROGRESS_CLASS, (LPSTR) NULL, WS_CHILD | WS_VISIBLE, rcClient.left, rcClient.bottom cyVScroll, rcClient.right, cyVScroll, hwndParent, (HMENU) 0, g_hinst, NULL); // Open the file for reading, and retrieve the // size of the file. hFile = CreateFile(lpszFileName, GENERIC_READ, FILE_SHARE_READ, (LPSECURITY_ATTRIBUTES) NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, (HANDLE) NULL); if (hFile == (HANDLE) INVALID_HANDLE_VALUE) return FALSE; cb = GetFileSize(hFile, (LPDWORD) NULL); // Set the range and increment of the progress // bar. SendMessage(hwndPB, PBM_SETRANGE, 0, MAKELPARAM(0, cb / 2048)); SendMessage(hwndPB, PBM_SETSTEP, (WPARAM) 1, 0); // Parse the file. pch = (LPCH) LocalAlloc(LPTR, sizeof(char) * 2048); pchTmp = pch; do { ReadFile(hFile, pchTmp, sizeof(char) * 2048, &cb, (LPOVERLAPPED) NULL); // TODO: Write an error handler to check that all the // requested data was read. . . // Include here any code that parses the // file. . // Advance the current position of the // progress bar by the increment. SendMessage(hwndPB, PBM_STEPIT, 0, 0); } while (cb); CloseHandle((HANDLE) hFile); DestroyWindow(hwndPB); return TRUE; } Хотя, может, статья устарела, и её не обновили вовремя. Соответствия между названиями классов и контролами нашёл в таблице, описывающей изменения классов в новой Висте. А то, что класс уже существует, показывает OllyDbg (ERROR_CLASS_ALREADY_EXISTS (00000582) ). GetLastError я вообще не вызываю. Возвращаемое значение InitCommonControlsEx равно 1(eax=1), если верить отладчику.
Zhelezovsky Смешались в кучу кони, люди и залпы тысячи орудий сплелись в кошмарный вой.. ICC_PROGRESS_CLASS и PROGRESS_CLASS. Найди 10 отличий. Зато есть в инклудах. Пробежись по ним и всё увидишь сам. А ты не верь всему, что тебе показывают. Вот лучше загляни в справочник (PSDK) и поищи в описании функции InitCommonControlsEx упоминание GetLastError. Нашёл? Я - нет. Но это скорее исключение. Чаще там написано примерно так: Теперь перечитай ещё раз и вдумайся. Потом перечитай ещё раз.
А если в описании функции не сказано, что для получения подробной информации об ошибке надо вызвать GetLastError, то она, в принципе, не должна влиять на это хранилище ошибок?
Zhelezovsky не должна влиять на это хранилище ошибок? Правильно написанная не должна. Т.е. должна содержать Код (Text): void foo(void) { DWORD dwErr = GetLastError(); ... SetLastError(dwErr); return; } Только полагаться на это не надо.