我收到错误消息无法访问已处置的对象.对象名称:'ApplicationProperties'.当我在关闭它之后尝试重新打开表单时.我注意到这是从退出表单,并退出是"处置"它们,所以我已将以下代码放在我的所有接受按钮,并取消按钮(任何关闭表单的按钮).
this.Hide();
this.Parent = null;
Run Code Online (Sandbox Code Playgroud)
这段代码只是隐藏了表单.没有关闭表格.
所以我的问题是,当我单击表单上的"x"按钮,然后尝试重新打开表单时仍然会收到错误消息.我尝试了几种不同的方法来修改表单的现有功能,例如:
private void ApplicationProperties_FormClosing(object sender, FormClosingEventArgs e)
{
//Hiding the window, because closing it makes the window unaccessible.
this.Hide();
this.Parent = null;
}
Run Code Online (Sandbox Code Playgroud)
但这让我没有运气.我想知道是否有人知道如何解决这个问题.这是在我的取消和接受按钮内为我工作的代码.关闭表单的所有按钮都是一样的.
private void OptionsCancelbtn_Click(object sender, EventArgs e)
{
//Hiding the window, because closing it makes the window unaccessible.
this.Hide();
this.Parent = null;
}
Run Code Online (Sandbox Code Playgroud)
我已经在form1的类顶部声明了实例,并在form1中有一个打开form2的按钮.
public partial class MainBox : Form
{
//Making a name for the ApplicationProperties form. It can be opened when called.
ApplicationProperties ApplicationPropertiesWindow = new ApplicationProperties();
private void ApplicationPropertiesbtn_Click(object sender, EventArgs e)
{
//Show the properties window.
ApplicationPropertiesWindow.Show();
}//End ApplicationProperties button.
}
Run Code Online (Sandbox Code Playgroud)
在我使用第二个表单上的"x"按钮关闭程序后,由于发生错误消息,我无法再次访问form2 ApplicationPropertiesWindow.Show();
在form2中我有以下代码:
public partial class ApplicationProperties : Form
{
//Creates and sets the instance MainBoxWindow.
public MainBox MainBoxWindow { get; set; }
Run Code Online (Sandbox Code Playgroud)
在您的FormClosing活动中试试这个:
private void ApplicationProperties_FormClosing(object sender, FormClosingEventArgs e)
{
//Hiding the window, because closing it makes the window unaccessible.
this.Hide();
this.Parent = null;
e.Cancel = true; //hides the form, cancels closing event
}
Run Code Online (Sandbox Code Playgroud)
因为现在它仍在关闭表格,因此仍然导致错误.
在我使用第二个表单上的“x”按钮关闭程序后,我无法再次访问 form2,因为错误消息在
ApplicationPropertiesWindow.Show();
当表单关闭 ( Form.Close) 时,表单本身及其所有相关资源都将被释放。这种自动处理只有两个例外,如文档中所述:
ShowDialog(而不是Show)显示为模态对话框。它以这种方式设计,以便您可以在用户关闭对话框后访问对话框的属性(例如,检索用户输入)。在这两种特殊情况下,您负责手动调用Dispose表单的方法。第二种情况是迄今为止最常见的(没有人真正使用 MDI 范式了),并且可以通过以下using语句轻松处理:
using (MyDialogBox dlg = new MyDialogBox())
{
DialogResult result = dlg.ShowModal(this);
if (result == DialogResult.Yes)
{
// access members of "dlg", and
// do whatever the user asked
}
} // the Dispose method is automatically called here
Run Code Online (Sandbox Code Playgroud)
在您的情况下,通常情况下,对该Close方法的调用正在关闭和销毁表单。您已经知道您无法访问已处理的对象(因为它不再存在!),这就是您在尝试显示它时收到异常的原因。为了在关闭后再次显示表单,您需要创建表单类的新实例:
MyForm frm = new MyForm();
frm.Show();
// ...
frm.Close();
Run Code Online (Sandbox Code Playgroud)
这确实是最好的方法。表单的新实例将与您要关闭的实例相同,因为它是从同一类创建的。您最好从面向对象的角度开始思考,并尽可能避免基于单例的设计。屏幕上显示的每个表单都是一个新的独立对象。一旦该对象被关闭并销毁,您就不能再使用它。如果要再次使用它,则需要创建一个新对象并显示它。
该Hide方法更像是一种技巧,仅当您想暂时隐藏表单的当前实例同时仍保留其状态(例如,其成员属性的值、其控件状态等)时才有用。这仅适用于永远不会被销毁的单例对象,并且必须仔细设计和维护。这也意味着这个表单对象一直在消耗资源,不管它是否被使用,都是浪费。
如果您必须这样做,您需要追踪导致您的表单实例被处理的原因。没有看到您的所有代码,我很难做任何事情,只能猜测问题可能出在哪里。它可能与您对AcceptButton和/或CancelButton属性的使用有关。无论哪种方式,最好和最干净的解决方案是覆盖该OnFormClosing方法并防止您的表单被关闭。你会隐藏它:
public class MyForm : Form
{
protected virtual void OnFormClosing(FormClosingEventArgs e)
{
// Prevent the form from closing.
e.Cancel = true;
// Hide it instead.
this.Hide();
}
// ...other code in your form class
}
Run Code Online (Sandbox Code Playgroud)
这样做的好处是您只需将代码放在一个地方,位于负责类的本地,而不是暴露给外部代码并分散在整个应用程序中。当然,它还可以防止表单被您控制之外的框架代码关闭。
我不知道你为什么将Parent属性设置为null. 顶级窗口(所有表单都是如此)永远不会有父窗口。只有子窗口(例如控件)有父窗口。它可以有一个所有者,但不一定。这取决于您在调用该Show方法时是否将所有者窗口作为参数传递。