Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Create owner drawn menus with C++, 2012-style

The goal of my quest is simple -- add icons to my context menu that is displayed through a call to TrackPopupMenu API. But evidently coding for Windows is like paddling with a spoon and there's no easy way of adding icons besides making owner drawn menus. So I did some search that came up with a bunch of C++ code on the subject of owner drawn menus, but so far I can't find any that would work for me. The reason is simple -- the menus it draws look like something that came out from Windows 95... So is there any way to do owner-drawn menus that have default Windows 7 look?

PS. If there's an easier way of adding icons to menu items, say, LoadIcon then ChangeMenuItem to set it, I'd appreciate if someone could show me how, because I'd gladly go with it instead...

PS2. OK, it takes way too long for my liking. Why can't I seem to do the simplest task in this OS :( I made a small test project to illustrate the issue. I load the bitmap with my own CreatePARGBBitmapFromIcon method that converts an icon into a PARGB bitmap (as was suggested below) and then displays it in two places: CStatic control (middle of the screen, that looks just fine), and in the menu item (that totally f's it up.) Here's the screenshot from Windows 7 and XP (both look totally different):

enter image description here

enter image description here

So guys, seriously, what am I missing here????

PS3. Thanks to @DavidHeffernan, I was able to fix it. Here's the working C++/MFC solution, here's an article the solution is based on, and here're a couple of screenshots:

enter image description hereenter image description here

Just FYI, it took me around 2 days to get this solved -- something that would've taken about 2 minutes on OS X, or iOS ...

And lastly a couple of my favorite quotes from the source article that I totally endorse:

All those hacks and recipes would be worthless if only there was simple consistent API for making menu item icons. Unfortunately menu icons, something that was always present in Windows and Microsoft applications, never got any decent API, moreover the methods to get those icons working change for every major Windows release, making us developers wasting our time “porting” our applications to new “shinny” Windows rather than doing something productive.

and this sums it up nicely:

AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAARGH! Why is Microsoft filled by idiots???

like image 649
c00000fd Avatar asked Dec 01 '12 21:12

c00000fd


1 Answers

This article tells you how to do it: http://www.nanoant.com/programming/themed-menus-icons-a-complete-vista-xp-solution

In summary, on XP you should pass HBMMENU_CALLBACK in the hbmpItem field of the MENUITEMINFO struct. This makes your menu owner draw, but you only need to deal with the icon in WM_MEASUREITEM and WM_DRAWITEM.

On Vista and up you put a PARGB32 bitmap (pre-multiplied alpha, 32 bit color depth) in hbmpItem and let the system draw the menu. So, no owner draw on Vista and up. Although the theme API does offer functionality for painting menus, it is fiendishly difficult to get right and there's really no need since you can let the system do it.

like image 160
David Heffernan Avatar answered Nov 02 '22 06:11

David Heffernan