Top.Mail.Ru
Мастера DELPHI, Delphi programming community Титульная страница Поиск, карта сайта Написать письмо 
| Новости | Поиск | FAQ | Статьи | Книги | Новости VCL |
| Форумы ЧАТ | Орешник | KOL и MCK |
Форумы -» Основная («Начинающим»)/ Базы / WinAPI / Компоненты / Сети / Media / Игры / Corba и COM / KOL / FreePascal / .Net / Прочее / RSDN.ORG

« предыдущая ветвь | форум | следующая ветвь »

Хранение параметров приложения


GuAV ©   (2004-08-08 15:12:00) 

Интересная тут идея появилась.

Допустим нужно сохранить какую-то информацию в реестр/ини.

Публикуем эту информацию как свойства соотв формы:

 TDupeAction = (daAdd, daSkip, daReplace);
 TfrmMain = class(TForm)
   ...
  published
   property DupeAction: TDupeAction read FDupeAction write FDupeAction;
   property NamedUnits: Boolean read FNamedUnits write FNamedUnits;
   property Recourse: Boolean read GetRecourse write SetRecourse;
 end;

Теперь их можно сохранить, причем сам список получить как разницу свойств этой формы и TForm

procedure WriteProp(Ini: TCustomIniFile; Section: string;
 Obj: TObject; Info: PPropInfo);
begin
 with Info^ do
   case PropType^.Kind of
     tkInteger, tkEnumeration, tkChar:
       Ini.WriteInteger(Section, Name, GetOrdProp(Obj, Info));
     tkFloat:
       Ini.WriteFloat(Section, Name, GetFloatProp(Obj, Info));
     tkString, tkLString:
       Ini.WriteString(Section, Name, GetStrProp(Obj, Info));
     tkWString:
       Ini.WriteString(Section, Name, GetWideStrProp(Obj, Info));
   end;
end;

procedure ReadProp(Ini: TCustomIniFile; Section: string;
 Obj: TObject; Info: PPropInfo);
begin
 with Info^ do
 begin
   if not Ini.ValueExists(Section, Name) then Exit;
   case PropType^.Kind of
     tkInteger, tkEnumeration, tkChar:
       SetOrdProp(Obj, Info, Ini.ReadInteger(Section, Name, 0));
     tkFloat:
       SetFloatProp(Obj, Info, Ini.ReadFloat(Section, Name, 0));
     tkString, tkLString:
       SetStrProp(Obj, Info, Ini.ReadString(Section, Name, ''));
     tkWString:
       SetWideStrProp(Obj, Info, Ini.ReadString(Section, Name, ''));
   end;
 end;
end;

procedure ReadWriteNewPubProps(Ini: TCustomIniFile;
 Obj: TForm; Write: Boolean);
var
 J, Size1, Size2: Integer;
 List1, List2: PPropList;
begin
   Size1:=GetTypeData(TForm.ClassInfo).PropCount;
   Size2:=GetPropList(PTypeInfo(Obj.ClassInfo),List1) - Size1;
   GetMem(List2, SizeOf(PPropInfo)*Size2);
   Move((List1^[Size1]), List2^, SizeOf(PPropInfo)*Size2);
   FreeMem(List1, SizeOf(PPropInfo)*Size1);
   for J:=0 to Size2-1 do
     if Write then
       WriteProp(Ini, Obj.Name, Obj, List2[J])
     else
       ReadProp(Ini, Obj.Name, Obj, List2[J]);
   FreeMem(List2, SizeOf(PPropInfo)*Size2);end;

Так, например, если хотим использовать ini файл

procedure ReadWriteIni(Form: TForm; Write: Boolean);
var Ini: TIniFile;
begin
 Ini:=TIniFile.Create(
   ChangeFileExt(Application.ExeName,'.ini'));
 try
    ReadWriteNewPubProps(Ini, Form, Write);
 finally
   Ini.Free;
 end;
end;

А в OnCreate/OnDestroy:

procedure TfrmMain.FormCreate(Sender: TObject);
 ...
begin
 ...
 ReadWriteIni(Self, False);
end;
procedure TfrmMain.FormDestroy(Sender: TObject);
begin
 ReadWriteIni(Self, True);
end;

смысл в том, что вышеописаные процедуры работают и для других таких форм (например, в другом проекте) - менять их уже не нужно.

Вот такой Ini получился:

[frmMain]
DupeAction=2
NamedUnits=0
Recourse=1


зы - возможны какие-то ошибки, но вроде работает.


GuAV   (2004-08-08 17:29:00) [1]


> все было сделано в виде процедуры, в которую передавалось
> два класса -- базовый и наследник

сделать obj: TObject и добавить для наследник для универсальности, или сделать Obj.ClassParent - проблемы не вижу, но пока устраивает и так.

> К тому времени, "велосипед" превратится во вполне комфортабельный
> мотороллер Suzuki :)

Это точно. Можешь не искать. Лучше скажи где информация по TypInfo, кроме самого TypInfo.pas - F1 молчит...


Sergey Kaminski   (2004-08-08 16:59:00) [2]

К тому времени, "велосипед" превратится во вполне комфортабельный мотороллер Suzuki :)

Да, в общем, там очень похоже было. И кода строк на 300, не больше.
Только, если я правильно вспоминаю, все было сделано в виде процедуры, в которую передавалось два класса -- базовый и наследник, и сохранялись свойства наследника, отличные от базового. Т.е, работало с произвольными классами. А так все тож самое, кажись.


Sergey Kaminski   (2004-08-08 16:54:00) [3]

Дак это сначала нужно на работу попасть :)
Отпуск закончится, пороюсь, если сохранилось - вышлю, обещаю. Только вряд ли это будет скоро.


GuAV   (2004-08-08 16:34:00) [4]

Sergey Kaminski ©   (08.08.04 16:16) [2]
Скинь, плиз, чтоб я велосипед не изобретал...


Sergey Kaminski   (2004-08-08 16:16:00) [5]

Я тоже подобное использовал. Даже где-то модуль завалялся от старого проекта на работе.


GuAV   (2004-08-08 15:48:00) [6]

Да, забыл
uses IniFiles, TypInfo, Forms, Classes;


Наверх

Титульная страница Поиск, карта сайта Написать письмо