Как сохранить и восстановить форму?

Итак, у меня есть форма с несколькими дюжинами элементов управления, и кто-то хотел бы сохранить, а затем восстановить их содержимое и настройки - какой переключатель был выбран, какова была позиция этого вверх/вниз и т.д.

Я также хотел бы сохранить любые записи, добавленные в поле списка во время выполнения.

Какой самый простой способ сделать это? DfmToString и наоборот? Напишите/прочитайте .INI? Что-то еще?

Ответы

Ответ 1

Решение 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 файл.

И чтобы загрузить FSecondForm из файла formdata.txt, мы пишем следующее:

  if not Assigned(FSecondForm) then
    FSecondForm := TfrmSecond.Create(Application);
  LoadComponentFromFile(FSecondForm,ExtractFilePath(Application.ExeName)+ 'formdata.txt');
  FSecondForm.Show;

LoadComponentFromFile необходимо создать экземпляр, который будет создан первым, поэтому мы проверяем, назначен ли FSecondForm, если нет, мы создаем его экземпляр (это экземпляр класса TfrmSecond), а затем загружаем в него данные файла. И в итоге мы покажем загруженную форму.

Ответ 2

Довольно легко читать/записывать свойства компонента или объекта или формировать позицию в INI файле или в реестре. Все, что вам нужно, есть в помощи. Вам просто нужно решить, когда вы хотите их прочитать (при создании, пока не покажете...) и сохраните их (при закрытии,...). Это зависит от того, что вы сохраняете/восстанавливаете. Если вы собираетесь использовать готовые компоненты и хотите сохранить позицию формы, убедитесь, что вы проверяете, как они обрабатывают несколько мониторов. Если вы делаете это по-своему, вы должны сами позаботиться об этом. Например, у вас может быть ноутбук и большой 22-дюймовый монитор, а позиция формы была сохранена, пока использовался ваш большой монитор. Позже, если вы откроете эту форму на ноутбуке, она может отображаться на экране, поэтому вы не можете видеть если этот случай не обрабатывается должным образом.