There is a whole series of SPI_SETxxxANIMATION settings that let you control which screen elements animate.

Notice that when using the SPI_SET* commands, you also have to choose whether the setting changes are temporary (lost at logoff) or persistent. The historically-named SPIF_UPDATEINIFILE flag causes the changes to be saved to the user profile; if you leave it off, then the changes are not saved and are lost when the user logs off. You should also set the SPIF_SENDCHANGE flag so that programs which want to refresh themselves in response to changes in the settings can do so.

The fact that there exist both temporary and persistent changes highlights the danger of accessing the registry directly to read or write the current settings. If the current settings are temporary, then they are not saved in the registry. The SystemParametersInfo function retrieves the actual current settings, including temporary ones. For example, if you want to query whether menus are being animated, and the user has temporarily disabled animation, reading the registry will tell you that they are being animated when in fact they are not.

Also, changes written to the registry don't take effect untll the next logon, because that is the only time the values are consulted. To make a change take effect immediately, you must use SystemParametersInfo.

It still puzzles me why people go to the undocumented registry keys to change these settings when there is a perfectly good documented function for doing it. Especially when the documented function works and the undocumented registry key is unreliable.

I remember one application that went straight for the undocumented registry keys (to get the icon title font, I think). Unfortunately for the application, the format of the registry key is different between Windows 95 and Windows 2000, and it ended up crashing. (It expected the Windows 95 format.) If it had used the documented method of retrieving the icon title font, it would have worked fine. In other words, this program went out of its way to go around the preferred way of doing something and got hoist by its own petard.

A contributory factor may be that most SystemParametersInfo options aren’t supported by Windows as a whole, only by specific versions of it; so if you’re writing an application that is to run on Windows, you have to wrap most SystemParametersInfo calls with fallback code to deal with the case when the user’s particular version of Windows doesn’t support that particular option.

It makes perfect sense once you know about it, the problem is how to know about it. Its similarily difficult to know exactly what is undocumented and not recommended. "Undocumented" is the same as "a document that exists but I can’t find" and "a document I didn’t look for".

This isn’t to excuse bad application behaviour, but it can help explain it.

People use the registry keys because they can browse the registry a lot easier than they can browse through the functions of the Win32 API. Since people don’t necessarily understand the design decisions of the underlying systems, they don’t know about temporary settings and such.

Basically, if you are trying to figure things out, it’s easier to browse the registry than it is to consult MSDN, and what’s in the registry seems to make plenty of sense because it’s so nice and readable.

The fact that you don’t understand it honestly shows that you’re too close to the system. Now that I know Win32 better and can figure it out, I don’t make those kinds of mistakes, but 90% of people don’t have time to memorize so much. There’s only so much you can push into your head before other stuff gets pushed out :)

Dummy registry keys could help. It might be handy to have a document that mapped system registry keys to APIs so that after a coder browses the registry to find the right (wrong) key, they could find the right way to do it.

But I think the real solution is the .NET Framework. Using the object browser, it’s pretty easy to find System.Windows.Forms.SystemInformation and see all of its properties. And Longhorn promises a comprehensive managed API.

"It still puzzles me why people go to the undocumented registry keys to change these settings when there is a perfectly good documented function for doing it. Especially when the documented function works and the undocumented registry key is unreliable."

I agree with the others, it can be hard to find the right API for the job. Take a simple example, change the wallpaper. No matter how hard you look, the obvious choices just don’t exist; SetWallpaper, SetSystemWallpaper, SetDeskWallpaper, etc. In fact I’m not aware of a single Win32 or Shell API that has "wallpaper" in it. So if you’ve never done this before it’s rather difficult to find the SPI_SETDESKWALLPAPER option for the SystemParametersInfo API. Sure if you do enough searches you’ll eventually find it, but many developers would give up before that and just go for the registry key which is easy to find and change.

The good news is that SystemParametersInfo’s interface is so incredibly complicated that you HAVE to spend the time reading the docs to understand it. This is in contrast to RegEnumKeyEx’s subtle lpcName behavior, which is easy to overlook.

Let’s see, uiParam passes in the size of what’s in pvParam, unless pvParam is pointing to an integral type. Not that this prevents errors, since many of the param struct sizes are identical (e.g., ACCESSTIMEOUT and FILTERKEYS, STICKYKEYS and TOGGLEKEYS). Sometimes pvParam isn’t a pointer at all, but a BOOL or other type passed by value.

I’ll add my "me too" to this thread. When I searched for "set wallpaper" on msdn.microsoft.com the top link was som KB article about "Using Paint Program and Active Desktop, Users Can Override Wallpaper Set by System Policy". WTF!?

Is there some list somewhere of all of the changes made if you select "Optimise for Best Performance" in that dialog box under System in Windows XP? (I don’t have a Windows XP box handy to check where exactly the option is, sadly.)

In particular I’m interested in how to programmatically switch from the "Luna" interface to the "Classic" interface. I regularly use computers on an Windows network which doesn’t support the profile roaming thing, so every time I log in I must reconfigure the system to suit myself. I briefly attempted to write a tool to automate this in the past, but couldn’t find all of the information I needed to programmatically do what I was doing manually.

It would be especially useful if I could do all of this with only temporary settings, as then I could use it for other people’s computers without messing up their stored profile settings. I’m a little wary, though: what happens if (for example) you open up the Display properties control panel and press OK while the temporary settings are in effect? Does it commit all of the temporary changes to the registry, or is it clever enough not to do that?

(In the past I did this kind of thing on Windows 2000 machines by exporting bits of the registry once I’d configured it all how I wanted it, then having a small tool which imported the registry file and did whatever was necessary to get the settings loaded. I seem to remember part of this involved killing off explorer.exe and starting it up again. It was horrible, but it was also quick and easy to do.)

Raymond said: "It still puzzles me why people go to the undocumented registry keys to change these settings when there is a perfectly good documented function for doing it."

It doesn’t surprise me at all.

The API is huge. It’s not always obvious that something is wrapped in an API. When Windows first started dictating how to organize my files with standard directorys like "Program Files" and "My Documents", many of us just thought it was a convention. It certainly wasn’t obvious that this was a configurable scheme that the system was fully aware of. It was just last year that I discovered the Shell functions to get handles on these special folders.

There is often more than one way to do something, as the previous commenter pointed out with SPI_GET_DOUBLECLICKTIME. Sometimes there are ways that seem equivalent but vary is subtle ways, like GetDeviceCaps(hdc, HORZRES/VERTRES) versus SPI_GETWORKAREA versus GetMonitorInfo() versus GetSystemMetrics().

Sometimes there isn’t an API for what you want to do, like finding the name and company of the registered user, but it seems obvious to explore the Registry for a workaround.

Sometimes the documentation is wrong. GetStockObject docs have had DEFAULT_GUI_FONT and SYSTEM_FONT wrong for who knows how long. (And do I have to use SPI_GETNONCLIENTMETRICS to determine the LOGFONT used in menus, or can I trust that it will always match DEFAULT_GUI_FONT?)

What the MSDN documentation needs is a giant index in the form: "If you want to do X, see API Y."

I don’t mean this as a slam against anyone. It’s just a list of the reasons why I’m not at all surprised that programmers often find something other than the right way to do what they need.

It would be like picking on you for not capitalizing Registry even though it’s clearly documented in one of the MS style guides as a word that should be documented. :-)

I think adding dummy values for comments in the registry isn’t the solution as it would make it larger and slow down systems.

But what about including the complete key name as a keyword in the recommanded API to use instead, so that once these developers found the key, a search on its path in MSDN will give them the function they’re looking for ?

Also, to change the desktop wallpaper, SPI_SETDESKWALLPAPER is outdated as it doesn’t work with non BMP images (ie JPEG, GIF and others, starting with IE4 Active Desktop).

IActiveDesktop::SetWallpaper is the new function for it, and SPI_SETDESKWALLPAPER should be used as a fallback when the ActiveDesktop interface is missing.

This is something that should be explained on the SystemParametersInfo page in MSDN Library IMO.

Speaking of SystemParametersInfo, it’d be nice if Windows Messenger would actually check to see if we had the minimize animations on when it "minimizes" to the task bar.

If someone is knowledgeable enough to disable the minimize animation, then its safe to assume they know where the system tray is and how it works. (Isn’t there a useless message box that comes up as well? Official IM clients always treat their users as if they were complete idiots it seems.)

Adding dummy keys to the registry might help but would only work for new Windows versions.

It might be more helpful if every relevant MSDN documentation contained a comment in the order of ‘Use this API function rather than changing registry key HLM/xxx/yyy’. The important thing here is that the registry key is spelled out explicitly so that searching for the registry key will find the correspondig API.

This would help at least those people who don’t just blindly change the registry value but try to figure out the consequences first.

using my standard approach when looking for unknown apis i searced the headers first. wallpaper returns 18 results in 3 files (mshtmcid.h, shlobj.h, winuser.h). a quick glance tells me im going to have to search msdn for iactivedesktop and spi_setdesktopwallpaper. at this point ive spent ~2 minutes and have a good idea of how do to what i need to.

admittedly, finding how to set the wallpaper is relatively easy using this approach compared to setting, say, the icon label font. font returns 4095 results…more than i want to look through. searching through the results for icon gives 2 matches, spi_geticontitlelogfont and spi_seticontitlelogfont. exactly what i want.

At this point, you should not stop, but instead continue to follow the steps.

2. Sort by location.

3. Look through for anything marked "Platform SDK". (This was easier with VC6, I think — now the prefixes to the words "Platform SDK" make this approach more time-consuming. Certainly not impossible, though.)

4. Note the only page in a "Platform SDK" section with a title that looks like it describe a Win32 functions is "SystemParametersInfo".

5. See nothing obvious, apart from the IActiveDesktop methods (put them on your mental queue). Therefore, use "SystemsParametersInfo" as a starting point, since, being a Win32 function, it’s slightly less unlikely to be the right answer than any of the other items, and it may provide some clues as to terminology or have something in the remarks section that points one in the right direction.

6. Look at it, read carefully, discover it is the one.

(Had you failed in step 6, you would have gone through your mental queue of items to look at for more clues. This is particularly handy for terminology. For example, my inclination would have been to search for "desktop background", and the presence of the "Wallpaper" items in the results would have given me a clue to try a search for "Wallpaper" if the "desktop background" search comes up with nothing.)

Obviously, I knew what to look for, which can help a bit :) But I’ve used this approach for a bunch of other stuff and always turned up trumps.

And sure enough, when I was looking for how to set the desktop background a few years ago, I found that very function pretty quickly.

I am on Raymond’s side for this kind of thing.

It might be a question of attitude. If you want to find something out, there is probably a function to do it, and you should look pretty hard to find it before giving up. If you have to resort to tweaking the registry, you’re going at it the wrong way, so try harder. (But I will admit that if the terminology is not what you expect, which it sometimes isn’t, then searching the registry can be helpful, as the names can give clues.)

Do other people not think this way? (Maybe not!) How hard does it have to be to find something before you resort to the dirty approach?

I’m not suggesting that the SDK docs are the greatest ever, just that the information is in there… somewhere… probably… and it sholud be given more than a cursory glance and a quick skim before resorting to ugly hacks.

P.S. please don’t get put off by my self-righteousness. My code is just as bad as yours :)

> A "readme" entry in those keys might also be helpful, even though I can forsee someone at a Windows Annoyances site writing an app to enum the whole registry and delete all values named "readme", for people who just can’t stand having all that "useless" data lying around. ;) <<

How about the reverse then? Microsoft could provide a .REG file for developers that would insert a whole bunch of "readme" keys into the registry.

Then as new tools are released they could also update the documentation in the registry.

"What the MSDN documentation needs is a giant index in the form: ‘If you want to do X, see API Y.’"

My thoughts exactly. This is something that has been needed since the beginning, and it’s what made programming in Win32/MFC so frustrating when I started out. I’d be like "ok, I want to do this. I know it’s possible, 99% of windows programs do it." and I’d spend 3 days digging through the documentation before I’d finally find what I needed.

Seems to me that the simplest, most standard, and most "discoverable" way of solving the registry key documentation problem would be to put them in a help file and enable context sensitive help in regedit/regedt32.

FFS. The whole point is that you don’t go buggering about in the registry. Adding help to regedit would just encourage this behaviour.

A better enhancement to regedit would be context-sensitive help of a different manner. It would watch for you searching for data that could me manipulated by an API and, if it detects you are doing this, print up a big message box calling you a cu

While we’re on about tweaking system setup without using the registry, I’ve been wondering if there’s any way to programmatically:

Set the default position of: the dialog that comes up when you hit CTRL-ALT-DEL, the dialog that comes up when you lock/unlock your computer and the dialog that comes up asking you to log in.

I know it’s a pointless little thing, but I do like to see my desktop wallpaper, and I always have at least 20 windows open, so the only time I ever get to see it is when I’ve locked my computer or logged out, but then the aforementioned dialog box is covering the wallpaper in the center. What I’d really like to do is move it to the upper right hand corner programmatically. Is this possible?

i don’t think adding stuff to the registry is the right way to go. you see, imo, the problem is not the systemparameters relevant registry keys. the problem is the documentation: it is possible to find stuff in msdn, but it’s hard.

this is beeing caused by the docs beeing somewhat ‘short’ – and not very well linked.

in a lot of cases, the docs don’t even contain any really useful information, so it’s necessary to actually write simple test programs to check out what the docs really want to say.

and this is the case with the win32 api docs as well as with the .net docs.

to be fair: msdn imo is by far better than any other documentation i’ve seen from other companies (especially when taking into account how much stuff is in there) – however, they still leave much to be desired…. as becomes obvious, when people are using strange methods (like tweaking reg keys) when ‘official’ apis are available.

iow: i think adding to the registry is not the way to go. adding to the quality of the docs would be more apropriate…

My example about the setting the wallpaper seems to have been a popular one, many people have since commented on it. I agree just because a quick 2 minute search doesn’t yield the correct API doesn’t mean you should give up and go straight for the undocumented reg key. But setting the wallpaper is a very simple example, what about more complex problems? How long are you supposed to look for an API before you give up and do it another way?

Another example from a problem I faced recently, I needed to know if a registry hive was volatile or persisted to disk on shutdown. I could not find a "RegIsHiveVolatile" API. I never did find a function, in the end I resorted to comparing it against the list of persisted hives at HKLMSYSTEMCurrentControlSetControlhivelist.

"put them in a help file and enable context sensitive help in regedit/regedt32."

This also means that the help file will have to be translated into 20+ languages – because the rule for Windows is that everything has to be translated into every language – to address a small audience that probably all can read English anyway.

This is sort of off-topic, but while on the subject of desktop wallpapers and the equivalent settings for registry keys, the registry key HKEY_CURRENT_USERControl PanelDesktopWallpaper maps to that SPI_SETDESKWALLPAPER setting, but what about the various combinations of TileWallpaper and WallpaperStyle (which basically map to the Tile, Stretch and Center settings in the Display Properties dialog).

I haven’t been able to find the equivalent API which sets those settings. Probably just missed some obvious thing, however…

I’m not sure of the true solution to this problem. I like the solution you mention of a Wiki.

I would like some sort of integration with the local system. Like a registry editor that downloads some tree layout description data and will show you your local registry with the annotated documentation. Of course, not included with Windows. Maybe some small MSDN download. Anything that wouldn’t require the 100+ language translation you talk about.

I think this would pretty much be the holy grail of navigating the registry. regedit + downloadable documention that’s probably available in a wiki-type format online.

>How about a registry browser that includes documentation about various keys and values?

An *old* version of NU (from like 1997 or so) had this feature. They had their own registry editor with a 3-pane view, the bottom pane showed docs on whatever key you were currently looking at. I don’t know why it didn’t survive, it seemed like a neat idea.

I like some of the suggestions I’ve seen, especially putting reg key names in the API docs pages so you can search on the key name to find the API.

A "readme" entry in those keys might also be helpful, even though I can forsee someone at a Windows Annoyances site writing an app to enum the whole registry and delete all values named "readme", for people who just can’t stand having all that "useless" data lying around. ;)

Information in the registry (where people are looking for it, regardless of whether they should be) and a wiki would be interesting.

There doesn’t seem to be a rule that the Windows API function names must be translated into 20 languages, so why would the registry hints need to be in 20 different languages?

I have much doubt that Microsoft would do the wiki right. My bet is on legal tying it up with lots of restrictive licensing and indemnification terms. Instead of making it public domain so any contributor can easily reuse the whole of the work they have partially contributed to and thereby increasing their incentive to build there. That’s based on my look at the wiki software a Microsoft employee did and what Microsoft is doing with it – I read the legal terms and walked away. There are better places to build things than there. And yes, if it’s PD people can reuse it. That’s part of the point – to make this stuff available everywhere, distributed by everyone, in anything.

Likely also that Microsoft wouldn’t use the wiki platform which has been best proved in the wild (Mediawiki).

Have some doubts on the culture also. Developers are developing applications and don’t necesarily (or generally at all if they have a choice) want to limit their market to Windows. Would Microsoft want to exclude porting and compatibility details for other platforms and interfaces or libraries? Developing with Windows as one target platform, but not the only one, that’s the sort information I’d be after.

But… I could be wrong. And I’d like to be.

I’m a bit biased on the wiki side though – I’m one of the technical team for the world’s largest and most popular wikis, hosted by Wikimedia. Though all my income-producing developing has been for Windows.

I know what you mean, Somebody, the level of distrust in the postings is rather high ;-)

Seriously, the only restriction Raymond has mentioned is that Microsoft is generally obligated to distribute official documentation in all languages. A community wiki would be excempt from this requirement, but would therefore be unofficial and unsupported — it’s a tradeoff.

BTW, The fact that Raymond is allowed to blog (as are many other Microsoft employees) should tell you that "legal tying it up" is unlikely.

Coming from someone whose main non-HTML UI experience is in nT logon scripts, I know why I constantly do it: I’ve been conditioned by a wide range of software that offers no APIs of any kind and rarely even have friendly interfaces. Almost everything I need to do via logon script has to be done by editing the registry or ini files. When I go to change windows settings if I’m in a hurry and can’t quickly find an api, I just naturally do the same – after all, the script runs prior to UI init, so I don’t have to worry about unrefreshed stale info.

I do consider it a cheap hack, and always try to replace it with more scalable methods when I come across them, but many times that’s the best I can do with an hour of googling when I’m building something and just need it to work for now.

Yes every user of MSDN knows how hard it can be to find some stuff. Some random stuff is easy but other random stuff is nearly impossible to find. Google is your friend in such cases. It still doesn’t always find everything, but it helps a lot. Finding APIs becomes almost as easy as finding undocumented registry keys…

3/9/2005 2:38 PM Raymond Chen

> the rule for Windows is that everything has

> to be translated into every language

At first I wondered where you got that from, but then noticed you meant Windows itself and not MSDN. Yeah that rule is obeyed in most of Windows. The Japanese version of MSDN is missing quite a lot of pages (neither Japanese nor English being present) and has a number of English-only pages.

> – to address a small audience that probably

> all can read English anyway.

Wrong. Most companies have a few employees who can speak English. That’s far removed from the idea that most employees speak English. Some of my co-workers have to ask for help even when they have English-language MSDN pages open on their screen.

My biggest gripe with MSDN is that it always manages to pull up the Windows CE documentation before anything else. I see where I can tell it to only search Windows CE, but I have yet to figure out how to tell it to never search Windows CE.

“What the MSDN documentation needs is a giant index in the form: ‘If you want to do X, see API Y.”

There is such index already. It called “Table of Contents”.

I read here a lot of lamentations about how difficult it is to retrieve information from MSDN. It’s so huge, its index is so immense, search delivers so many hits, etc. etc. It seems that people completely forgot to use anything besides Index and Search tabs. Of course there will be countless results for search “set wallpaper” when you search several GB of compressed text! But, hey, it’s so easy to type a few words and hit Search button, then let the MSDN to read my mind and figure out what I want to find.

If I don’t know what function to use I always start from TOC. Then rarely there is a need to fall back on index or brute force search. I’m using index only to quickly peep function’s parameters or class’ members. However, with help of IntelliSense I don’t need index most of the time. I’m using search quire rarely, only if I’m stuck or want to check whether there is some KB article on the topic. When I found what I need in Index or Search, then I always press Synchronize button to see where I am in the TOC. It always helps to read several topics before and after, too.

At the first time people reluctant to go to TOC. Because it requires thinking about what do you want to find before hitting buttons. And thinking is always painful. But once one’s accustomed to this habit it saves literary hours of tedious searches.

Sometimes it is hard to follow these "rules." Take for instance the Distributed Transaction Coordinator, or DTC for short. If you wanted to get or change any particular setting related to DTC you can’t do it the same way across OS versions. In Windows 2003, there is the IDtcNetworkAccessConfig interface you can use. To change the same settings on Windows XP, the registry appears the only option. Furthermore, the upcoming Windows 2003 SP1 DTC changes (which mirror the XP SP2 changes) has not updated the API to reflect the change (at least in the SP1 RC2 version of the SDK documentation). Specifically, there is no updated method of allowing or disallowing specific transaction permissions such as inbound or outbound, so the API is useless – back to registry keys! Checking the DTC authentication level never had an API – just some registry keys documented in a KB article. I hope they fix this oversight for the final SP1 release – but in the meantime, what is a developer expected to do?

If there’s no API to do it, then it might be worthwhile to take the risk of registry hacking. The important point is simply that there is a risk, and registry poking isn’t the best way; things may change, your program may break, and in any event you have to muck about with all that RegOpenKey stuff.

But some people seem to think of registry hacking as the first port of call. To me, this is akin to doing something like reading filenames by doing "system("dir>fred.txt")" and then extracting columns 30 and onwards of all lines of "fred.txt" except the first and last few. It’s a solution, sure, and it probably worked at the time, but it’s flaky as hell, and to top that off pointless because there is a documented API that will do it for you much more easily.

(I pick that fairly strange example because I’ve seen it done, and because most people will probably agree it’s not reliable.)

Just surprised that people are so willing to get down and dirty without worrying about it. It’s impossible, as always, to supply any hard-and-fast rules, because there are always exceptions. But as a guiding principle, it’s sensible to try as hard as possible to avoid registry poking…

4nt.exe starts the filenames at column 36, which of course is one potential problem :) There’s the whole DIRCMD can of worms, too, not to mention DOSKEY macros and whatnot. (That’s just in case there was any confusion that this could be made to work without a vast amount of effort and lots of confusing breakages along the way :)

"Of course there will be countless results for search “set wallpaper” when you search several GB of compressed text!"

Why is it searching so many documents in the first place? I went to MSDN not TechNet. Why would I care about wallpaper policies and how users can overwrite them?

"But, hey, it’s so easy to type a few words and hit Search button, then let the MSDN to read my mind and figure out what I want to find."

Yep. I’ll use the simplest and quickest way to find what I need. I’ve already got a whole load of crap in my head when I’m developing. I don’t need any more. The suggestion to use Google seems to work the best.

"At the first time people reluctant to go to TOC. Because it requires thinking about what do you want to find before hitting buttons. And thinking is always painful. But once one’s accustomed to this habit it saves literary hours of tedious searches. "

You find some rhyme and reason in the TOC. Good for you. I don’t. Which sub category of "Win32 and COM Development" should I expand to find out how to set the wallpaper? Graphics and Multimedia? Platform SDK? User Interface? Which sub-category? Which sub-sub-category? Isn’t a game of "The Great API Quest" fun when you have a deadline to meet?