我如何从记忆中摧毁(免费)一张表格?

时间:2011-01-07 07:21:36

标签: delphi delphi-xe

我的项目中有2个表单(Form1和Form2),Form1是自动创建表单,但Form2是可用表单。 我怎么能创建Form2并卸载Form1?

我在此代码中收到“访问验证”错误。

这是Form1代码:

1.  uses Unit2;
//*********
2.  procedure TForm1.FormCreate(Sender: TObject);
3.  var a:TForm2;
4.  begin
5.      a := TForm2.Create(self);
6.      a.Show;
7.      self.free;  // Or self.destory;
8.  end;

感谢。


我将“Serg”代码修改为:

unit Unit1;

interface

uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls;

type
  TForm1 = class(TForm)
    Button1: TButton;
    procedure Button1Click(Sender: TObject);
  private
    { Private declarations }
  public
    { Public declarations }
  end;
var
  Form1: TForm1;

implementation

uses Unit2;

{$R *.dfm}

procedure TForm1.Button1Click(Sender: TObject);
begin
  Application.CreateForm(TForm2, Form2);
  Release;
end;

end.

///

program Project1;
uses
  Forms,
  Unit1 in 'Unit1.pas' {Form1},
  Unit2 in 'Unit2.pas' {Form2};
{$R *.res}
begin
  Application.Initialize;
  Application.MainFormOnTaskbar := True;
  Form1:= TForm1.Create(Application);
  Application.Run;
end.

但是这个项目会自动启动然后自动退出,为什么? 我想显示Form1,当我们单击Button1然后显示Form2和免费(Release)Form1。我怎么能这样呢?

5 个答案:

答案 0 :(得分:12)

当您销毁表单时,最好使用Release。

发布几乎与免费相同,但它等待待处理的消息以避免崩溃。

你永远不应该使用Destroy。 Free / Release调用析构函数。

Self是当前对象(在你的代码Form1中,所以self.Free会杀死当前的表单。这会导致访问冲突。自动创建Form1,它也会被自动销毁,所以你不应该自己销毁它。如果你不想要它,隐藏它。

如果您想稍后处理它,您应该保留对新创建的表单的引用。

您修改的代码应该是:

uses Unit2;

TForm1 = class (TForm)
private
  FChild : TForm2;
end;

procedure TForm1.FormCreate(Sender: TObject);
begin
  FChild := TForm2.Create(nil);
  Hide; // Hides form 1
  FChild.Show;
end;

procedure TForm2.FormDestroy(Sender: TObject);
begin
  FChild.Release;
end;

但是你为什么要在创建第一个表单的表单中创建另一个表单。为什么不完全删除第一个表单而只使用第二个表单(自动创建)?

答案 1 :(得分:2)

你正试图做一些奇怪的事。

如果没有关闭申请,您无法释放主表单,因此您的Form1不应该是自动处理表单,Form1和Form2都应该手动创建。

首先,您应该像这样编辑项目源以手动创建Form1:

program Project9;

uses
  Forms,
  Unit1 in 'Unit1.pas' {Form1},
  Unit2 in 'Unit2.pas' {Form2};

{$R *.res}

begin
  Application.Initialize;
  Application.MainFormOnTaskbar := True;
  Form1:= TForm1.Create(Application);
  Application.Run;
end.

Form1.OnCreate应写为

procedure TForm1.FormCreate(Sender: TObject);
begin
  Application.CreateForm(TForm2, Form2);
  Release;
end;

这将使Form2成为您的应用程序的主要形式。如前所述,您应该使用Release方法来释放表单。

答案 2 :(得分:0)

如果Form1是'autocreate',它由应用程序对象拥有 - 您不应该在代码中释放它。如果Form1拥有Form2,则应用程序会清除它们。

我会这样做,但不确定它是否符合您的要求:

procedure TForm1.FormCreate(Sender: TObject);
var a:TForm2;
begin
  a := TForm2.Create(nil);
  try
    a.Show;
 finally
   freeandNil(a);
 end; 
end;

答案 3 :(得分:0)

begin
  Application.Initialize;
  Application.CreateForm(TForm1, Form1);
  Application.Run;
end.

...

procedure TForm1.FormClose(Sender: TObject; var CanClose: Boolean);
begin
  if MessageDlg ('Are you want to exit?', mtConfirmation,
      [mbYes, mbNo], 0) = mrNo then
    CanClose := False;
end;

所以,这就是......

答案 4 :(得分:0)

如果所有Form1都应该初始化但未显示,请考虑使用数据模块。这些不能显示但仍可以自动处理。