Reputation: 908
We would like under some circumstances to block the action of the close button in the title bar. The problem is that it's a MDI applications and it seems that we will have to add code in each forms to cancel the operation in the Closing
event handler. It seems that the child forms are the first to receive the event. There is no way to add code at a single place to cancel the close operation. Information on how the close event is propagated to the child form would be welcome. Is there a simple way of doing what we want to do?
Upvotes: 3
Views: 296
Reputation: 941665
Windows provides a way to do this, you can tinker with the system menu. Provides for nice feedback as well, the close button will actually look disabled. You can disable the SC_CLOSE command in the system menu. Best demonstrated with a sample form, get started by dropping a button on it:
using System.Runtime.InteropServices;
...
public partial class Form1 : Form {
public Form1() {
InitializeComponent();
button1.Click += new EventHandler(button1_Click);
}
private bool mCloseEnabled = true;
public bool CloseEnabled {
get { return mCloseEnabled; }
set {
if (value == mCloseEnabled) return;
mCloseEnabled = value;
setSystemMenu();
}
}
protected override void OnHandleCreated(EventArgs e) {
base.OnHandleCreated(e);
setSystemMenu();
}
private void setSystemMenu() {
IntPtr menu = GetSystemMenu(this.Handle, false);
EnableMenuItem(menu, SC_CLOSE, mCloseEnabled ? 0 : 1);
}
private const int SC_CLOSE = 0xf060;
[DllImport("user32.dll")]
private static extern IntPtr GetSystemMenu(IntPtr hWnd, bool revert);
[DllImport("user32.dll")]
private static extern int EnableMenuItem(IntPtr hMenu, int IDEnableItem, int wEnable);
private void button1_Click(object sender, EventArgs e) {
CloseEnabled = !CloseEnabled;
}
}
Upvotes: 3
Reputation: 5755
Michael already wrote the answer in the comments (just to add it here to the answers):
Create a single BaseFormsClass where you override the behaviour and then subclass your classes from the new BaseFormsClass.
Upvotes: 1