关闭Windows窗体时提示用户保存更改的能力

3
我正在使用C# Windows Forms(.NET 3.5),并尝试实现以下功能:当用户修改详细表单上的任何数据列,并在没有保存的情况下尝试关闭表单时,系统应该弹出我的消息"保存更改?"
我知道我可以始终为文本框等使用TextChanged事件,但这需要多个事件编码。我想使用一个特定的事件处理程序,它检测与我的BindingSource相关联的任何字段中的值的更改。
我已经像这样绑定了我的列:
textbox1.DataBindings.Add("Text", this.bindingSource1, "dbcolumn_1", true);
3个回答

1

这样的东西可行吗?

  1. 在表单中定义一个changedFlag变量,初始值为false。

    private changedFlag = false; // 表单值已更改,在关闭表单时检查

  2. 将以下代码放入退出按钮的事件处理程序中,或者调整为表单关闭处理程序:

        if (this.changedFlag && MessageBox.Show("保存更改后再退出吗?", "保存更改?", MessageBoxButtons.OKCancel) == DialogResult.OK)
        {
            this.Save();
        }
    
  3. 创建一个函数,该函数接受一个控件容器并递归地查找其控件以连接更改处理程序(在步骤4中定义)。

    private void AddOnChangeHandlerToInputControls(Control ctrl)
    {
        foreach (Control subctrl in ctrl.Controls)
        {
            if (subctrl is TextBox)
            {
                ((TextBox)subctrl).TextChanged += new EventHandler(InputControls_OnChange);
            }
            else if (subctrl is CheckBox)
            {
                ((CheckBox)subctrl).CheckedChanged += new EventHandler(InputControls_OnChange);
            }
            else if (subctrl is RadioButton)
            {
                ((RadioButton)subctrl).CheckedChanged += new EventHandler(InputControls_OnChange);
            }
            else if (subctrl is ListBox)
            {
                ((ListBox)subctrl).SelectedIndexChanged += new EventHandler(InputControls_OnChange);
            }
            else if (subctrl is ComboBox)
            {
                ((ComboBox)subctrl).SelectedIndexChanged += new EventHandler(InputControls_OnChange);
            }
            else
            {
                if (subctrl.Controls.Count > 0)
                {
                    this.AddOnChangeHandlerToInputControls(subctrl);
                }
            }
        }
    }
    
  4. 创建一个通用的更改处理程序函数,将changedFlag设置为true。

    private void InputControls_OnChange(object sender, EventArgs e)
    {
        this.changedFlag = true;
    }
    
  5. 一旦您的控件构建完成(不确定是否动态生成,但您在示例中使用了textbox1,因此我假设没有),请从步骤3调用该函数并传入输入的容器控件。

    AddOnChangeHandlerToInputControls(panelFormContainer);

通过传递表单控件的容器,您可以避免为每个控件手动连接更改处理程序。并且请记住修改Save()函数以重置changedFlag = false;

0

nothingIsNecessary的答案非常接近,但我仍然需要查找一下才能使其正常工作。

问题在于

AddOnChangeHandlerToInputControls(panelFormContainer);

应该是

AddOnChangeHandlerToInputControls(this);

panelFormContainer不起作用,我也找不到相关文档。

参考资料:循环遍历表单上的所有控件,甚至其中的分组框

另外,根据需要,我还添加了更多的控件类型。

对于日期选择器,我使用了MouseCaptureChanged,因为复选框有时会触发ValueChanged事件,有时却不会。¯_(ツ)_/¯

private void AddOnChangeHandlerToInputControls(Control ctrl) 
    {
        foreach (Control subctrl in ctrl.Controls)
        {
            if (subctrl is TextBox)
            {
                ((TextBox)subctrl).TextChanged += new EventHandler(InputControls_OnChange);
            }
            else if (subctrl is CheckBox)
            {
                ((CheckBox)subctrl).CheckedChanged += new EventHandler(InputControls_OnChange);
            }
            else if (subctrl is RadioButton)
            {
                ((RadioButton)subctrl).CheckedChanged += new EventHandler(InputControls_OnChange);
            }
            else if (subctrl is ListBox)
            {
                ((ListBox)subctrl).SelectedIndexChanged += new EventHandler(InputControls_OnChange);
            }
            else if (subctrl is ComboBox)
            {
                ((ComboBox)subctrl).SelectedIndexChanged += new EventHandler(InputControls_OnChange);
            }
            else if (subctrl is MaskedTextBox)
            {
                ((MaskedTextBox)subctrl).TextChanged += new EventHandler(InputControls_OnChange);
            }
            else if (subctrl is DateTimePicker)
            {
                ((DateTimePicker)subctrl).MouseCaptureChanged += new EventHandler(InputControls_OnChange);
            }
            else if (subctrl is RichTextBox)
            {
                ((RichTextBox)subctrl).TextChanged += new EventHandler(InputControls_OnChange);
            }
            else if (subctrl is NumericUpDown)
            {
                ((NumericUpDown)subctrl).TextChanged += new EventHandler(InputControls_OnChange);
            }
            else
            {
                if (subctrl.Controls.Count > 0)
                {
                    this.AddOnChangeHandlerToInputControls(subctrl);
                }
            }
        }
    }

0

谢谢您的回复。我的表单中有大约80个字段,包括TextBox、Combobox、checkbox等,它们都与BindingSource和DataTable相关联。我希望找到一个解决方案,只需处理BindingSource或DataTable即可,而不是在on_closing事件处理程序中将每个字段与其原始值进行比较,以检查是否有任何更改。谢谢。 - AGR090808

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接