It's also one of the first. Win32's origins extend back over 35 years and start on machines with a tiny fraction of the capability of even the smallest of today's modern PC's. It was also built with a different set of tradeoffs and in a radically different culture of software development. (Most modern developers hadn't been born at the time of it's initial design, and most of the people who were actively writing this stuff in the early-to-mid 1980's, I'm sure have moved on. 35 years is pretty much a career.)
> MFC is also quite bad because of huge abstraction leakages; it fills like Win32 with bolted on classes.
That's pretty much what it was... by design. There was a more object-oriented library that Microsoft developed, prior to MFC. They tested it on developers that had essentially just come up to speed on the (then-new) Win16 API, who all complained about having to ascend another learning curve for a fancy object oriented language and framework. Microsoft's reaction was to drop the older framework (referred to as AFX) and develop MFC as a thin wrapper around Win16. (This is part of why there are AFX prefixes scattered throughout the MFC codebase.... it's a legacy of the earlier framework.)
Even then, early versions of MFC had some utility, mainly around making things more type safe. Because it bound C++ instances to Window system instances, it made it easy to attach user data structures to UI components. (Otherwise, you were worrying about window or class words, which were Microsoft's original approach to that problem and used by MFC under the hood.) MFC also handled parsing of window message arguments. Win16 also sent messages with just a word and a long, when what you really might need is a set of mouse button flags and an x/y position or something. MFC helped with that too, by 'cracking' the message arguments into something closer to what you'd expect.
(To this day, Win32 documentation still includes instructions on parsing WPARAMS, etc.
https://docs.microsoft.com/en-us/windows/win32/inputdev/wm-m... )
MFC is horrible, I agree. I've had to work with it and the indirection just gets in the way and creates bloat. That is overengineering.
I have used wxWidgets a lot and really like it, but for modern C++ on Windows what do Microsoft recommend?
I can't seem to get any idea. Honestly, I would like to know.
I do not know what MS would recommend these days. From my point of view they basically functionally abandoned it but dragged it along because most of their stuff was built with it. The .NET libs was where all the new stuff was going (WPF, WinUI). WTL may be worth a look it looks like it comes out of the ATL/MFC lineage.
Especially when you take into account that the first GUI application MS made was Excel for the Macintosh. And then they more-or-less wrote Windows as a runtime environment for porting Excel to PCs.
Not getting into any of that old-school MS-stole-the-GUI flamewar business, I just think it's genuinely historically interesting to note the parallels when you play with each.
Maybe I haven't done enough WinAPI programming, but where is that true? I know there are a few helper functions that automatically dispatch an event to a callback, but I thought in general all events had to be intercepted and dispatched in the message loop
So the question is, back then was there any better GUI programming layers?
And the answer is yes, there was actually an API that was better and it was called OS/2.
At that time Microsoft was in a partnership with IBM to develop OS/2.
However, when the partnership fell apart, Microsoft just took big chunks of that OS/2 API and created a sub par version and called it the Windows API.
Microsoft learned from the mistakes IBM forced on them and did a better job. Right off the top of my head:
* IBM forced 80286 compatibility in an 80386 world.
* IBM forced incompatibility between Windows and OS/2 for the sake of preserving their mainframe graphics API's.
* OS/2 had a single messaging queue for the whole desktop.
* OS/2 was tied to the underlying hardware to the extent of being written partly in assembler.
OS/2 was great... I loved OS/2 2.0 in particular (and I worked for IBM testing OS/2 LAN Server for a summer)... but IBM had no idea how to address the market and no sense of how fast it was evolving.
In a more Microsoft-centric world, I'm pretty sure the OS/2 API would've been exactly as you describe it and almost strictly in parallel with Windows. In fact, Microsoft did exactly this with Win32s (and Windows 95) In their relationship with Windows NT (which was once known as OS/2 NT or OS/2 3.0).
The same compiled binary could run on both the 'entry level' OS and the 'server level' OS, with a bit of care taken in the way the API was used.
That's a fairly broad description, isn't it? At least I have a hard time coming up with windowing API models that don't fundamentally work that way at the lower levels. (About the only exception think of is a text-based library that shipped with Microsoft BASIC 7.0, and that was mainly because the language didn't support any of the abstractions needed for callbacks.)
However OS/2 had many other layers to it's programming SDK that were not found in early Windows.
For example there was the Dos layer for things like processes, threads, semaphores, files, directories etc.
And then there was the Gdi layer for graphics.
Most of that functionality only made it's way into Windows with the advent of Windows NT (Windows 3.x/95 had poorer versions of those functions. For example running a process and capturing it's output was a real pain in Windows 3.x and Windows 95).
And based on the fact so many of those OS/2 Dos function have an equivalent Windows NT version I suspect Microsoft used that OS/2 design as their starting point for NT.
As just one of many examples consider DosCreateThread from OS/2 1.x
http://www.edm2.com/index.php/DosCreateThread_(OS/2_1.x)
It looks a lot like the CreateThread function found in Win32:
https://docs.microsoft.com/en-us/windows/win32/api/processth...
Maybe I just haven't had my coffee yet, but I'm not understanding what this is supposed to mean.
MFC is also quite bad because of huge abstraction leakages; it fills like Win32 with bolted on classes.
It seems like Win32 happened a bit by accident, a bit by overengineering and a bit by Microsoft's attempt to lock everyone to their 'special' development environments, which did not include C as a conscious choice by Microsoft.