How to enable common controls in a Windows app

2020-02-28 07:09发布

I'm trying to enable common controls in an application. I followed the steps given in this MSDN article, specifically the section Using ComCtl32.dll Version 6 in an Application That Uses Only Standard Extensions. But I can't get it to work.

The only thing I'm doing differently from the article is that I add the manifest information in Project Property Pages | Configuration Properties | Linker | Manifest File | Additional Manifest Dependencies. This is what I enter in the textbox:

"type='Win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' processorArchitecture='*' publicKeyToken='6595b64144ccf1df' language='*' xmlns='http://schemas.microsoft.com/developer/msbuild/2003'";%(AdditionalManifestDependencies)

When I check the generated manifest (MyApp.exe.intermediate.manifest), it looks correct.

I also add a link dependency to ComCtl32.lib in Project Properties | Configuration Properties | Linker | Input | Additional Dependencies. I also call InitCommonControlsEx at startup with the INITCOMMONCONTROLSEX structure initialized like this:

INITCOMMONCONTROLSEX icex;
icex.dwSize = sizeof(INITCOMMONCONTROLSEX);
icex.dwICC = ICC_STANDARD_CLASSES;

But the call to InitCommonControlsEx always returns FALSE (which means it failed). After some investigation I found out that the error code returned from GetLastError is ERROR_FILE_NOT_FOUND. What could be the problem?

UPDATE: I noticed something that could be related to the "file not found error". When I run the app from the debugger, one of the lines in the Output window is:

'MyApp.exe': Loaded 'C:\Windows\winsxs\x86_microsoft.windows.common-controls_6595b64144ccf1df_5.82.6002.18305_none_88f3a38569c2c436\comctl32.dll', Cannot find or open the PDB file

However, there are a bunch of similar lines for some of the more standard libraries like kernel32.lib, user32.lib, etc:

'MyApp.exe': Loaded 'C:\Windows\System32\ntdll.dll', Cannot find or open the PDB file

'MyApp.exe': Loaded 'C:\Windows\System32\kernel32.dll', Cannot find or open the PDB file

'MyApp.exe': Loaded 'C:\Windows\System32\msvcrt.dll', Cannot find or open the PDB file

'MyApp.exe': Loaded 'C:\Windows\System32\user32.dll', Cannot find or open the PDB file

Those lines always appear for any application, and it causes no problems. Could it be different for ComCtl32.dll?

标签: c++ winapi
2条回答
▲ chillily
2楼-- · 2020-02-28 07:37

OK. I did some homework on this and discovered something new myself. How I eventually got this to work was almost what you're trying to do:

  1. Go to Project/Properties/Linker/Manifest File/Additional Manifest Dependencies
  2. Enter the following text verbatim (meaning all single and double quotes exactly as below). This is all on a single line, btw.

    "type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' processorArchitecture='*' publicKeyToken='6595b64144ccf1df' language='*'"

  3. Save your settings an do a FULL project (if not solution) rebuild to force manifest and PCH regeneration.

Prior to doing this the following was in my load-list:

Loaded 'C:\Windows\winsxs\x86_microsoft.windows.common-controls_6595b64144ccf1df_5.82.7601.17514_none_ec83dffa859149af\comctl32.dll'

After hand-forcnig the manifest version for common controls, the load list now includes this (and properly answers TRUE to InitCommonControlsEx(), which is the point of all this in the first place):

Loaded 'C:\Windows\winsxs\x86_microsoft.windows.common-controls_6595b64144ccf1df_6.0.7601.17514_none_41e6975e2bd6f2b2\comctl32.dll'

Note: you can also do this with an in-source #pragma, ideally in your stdafx.h header, but I prefer it this way.

Hope it helps.

查看更多
家丑人穷心不美
3楼-- · 2020-02-28 07:58

No, the warnings about the PDB files are just there to tell you that you don't have debugging info for the Windows system DLLs. Getting a FALSE return from InitializeCommonControlsEx() is of course the key problem.

There is something wrong with the Additional Manifest Dependencies string you use. I tinkered with it for a while but couldn't find the flaw. It is often easier to specify linker options in your source code. Everything worked well when I used:

#include <CommCtrl.h>
#pragma comment(lib,"comctl32.lib")
#pragma comment(linker,"/manifestdependency:\"type='win32' name='Microsoft.Windows.Common-Controls' version='6.0.0.0' processorArchitecture='*' publicKeyToken='6595b64144ccf1df' language='*'\"")

Just copy and paste the above code snippet into one of your source files.

查看更多
登录 后发表回答