What’s the atom returned by RegisterClass useful for?

Date:October 11, 2004 / year-entry #363
Tags:history
Orig Link:https://blogs.msdn.microsoft.com/oldnewthing/20041011-00/?p=37603
Comments:    8
Summary:The RegisterClass and RegisterClassEx functions return an ATOM. What is that ATOM good for? The names of all registered window classes is kept in an atom table internal to USER32. The value returned by the class registration functions is that atom. You can also retrieve the atom for a window class by asking a window...

The RegisterClass and RegisterClassEx functions return an ATOM. What is that ATOM good for?

The names of all registered window classes is kept in an atom table internal to USER32. The value returned by the class registration functions is that atom. You can also retrieve the atom for a window class by asking a window of that class for its class atom via GetClassWord(hwnd, GCW_ATOM).

The atom can be converted to an integer atom via the MAKEINTATOM macro, which then can be used by functions that accept class names in the form of strings or atoms. The most common case is the lpClassName parameter to the CreateWindow macro and the CreateWindowEx function. Less commonly, you can also use it as the lpClassName parameter for the GetClassInfo and GetClassInfoEx functions. (Though why you would do this I can't figure out. In order to have the atom to pass to GetClassInfo in the first place, you must have registered the class (since that's what returns the atom), in which case why are you asking for information about a class that you registered?)

To convert a class name to a class atom, you can create a dummy window of that class and then do the aforementioned GetClassWord(hwnd, GCW_ATOM). Or you can take advantage of the fact that the return value from the GetClassInfoEx function is the atom for the class, cast to a BOOL. This lets you do the conversion without having to create a dummy window. (Beware, however, that GetClassInfoEx's return value is not the atom on Windows 95-derived operating systems.)

But what good is the atom?

Not much, really. Sure, it saves you from having to pass a string to functions like CreateWindow, but all it did was replace a string with with an integer you now have to save in a global variable for later use. What used to be a string that you could hard-code is now an atom that you have to keep track of. Unclear that you actually won anything there.

I guess you could use it to check quickly whether a window belongs to a particular class. You get the atom for that class (via GetClassInfo, say) and then get the atom for the window and compare them. But you can't cache the class atom since the class might get unregistered and then re-registered (which will give it a new atom number). And you can't prefetch the class atom since the class may not yet be registered at the point you prefetch it. (And as noted above, you can't cache the prefetched value anyway.) So this case is pretty much a non-starter anyway; you may as well use the GetClassName function and compare the resulting class name against the class you're looking for.

In other words, window class atoms are an anachronism. Like replacement dialog box classes, it's one of those generalities of the Win32 API that never really got off the ground, but which must be carried forward for backwards compatibility.

But at least now you know what they are.

[Typos fixed October 12.]


Comments (8)
  1. Cooney says:

    you can take advantage of the fact that the return value from the GetClassInfoEx function is the atom for the class, cast to a BOOL.

    Is this guaranteed, or is it subject to change in future versions?

  2. Ivo says:

    Yeah, I was wondering the same thing about casting to BOOL yesterday. The dialog procedure is supposed to handle some messages by casting the return value to BOOL instead of using DWL_MSGRESULT (WM_CTLCOLORBTN, WM_CTLCOLORSTATIC, etc, probably others). How does that translate to 64 bit? Is BOOL 64 bit, or is HBRUSH 32 bit on a 64 bit system?

  3. superclasser says:

    GetClassInfoEx is useful for superclassing.

  4. Raymond Chen says:

    Right, but why would you superclass a class that you yourself registered? Wouldn’t you just fix your original class? I can see superclassing somebody else’s class, but in that case you don’t have their atom since you didn’t call RegisterClass originally.

  5. doynax says:

    I’m using the ATOM as a handle when writing my win32 wrapper classes. Saves having to deal with string allocation, especially since the names were auto generated anyway.

    But why can’t I patch a window class without creating an actual window instance?

    This feels kinda strange since I can get a handle (i.e. the ATOM) and even retreive it’s data (GetClassInfoEx) without having a window around. Not to mention that I have to create a dummy window to subclass standard controls.

  6. Ryan Myers says:

    I use it for a similar reason to doynax. If you’re making a C++ wrapper for a window class and want to delete the wrapper as part of the destructor, you have to keep around either the name of the class or the atom returned by RegisterClassEx. Although I didn’t know about the legacy reasons for atoms — that might lead me to store it as a string instead.

  7. teebee says:

    I find it terribly helpful/useful to use the GCW_ATOM to determine the window class during the WM_NOTIFY processing of my C appication. Prior to using GCW_ATOM we used a strcmp loop through all the currently supported window classes we’ve implemented. The overhead of 30 or more strcmp and a strcpy seems much worse that a loop comparing 30 ATOMS.

Comments are closed.


*DISCLAIMER: I DO NOT OWN THIS CONTENT. If you are the owner and would like it removed, please contact me. The content herein is an archived reproduction of entries from Raymond Chen's "Old New Thing" Blog (most recent link is here). It may have slight formatting modifications for consistency and to improve readability.

WHY DID I DUPLICATE THIS CONTENT HERE? Let me first say this site has never had anything to sell and has never shown ads of any kind. I have nothing monetarily to gain by duplicating content here. Because I had made my own local copy of this content throughout the years, for ease of using tools like grep, I decided to put it online after I discovered some of the original content previously and publicly available, had disappeared approximately early to mid 2019. At the same time, I present the content in an easily accessible theme-agnostic way.

The information provided by Raymond's blog is, for all practical purposes, more authoritative on Windows Development than Microsoft's own MSDN documentation and should be considered supplemental reading to that documentation. The wealth of missing details provided by this blog that Microsoft could not or did not document about Windows over the years is vital enough, many would agree an online "backup" of these details is a necessary endeavor. Specifics include:

<-- Back to Old New Thing Archive Index