Disable or Hide Minimize, Maximize and Close Buttons in C# Windows Forms

A patient check-in kiosk that anyone can maximize, minimize or close halfway through isn’t much of a kiosk.

Quick answer: you disable minimize and maximize buttons in C# Windows Forms by setting MaximizeBox and MinimizeBox to false. Set ControlBox = false to remove the close button too:

MaximizeBox = false;   // Maximize greyed out
MinimizeBox = false;   // with both false, both disappear
ControlBox = false;    // no Minimize, Maximize, Close or icon

We ran each setting on .NET 10 in a small clinic check-in app and captured the real title bars, including two close-button tricks that only look locked.

What You Need Before You Start

You need Windows and the .NET 10 SDK. Each example is a Windows Forms file-based app: one .cs file you run with dotnet run File.cs.

The #:property lines target net10.0-windows with Windows Forms on; PublishAot=false turns off Native AOT, which Windows Forms doesn’t support. New to this? See how to create a console application in Visual Studio Code.

Step 1: Hide the Maximize and Minimize Buttons with MaximizeBox and MinimizeBox

Our sample is a check-in app for a Boise, Idaho clinic. We opened seven forms, one setting each, and captured them running:

#:property TargetFramework=net10.0-windows
#:property UseWindowsForms=true
#:property PublishAot=false

class Program
{
    [STAThread]
    static void Main()
    {
        ApplicationConfiguration.Initialize();
        Form[] forms =
        [
            Make("1. Default (Sizable)", f => { }),
            Make("2. MaximizeBox = false", f => f.MaximizeBox = false),
            Make("3. MinimizeBox = false", f => f.MinimizeBox = false),
            Make("4. MaximizeBox and MinimizeBox = false", f => { f.MaximizeBox = false; f.MinimizeBox = false; }),
            Make("5. ControlBox = false", f => f.ControlBox = false),
            Make("6. FixedDialog only", f => f.FormBorderStyle = FormBorderStyle.FixedDialog),
            Make("7. FixedToolWindow", f => f.FormBorderStyle = FormBorderStyle.FixedToolWindow),
        ];
        int open = forms.Length;
        for (int i = 0; i < forms.Length; i++)
        {
            forms[i].Location = new Point(40, 40 + i * 100);
            forms[i].FormClosed += (_, _) => { if (--open == 0) Application.ExitThread(); };
            forms[i].Show();
        }
        Application.Run();
    }

    static Form Make(string title, Action<Form> setup)
    {
        var form = new Form { Text = title, StartPosition = FormStartPosition.Manual, ClientSize = new Size(600, 40) };
        setup(form);
        return form;
    }
}
Seven real WinForms title bars on .NET 10: default, MaximizeBox false with a greyed maximize button, MinimizeBox false, both false showing only the close button, ControlBox false with no buttons, FixedDialog and FixedToolWindow
What each setting really does to the title bar on Windows 11

Set only one of the two to false and Windows greys that button out. Set both to false and both disappear, leaving just the close (X) button.

You can’t hide Maximize alone and keep Minimize; that takes a custom title bar. I’ve found the greyed button is fine for most apps.

Step 2: Hide the Close Button and Icon with ControlBox = false

Row 5 shows ControlBox = false: every button and the icon are gone. Per Microsoft Learn, it only works with the FixedSingle, Sizable, Fixed3D or FixedDialog border styles.

Without an X, add a Done button that calls Close(), wired up with a normal event handler in C#.

Step 3: Stop Resizing with FormBorderStyle (FixedSingle, FixedDialog, None)

Hiding Maximize doesn’t stop a user from dragging the border. For that, set FormBorderStyle to FixedSingle or FixedDialog (default: Sizable).

Row 6 is a gotcha: FixedDialog alone drops the icon but keeps Minimize and Maximize. Row 7, FixedToolWindow, keeps only a slim X, and None removes the title bar.

FormBorderStyle is an enum in C#, so the Designer and your code share the same values.

Step 4: Disable Only the Close (X) Button with CS_NOCLOSE

There’s no CloseBox property. To grey out just the X while keeping the others, override CreateParams and add the Win32 class style CS_NOCLOSE (0x200):

#:property TargetFramework=net10.0-windows
#:property UseWindowsForms=true
#:property PublishAot=false

class Program
{
    [STAThread]
    static void Main()
    {
        ApplicationConfiguration.Initialize();
        Application.Run(new CheckInForm());
    }
}

class CheckInForm : Form
{
    const int CS_NOCLOSE = 0x200;     // Win32 class style: disables Close on the window menu

    public CheckInForm()
    {
        Text = "Cedar Creek Clinic - Patient Check-In";
        ClientSize = new Size(560, 160);
        MaximizeBox = false;
        FormBorderStyle = FormBorderStyle.FixedSingle;
        Controls.Add(new Label
        {
            Text = "Welcome! Tap your name to check in for today's visit.",
            Font = new Font("Segoe UI", 12),
            AutoSize = true, Left = 24, Top = 24
        });
        FormClosing += (_, e) => Console.WriteLine($"FormClosing raised: {e.CloseReason}");
    }

    protected override CreateParams CreateParams
    {
        get
        {
            CreateParams cp = base.CreateParams;
            cp.ClassStyle |= CS_NOCLOSE;
            return cp;
        }
    }
}

Output (after the close test below):

FormClosing raised: UserClosing
Cedar Creek Clinic Patient Check-In form on .NET 10 with the close (X) button greyed out by CS_NOCLOSE and the maximize button disabled
CS_NOCLOSE greys out the X; MaximizeBox = false greys out Maximize

CreateParams is a protected virtual property, so this is plain method overriding in C#: call base, add the flag, return it.

Important: I then sent the window SC_CLOSE, the command the X button sends. The form closed anyway and printed the line above. CS_NOCLOSE changes how the button looks, so pair it with the check in Step 5.

Step 5: Block the Close Button in FormClosing with CloseReason.UserClosing

To really stop a close, handle FormClosing and set e.Cancel = true when e.CloseReason is UserClosing, the reason Learn lists for the X button and Alt+F4.

Here a timer stands in for a staff PIN check and unlocks the window after 5 seconds. Both handlers are lambdas, a short form of an anonymous method in C#:

#:property TargetFramework=net10.0-windows
#:property UseWindowsForms=true
#:property PublishAot=false

class Program
{
    [STAThread]
    static void Main()
    {
        var form = new Form { Text = "Cedar Creek Clinic - Front Desk" };
        var staffPin = new System.Windows.Forms.Timer { Interval = 5000 };
        bool unlocked = false;
        form.FormClosing += (_, e) =>
        {
            e.Cancel = e.CloseReason == CloseReason.UserClosing && !unlocked;
            Console.WriteLine($"{e.CloseReason}: {(e.Cancel ? "blocked" : "closing")}");
        };
        staffPin.Tick += (_, _) => { unlocked = true; form.Close(); };
        staffPin.Start();
        Application.Run(form);
    }
}

Output:

UserClosing: blocked
UserClosing: closing
VS Code running FormClosingGuard.cs on .NET 10: the X button close prints UserClosing blocked, then the unlocked Close prints UserClosing closing
The X click is blocked; after the unlock, Close() goes through

While it ran, I sent it the X button’s SC_CLOSE: that’s the blocked line. Then the timer unlocked and closed it.

Your own Close() call also arrives as UserClosing, which is why the flag exists. Application.Exit() arrives as ApplicationExitCall.

How Do You Change MaximizeBox and MinimizeBox at Runtime?

Just set them again; the open window updates. Our setup screen turns the buttons off on Start kiosk mode:

#:property TargetFramework=net10.0-windows
#:property UseWindowsForms=true
#:property PublishAot=false

class Program
{
    [STAThread]
    static void Main()
    {
        ApplicationConfiguration.Initialize();
        Application.Run(new SetupForm());
    }
}

class SetupForm : Form
{
    readonly Button btnLock = new() { Text = "Start kiosk mode", Left = 24, Top = 24, Width = 180, Height = 36 };

    public SetupForm()
    {
        Text = "Cedar Creek Clinic - Kiosk Setup";
        ClientSize = new Size(560, 90);
        Controls.Add(btnLock);
        btnLock.Click += (_, _) =>
        {
            MaximizeBox = false;
            MinimizeBox = false;
            FormBorderStyle = FormBorderStyle.FixedSingle;
            btnLock.Enabled = false;
        };
    }
}
Before and after on .NET 10: the Kiosk Setup form shows minimize, maximize and close buttons, and after Start kiosk mode only the close button remains
Setting MaximizeBox and MinimizeBox at runtime updates the open window

To go back, set both to true and the border to Sizable. SetupForm sets them on itself because it inherits from Form.

Should You Hide the Buttons in the Designer or in Code?

Either works, because the Properties window just writes code into Form1.Designer.cs:

this.FormBorderStyle = System.Windows.Forms.FormBorderStyle.FixedSingle;
this.MaximizeBox = false;
this.MinimizeBox = false;

That file is half of a partial class in C#. I use the Designer for fixed settings and code for runtime changes.

Minimize, Maximize and Close Button Cheat Sheet

GoalSettingResult we saw
Grey out MaximizeMaximizeBox = falseMaximize greyed out
Grey out MinimizeMinimizeBox = falseMinimize greyed out
Hide Minimize and Maximizeboth falseOnly the X is left
Hide all buttons and the iconControlBox = falseCaption text only
Block resizingFixedSingle or FixedDialogBorder can’t be dragged
Grey out only the XCS_NOCLOSE in CreateParamsX greyed, still closable
Stop closing for realFormClosing + UserClosingX blocked

Common Mistakes to Avoid When You Disable the Buttons

FormBorderStyle.None without a way out. With no title bar, the form can’t be moved or closed by mouse. Add your own close button.

Forgetting ShowInTaskbar on tool windows. A FixedToolWindow form still needs ShowInTaskbar = false to stay off the taskbar; it defaults to true.

Trusting a greyed X. ControlBox = false and CS_NOCLOSE change the title bar, not the close path. Only FormClosing catches Alt+F4 and programmatic closes.

Maximized MDI children. ControlBox = false has no effect on an MDI child that’s maximized when it’s created.

Next Steps

Next, let staff pick an export folder with the folder browser dialog in C#, built the same file-based way.

We’d read these next for the rest of a small WinForms tool:

Frequently Asked Questions

How do I disable the maximize button in a C# Windows Form?

Set MaximizeBox = false in the Properties window or in code. The button stays visible but greyed out.

How do I remove the minimize, maximize and close buttons in C#?

Set ControlBox = false to hide all three and the icon. See the Form.ControlBox reference on Microsoft Learn for the border styles it needs.

How do I disable only the close (X) button?

Add CS_NOCLOSE (0x200) to ClassStyle in a CreateParams override, and cancel UserClosing in FormClosing to really block it.

Does Alt+F4 still close a form with ControlBox = false?

Don’t rely on the missing button. Alt+F4 raises FormClosing with CloseReason.UserClosing, so cancel it there. The CloseReason enum lists every reason.

How do I stop users from resizing a Windows Form?

Set FormBorderStyle to FixedSingle or FixedDialog and MaximizeBox to false.