Creating a immovable windows’ form in c#

June 5, 2006

Recently there were many posts asking about "creating a immovable form in .NET". I guess there are three approaches:

1. Make the property FormBorder=None and repaint the minimize, maximize and close buttons with custom bitmaps and set the event handlers respectively.

2. Keep the FormBorder as it is and try to save the initial position of the form in a Point. Then restore the location to the initial point when ever the Form's LocationChanged event is hit.

System.Drawing.Point initialLocation; 
private void Form1_Load(object sender, System.EventArgs e)
{
initialLocation=this.Location;
}

private void Form1_LocationChanged(object sender,System.EventArgs e) 
{
Me.Location = initLocation;
}

This causes flickering of the form though the purpose is served.

3. Next the last and complex method is overridding the WinProc to disable the [Move] menuitem from the system menu.


[DllImport("user32.dll")]
private static extern Int32 EnableMenuItem ( System.IntPtr hMenu , Int32 uIDEnableItem, Int32 uEnable);
private const Int32 HTCAPTION = 0x00000002;
private const Int32 MF_BYCOMMAND =0x00000000;
private const Int32 MF_ENABLED =0x00000000;
private const Int32 MF_GRAYED =0x00000001;
private const Int32 MF_DISABLED =0x00000002;
private const Int32 SC_MOVE = 0xF010;
private const Int32 WM_NCLBUTTONDOWN = 0xA1;
private const Int32 WM_SYSCOMMAND = 0x112;
private const Int32 WM_INITMENUPOPUP = 0x117;

protected override void WndProc(ref System.Windows.Forms.Message m )
{
if( m.Msg == WM_INITMENUPOPUP )
{
//handles popup of system menu

if ((m.LParam.ToInt32() / 65536) != 0 ) // 'divide by 65536 to get hiword

{
Int32 AbleFlags = MF_ENABLED;
if (!Moveable)
{
AbleFlags = MF_DISABLED | MF_GRAYED; // disable the move

}
EnableMenuItem(m.WParam, SC_MOVE, MF_BYCOMMAND | AbleFlags);
}
}if(!Moveable)
{
if(m.Msg==WM_NCLBUTTONDOWN) //cancels the drag this is IMP

{if(m.WParam.ToInt32()==HTCAPTION) return;
}
if (m.Msg==WM_SYSCOMMAND) // Cancels any clicks on move menu

{
if ((m.WParam.ToInt32() & 0xFFF0) == SC_MOVE) return;
}
}
base.WndProc(ref m);
}

This is how you can disable the form being moved.
Enjoy

-Bugs!

About these ads

10 Responses to “Creating a immovable windows’ form in c#”

  1. cipher_nemo Says:

    Thanks for sharing this, but you failed to mention that the user will neeed to add a using statement (using System.Runtime.InteropServices) to use the DllImport command. Also, where is “Moveable” defined? That isn’t created or defined any where. Thanks.

  2. Vaibhav Says:

    Hi cipher_nemo,
    Thanks for you comments,
    “Moveable” will just be a bool depending on your needs, and my apologies for not taking that in to consideration.

    Yes, indeed you need reference to InteropServices for DllImport. I have not considered any references thinking that users already know it :) my mistake again.

    Thanks a lot of the pointing out the issues.

    -Bugs!

  3. venki Says:

    I want clear explanation about this pgm.

  4. reo63 Says:

    This is brilliant! You are awesome!

    If you are unable to figure out Moveable is a
    member boolean you have to add yourself and
    assign to false, you do not deserve to steal this wonderful piece of code.

    I really like it because if you try the approach #2,
    you will see your cpu usage go bananas in the
    Windows Task Manager when you try to move the window…
    And method #3 keeps everything relatively flat
    (provided you haven’t already got too much stuff going
    on to begin with).

    Thanks!

  5. Vaibhav Says:

    To Venki,

    Hey, pls. let me know what have u not understood?
    The method 3 is a native code just wrapped in c#.
    All the constants are defined in vc (msdn)

    WinProc is a callback message handler, which is the basic for windows message handling…

    Do read about the message handling done in old days VC.

    Still, need more info. write to me at vaibhav[dot]gaikwad[at]gmail[dot]com

    Happy Coding..
    -Bugs!

  6. b-- Says:

    Even easier way:

    protected override void WndProc(ref Message message)
    {
    const int WM_SYSCOMMAND = 0x0112;
    const int SC_MOVE = 0xF010;

    switch(message.Msg)
    {
    case WM_SYSCOMMAND:
    int command = message.WParam.ToInt32() & 0xfff0;
    if (command == SC_MOVE)
    return;
    break;
    }

    base.WndProc(ref message);
    }

  7. Vaibhav Says:

    Yes, this might also do, but I haven’t tried it.

    Thanks,
    -Bugs!

  8. snakereef Says:

    Hi, there!

    It’s a great code!!!
    It’s very helpful too!!!

    But, I’m with a doubt…

    How can I put it in a class ?

    I have a project with a lot of forms (using a MDI Container) and I want to avoid to put it in all the forms…

    thanks a lot!

    []s

    João Luiz


  9. […] a feeling during this link. You competence be prying in choice #3. It will need we to hang some internal code, though should […]


  10. […] a feeling during this link. You competence be prying in choice #3. It will need we to hang some internal code, though should […]


Leave a Reply

Please log in using one of these methods to post your comment:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

Follow

Get every new post delivered to your Inbox.

%d bloggers like this: