因此,我有一个表格,有几十个控件,有人想保存并稍后恢复它们的内容和设置 - 选择哪个单选按钮,上/下位置是什么等。如何保存和恢复表单?
I还想在运行时存储添加到列表框的任何条目。
最简单的方法是什么? DfmToString和反向?写/读一个.INI?还有别的吗?
因此,我有一个表格,有几十个控件,有人想保存并稍后恢复它们的内容和设置 - 选择哪个单选按钮,上/下位置是什么等。如何保存和恢复表单?
I还想在运行时存储添加到列表框的任何条目。
最简单的方法是什么? DfmToString和反向?写/读一个.INI?还有别的吗?
PRUZ的解决方案是一个现成的解决方案; JVCL是开源的,使用JvFormStorage很简单,但是你也可以使用Delphi自己的流式机制而不使用任何第三方组件。下面是一个例子:
procedure SaveComponentToFile(Component: TComponent; const FileName: TFileName);
var
FileStream : TFileStream;
MemStream : TMemoryStream;
begin
MemStream := nil;
if not Assigned(Component) then
raise Exception.Create('Component is not assigned');
FileStream := TFileStream.Create(FileName,fmCreate);
try
MemStream := TMemoryStream.Create;
MemStream.WriteComponent(Component);
MemStream.Position := 0;
ObjectBinaryToText(MemStream, FileStream);
finally
MemStream.Free;
FileStream.Free;
end;
end;
SaveComponentToFile取组件实例,加上文件名,和溪流的组分引入该文件,以人类可读的文本
从文件加载组件,您可以使用这样的代码:
procedure LoadComponentFromFile(Component: TComponent; const FileName: TFileName);
var
FileStream : TFileStream;
MemStream : TMemoryStream;
i: Integer;
begin
MemStream := nil;
if not Assigned(Component) then
raise Exception.Create('Component is not assigned');
if FileExists(FileName) then
begin
FileStream := TFileStream.Create(FileName,fmOpenRead);
try
for i := Component.ComponentCount - 1 downto 0 do
begin
if Component.Components[i] is TControl then
TControl(Component.Components[i]).Parent := nil;
Component.Components[i].Free;
end;
MemStream := TMemoryStream.Create;
ObjectTextToBinary(FileStream, MemStream);
MemStream.Position := 0;
MemStream.ReadComponent(Component);
Application.InsertComponent(Component);
finally
MemStream.Free;
FileStream.Free;
end;
end;
end;
LoadComponentFromFile需要一个组件实例,和一个文件名,然后加载文件内容到组件实例。为避免命名冲突,在将文件数据加载到实例之前,我们释放实例的所有现有组件。
现在你可以使用上面的代码保存表单到一个文件:
SaveComponentToFile(FSecondForm,ExtractFilePath(Application.ExeName)+ 'formdata.txt');
FSecondForm是一个表单实例,它会被保存到“formdata.txt”文件相同的文件夹里面EXE文件。
,并从“formdata.txt”文件加载FSecondForm,我们这样写:
if not Assigned(FSecondForm) then
FSecondForm := TfrmSecond.Create(Application);
LoadComponentFromFile(FSecondForm,ExtractFilePath(Application.ExeName)+ 'formdata.txt');
FSecondForm.Show;
LoadComponentFromFile需要先创建的实例,所以我们检查,如果FSecondForm分配,如果没有,我们创建了一个它的实例(它是TfrmSecond类的一个实例),然后将文件数据加载到该实例中。最终,我们显示加载的表单。
它很容易读/写组件或对象属性,或在INI文件或注册表中形成位置。你需要的一切都有帮助。您只需要决定何时阅读它们(在创建之前,在展示之前)并存储它们(靠近......)。这取决于你正在保存/恢复的内容。 如果您打算使用现成的组件并希望保存表单位置,那么请确保检查它们如何处理多个监视器。如果你以自己的方式去做,你应该自己照顾自己。例如,您可能有一台笔记本电脑和一台22英寸的大屏幕显示器,在使用大显示器时可以保存表格的位置。稍后,如果您在笔记本电脑上打开此表单,则可能会显示屏幕,以至于看不到如果这种情况没有得到妥善处理,可以使用DELPHI自己的流式机制。
+1这是一个低调,但我一定会照顾它(在最糟糕的情况下,用户可以编辑或重命名保存文件) – Mawg 2013-01-24 02:40:09
谢谢,这看起来不错。现在,我将把它包装在一个循环中,并使其递归,然后我就开始了。 – Mawg 2013-01-22 02:41:34
为什么在释放子组件之前将Parent设置为零?而不是整个循环,不会'Component.DestroyComponents'做的伎俩? – NGLN 2013-11-15 19:21:35
为什么'LoadComponentFromFile()'将'Component'添加到'Application'的拥有组件列表中?它不应该这样做。 – 2015-06-09 23:37:26