Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
503 views
in Technique[技术] by (71.8m points)

c# - Setting a Windows form to be bottommost

Some background

One of my current clients runs a chain of Internet points where customers an access the net through PC:s set up as "kiosks" (a custom-built application "locks" the computer until a user has signed in, and the running account is heavily restricted through the Windows group policy). Currently, each computer is running Windows XP and uses Active Desktop to display advertisements in the background. However, since my client has got problems with Active Desktop crashing on a daily basis (in addition to generally slowing down the computer) I have been asked to develop an application that replaces it.

The problem

I am trying to investigate whether it is possible to build a Windows forms application (using C#) that always stays in the background. The application should lie above the desktop (so that it covers any icons, files etc) but always behind all other running applications. I guess I'm really looking for a BottomMost property of the Form class (which doesn't exist, of course).

Any tips or pointers on how to achieve this would be highly appreciated.

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

This isn't directly supported by the .NET Form class, so you have two options:

1) Use the Win32 API SetWindowPos function.

pinvoke.net shows how to declare this for use in C#:

[DllImport("user32.dll")]
static extern bool SetWindowPos(IntPtr hWnd, IntPtr hWndInsertAfter, int X, int Y, int cx, int cy, uint uFlags);

static readonly IntPtr HWND_BOTTOM = new IntPtr(1);
const UInt32 SWP_NOSIZE = 0x0001;
const UInt32 SWP_NOMOVE = 0x0002;
const UInt32 SWP_NOACTIVATE = 0x0010;

So in your code, call:

SetWindowPos(Handle, HWND_BOTTOM, 0, 0, 0, 0, SWP_NOMOVE | SWP_NOSIZE | SWP_NOACTIVATE);

As you commented, this moves the form to the bottom of the z-order but doesn't keep it there. The only workaround I can see for this is to call SetWindowPos from the Form_Load and Form_Activate events. If your application is maximized and the user is unable to move or minimise the form then you might get away with this approach, but it's still something of a hack. Also the user might see a slight "flicker" if the form gets brought to the front of the z-order before the SetWindowPos call gets made.


2) subclass the form, override the WndProc function and intercept the WM_WINDOWPOSCHANGING Windows message, setting the SWP_NOZORDER flag (taken from this page).


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...