Date: | May 5, 2005 / year-entry #113 |
Tags: | code |
Orig Link: | https://blogs.msdn.microsoft.com/oldnewthing/20050505-04/?p=35703 |
Comments: | 44 |
Summary: | For some reason, people think too hard. If you want to create a fullscreen window that covers the taskbar, just create a fullscreen window and the taskbar will automatically get out of the way. Don't go around hunting for the taskbar and poking it; let it do its thing. As always, start with the scratch... |
For some reason, people think too hard. If you want to create a fullscreen window that covers the taskbar, just create a fullscreen window and the taskbar will automatically get out of the way. Don't go around hunting for the taskbar and poking it; let it do its thing. As always, start with the scratch program and add the following: HWND CreateFullscreenWindow(HWND hwnd) { HMONITOR hmon = MonitorFromWindow(hwnd, MONITOR_DEFAULTTONEAREST); MONITORINFO mi = { sizeof(mi) }; if (!GetMonitorInfo(hmon, &mi)) return NULL; return CreateWindow(TEXT("static"), TEXT("something interesting might go here"), WS_POPUP | WS_VISIBLE, mi.rcMonitor.left, mi.rcMonitor.top, mi.rcMonitor.right - mi.rcMonitor.left, mi.rcMonitor.bottom - mi.rcMonitor.top, hwnd, NULL, g_hinst, 0); } void OnChar(HWND hwnd, TCHAR ch, int cRepeat) { if (ch == TEXT(' ')) { CreateFullscreenWindow(hwnd); } } HANDLE_MSG(hwnd, WM_CHAR, OnChar);
Note that this sample program doesn't worry about destroying that
fullscreen window or preventing the user from creating more than one.
It's just a sample.
The point is seeing how the
We use
the
I've seen people hunt for the taskbar window and then do
a First is a mental exercise you should always use when evaluating tricks like this: "What if two programs tried this trick?" Now you have two programs both of which think they are in charge of hiding and showing the taskbar, neither of which is coordinating with the other. The result is a mess. One program hides the taskbar, then the other does, then the first decides it's finished so it unhides the taskbar, but the second program wasn't finished yet and gets a visible taskbar when it thought it should be hidden. Things only go downhill from there. Second, what if your program crashes before it gets a chance to unhide the taskbar? The taskbar is now permanently hidden and the user has to log off and back on to get their taskbar back. That's not very nice. Third, what if there is no taskbar at all? It is common in Terminal Server scenarios to run programs by themselves without Explorer [archived]. In this configuration, there is no Explorer, no taskbar. Or maybe you're running on a future version of Windows that doesn't have a taskbar, it having been replaced by some other mechanism. What will your program do now? Don't do any of this messing with the taskbar. Just create your fullscreen window and let the taskbar do its thing automatically. |
Comments (44)
Comments are closed. |
Your coding style has little to be desired. Do you normally code that way to be difficult to read with bad indenting? Glad you dont work here.
Come on now, that’s just rude. Code style is a relative thing; what looks perfectly readable to you may not be to someone not used to it.
Back on topic, it seems like lots of programmers purposely look for the hardest way to do something. Instead of just creating a full size window and seeing what the task bar does they start out by assuming that they need to write complicated code to hide the task bar.
The link to the Terminal Server page is throwing a 404 – guess there’s a typo there
No this isn’t my normal coding style. I have to alter it to conserve space and because nobody wants to read 200 lines of boring code in a blog entry.
I reckon if a future version of Windows doesn’t have a taskbar, it’ll still be forced to pretend it does, for compatibility with misbehaved apps; the same way that there’s still a PROGMAN window for installers to have DDE conversations with in WinXP.
Then again, the ill-behaved program could be running on NT 3.51 which certainly doesn’t have a taskbar.
Coding style is not a relative thing when trying to convey information or in a workplace.
The link "run programs by themselves without Explorer" is broken.
My apologies if this is too off-topic.
I use an autohide taskbar, and there are times that I’m using a maximized application, and moving the cursor to the edge of the window where the taskbar is hiding doesn’t bring up the taskbar. I have to Alt-Tab to another application or use the windows key to bring it up. This doesn’t happen all the time, and I haven’t been able to find any pattern to the behavior. I’m pretty sure that the applications aren’t doing anything intentionally to cause this, because one of them is VS.NET 2003, and another is my application. It also happens to some of our customers. I don’t imagine that VS is doing anything, and I know I’m not messing with the taskbar. I’m also not using CreateFullscreenWindow().
Is there anything else that will block access to the taskbar?
The expression is "leaves a lot to be desired". What you said is actually a compliment, it says that his coding style is almost perfect.
Uh, ignore that last comment, I read it as "leaves little", not "has little".
Now that we know how to make a full screen window, I ask that the developers out there use this feature sparingly. Such a feature could easly be abused. I personally like my taskbar and don’t want it covered except in limited instances such as full screen games (e.g. Unreal Tournament), and maybe the occasional full screen web browsing session.
I think the link should be http://www.microsoft.com/resources/documentation/windows/xp/all/proddocs/en-us/mstsc_start_program.mspx. Terminal Services allows you to specify a program to be started – in effect that program is then the shell. When that program is closed, your session ends. You can still disconnect from the server, and leave the program running, as usual.
Another case where Explorer isn’t the shell is if you boot in ‘Safe Mode with Command Prompt’. In this case your shell is CMD.EXE, the NT command interpreter.
Should that not be:
mi.rcMonitor.right – mi.rcMonitor.left + 1
and
mi.rcMonitor.bottom – mi.rcMonitor.top + 1
??
<quote>
Or maybe you’re running on a future version of Windows that doesn’t have a taskbar, it having been replaced by some other mechanism. What will your program do now?
</quote>
Clearly these application wouldn’t even run. They’d either crash from sending a undocumented windows messages to explorer and mucking with internal data structures (now changed in Windows 2020)… or adding 60 to the NM_DBLCLK notify struct for coords, or maybe they’d simply refuse to start with incorrectly OS version checks… geesh I think I read this blog WAY too much…
Meh, what are you on, man? Raymond is a lvl 900 ninja coder. He could cast a 1200 damage VC++ spell as an afterthought. Also, he knows Itanium assembly. Pour out your Haterade.
Ah, but what will your program do when, in the future, people have stopped using monitors altogether and are using retina implants?
meh, when you have spent fifteen years like Raymond has, helping literally millions of developers via USENET and this blog, when you have personally developed major parts of the most widely used operating system in the world, when you have an incredibly deep knowledge of Windows programming and can share it with Raymond’s amazing clarity, then come back here and complain about the standard of a code sample.
Frank: Try it and see. Report back your findings.
I use Aloe Vera impregnated kitchen towels after I stop kissing Raymond’s bottom as it leaves my goate beard smoother and refreshed.
This is slight OT:
In WinCE, the taskbar doesn’t play nicely. A maximized, fullscreen app will still be covered by the taskbar because by default the "Always on top" option is turned on and the "Auto hide" option is turned off. This is normal.
But what is not normal is that an app can set the registry keys[1] to hide the taskbar and then broadcast a WM_SETTINGCHANGE message (or send a WM_WININICHANGE message) and the taskbar will ignore it.
The only way to coax the taskbar to abide by its settings as the shell loads is to set these keys in the registry via the Platform Builder, which most app writers don’t have access to.
One of the common solutions in the CE newsgroups to this problem has been to use FindWindow("HHTaskBar") to find and hide the taskbar.
So I guess my point, if I have one, is that sometimes people think too hard, but other times they’re forced into bad solutions by people who didn’t think hard enough.
[1]
HKLMSOFTWAREMicrosoftShellOnTop
HKLMSOFTWAREMicrosoftShellAutoHide
Where is it documented that whacking registry keys is the correct way to change Taskbar settings on WinCE? Tomorrow I’ll talk about the documented way of changing Taskbar settings on XP. And it doesn’t involve whacking registry keys.
Raymond: Since the Taskbar itself sets this registry key when a user clicks the "Always on top" checkbox, it seems a little bit heavy-handed to call it "whacking the registry," doesn’t it?
At any rate, I’m looking forward to tomorrow’s post.
Raymond,
maybe you can answer this question: Your code above does create a proper fullscreen window. I’ve been using similar code for my fullscreen windows, yet some applications e.g. MSN Messenger push their toast windows on top of mine, even though the TOPMOST style bit is set. Other apps, such as Windows Media Player don’t get the toasts pushed on top of them – how is an application supposed to detect the presence of a fullscreen app and specifically how does Messenger do it?
The Taskbar is allowed to modify its internal data. But other people aren’t. I fail to see what’s so unfair about this. I’m sure your code prbably wasn’t designed for other programs to mess with its internal data structures either.
MSN Messenger toasts appear on top of my Media Player window. Maybe yours is configured differently? You can have multiple topmost windows and clearly only one of them can win.
Frank, RECT’s in Windows have 1 added to the right and the bottom for a number of reasons that I believe Raymond discussed months ago in this blog.
One widely used program that hunts for the taskbar window and explicitly hides it is Apple’s QuickTime Player, when the user plays a file full-screen using Ctrl+F.
What makes it worse is that QuickTime Player often fails to unhide the taskbar window when it comes back out of full-screen mode. It’s infuriating.
It happens often enough that I ended up writing a tiny utility that hunts for the taskbar window and unhides it, and binding that utility to a global keyboard shortcut.
Maybe the upcoming QuickTime 7 will finally fix the problem.
Honestly, I stopped counting the number of times I’ve found myself needing to restart the Explorer process to get my taskbar back; likewise, I stopped counting the number of uninstallers I’ve run to get rid of the programs that forced me to do that. :) Good advice, indeed, Raymond.
(And lemme give you a hint, meh — you’d absolutely *kill* to have Raymond working wherever you happen to have found a sucker gullible enough to hire you.)
Raymond,
Your reaction to people "whacking" the registry reminded me of this snippet from MS’s tweakomatic utility (http://www.microsoft.com/technet/scriptcenter/tools/twkmatic.mspx#EJAA) documentation.
As you probably know, Microsoft has a sort of love-hate relationship with the registry. The registry is the configuration database for Windows and Windows applications, and many options can only be set by manually changing a value in the registry. For example, if you’ve ever read a Microsoft Knowledge Base article, you’ve likely seen a sentence similar to this:
“To correct this problem, change the following value in the registry.”
Now that’s fine, except that this sentence is invariably followed by a disclaimer similar to this one:
Warning
Don’t ever change a value in the registry. Ever. We know we just told you to do that, but would you jump off a cliff if we told you to? Don’t ever change a value in the registry. Don’t even say the word registry. We know a guy once who said the word registry, and three days later he was hit by a bus. True story. As a matter of fact, you shouldn’t even have a registry on your computer. If you suspect that you do have a registry on your computer, please call us and a trained professional will be dispatched to your office to remove the registry immediately. If you accidentally touch the registry, wash your hands with soap and water and call a doctor. Do not swallow the registry or get it in your eyes!
You can use shells other than Explorer on any version of Windows, and then you’ll likely have no taskbar. I doubt it would cause any trouble with naughty apps in this case, in fact it might be better because then they won’t succeed in hiding the shell’s goodies.
The interesting thing for me is *how* the shell detects a full-screen window. IIRC there’s a notification, but it’s not entirely reliable. (ISTR that IE windows can give false positives or somesuch) Then there’s ITaskbarList2::MarkFullscreenWindow, but I doubt many use it. (new in XP)
I think boxmonkey is referring to the fact that most of the settings that Tweakomatic allows you to tweak are THROUGH the registry and not through some API… [Check out all the Windows Explorer related settings in Tweakomatic!]
Therefore, it seems like in some cases even MS acknowledges that tweaking settings (NOT troubleshooting) through messing with the registry is OK.
Specifically, you mean that the Tweakomatic part of MS approves of registry hacking. The shell team disapproves.
Yes, except I don’t see how anyone not working with or for Microsoft can fathom this difference.
[OK, I’m being obtuse. You can if you try hard enough — but it seems that life would be easier if at least MS could present a consistent face to the external world.]
Yes, I know I always expect HP’s printer, server, and soho sales departments to always be in sync in prices, PR, strategy, and best practices. Because everything the company does gets vetted by the CEO. Right?
MS is the same as HP or IBM, with gazillions of departments; just because they almost all do software or software support doesn’t mean they’re on the same page.
Besides, tweakomatic comes with one of those huge DO THIS AT YOUR OWN RISK disclaimers.
Sigh. Apparently people fail to distinguish between information for *troubleshooting* purposes and information for general use.
Use SHAppBarMessage
I posted a comment here last night (regarding the need for documentation and the tweaks needed for frame windows to go full screen) and it received a couple of replies but is no longer here. If this was deliberate, that is fine but it didn’t appear controversial to me so could indicate that the site software has problems.
The server software is being upgraded – I’m told that comments lost during the upgrade will be restored when the upgrade is complete.
Neil, forget what I said earlier about the WS_POPUP window style. What matters is whether the window has a title bar and a sizing border (WS_CAPTION+WS_THICKFRAME), see "Taskbar Display Options" at MSDN:
http://msdn.microsoft.com/library/en-us/shellcc/platform/shell/programmersguide/shell_int/shell_int_programming/taskbar.asp
Oops.. in my previous comment I meant to say
"applications like MSN Messenger", but I left off
the "Messenger" by mistake. Also, I wanted to clarify that I realize WM_PAINT gets sent when one window has moved over another, but I just wanted to know if there was a more specific message (b/c WM_PAINT could have been sent for any number of reasons, especially in a game).
Thanks, in advance, anyone who cares to respond.
Michael Ruck had posted about applications like
MSN, that also use topmost windows, appearing on top of your fullscreen window. I was curious about the same thing. Sorry if this is a dumb question, but I am new to Win32 programming and have not found an answer to it using search engines or MSDN. Is there a message that gets posted to a window when another window appears above any part of it? I am guessing that if one were to handle that message, they could push the offending window back under the fullscreen window (assuming this is in an application like a game, where you would want to do that b/c some people do not want other things appearing while they are playing). Is that wrong, or is there an easier way?
"push the offending window back" – That just creates an arms race. More on this subject on June 7th.
Speaking of leaving the taskbar alone…
Not that I’ve ever had spyware on my own PC, but I thought I’d try out Microsoft "AntiSpyware Beta". I ran a scan and then forgot about it.
A few hours later, when I tried to start Cygwin, a notification window warning me about something or other comes up. The window slides up from the bottom right corner of the screen and perches itself atop the taskbar.
Of course, that’s what it was trying to do. But since I align my taskbar to the right of the screen, instead the notification just shot upwards until it fell off the top of my screen.
It was kind of cute.
PingBack from http://www.hilpers.com/954263-taskleiste-ausblenden