Dynamisch erstellte GUI speichern

Für allgemeine Fragen zur Programmierung, welche nicht! direkt mit Lazarus zu tun haben.
Antworten
ArmFPC1
Beiträge: 33
Registriert: Do 19. Mär 2015, 18:18

Dynamisch erstellte GUI speichern

Beitrag von ArmFPC1 »

Hi Leute,
ich hab mal eine Frage bezüglich abspeichern von Labels und Buttons die zu Laufzeit erstellt werden und von der position her auch verschoben werden können.

Mir ist bekannt das man über den Objektinspektor die SessionProperties gemacht werden kann. Aber so wie ich es bis jetzt verstehe nur mit den Objekten die über den Designer "Statisch" erstellt werden. Wie kann ich diese Funktion verwenden beim schließen von meinem eigenen Programmes.

So dass bei Starten alle Elemente wieder an den Stellen sind, wo sie hin sollen, Namen und auch die Funktionen wie onMouseMove etc.

Gibt es da was fertiges oder muss man da was selber schreiben.

Wenn ja wie bekomme ich am leichtesten alle Child Objekte von der Form? Ich bin da noch nicht ganz schlau draus geworden. Muss dazu sagen ich bin Anfänger mit Lazarus / Pascal .

Danke schonmal !!

Warf
Beiträge: 1908
Registriert: Di 23. Sep 2014, 17:46
OS, Lazarus, FPC: Win10 | Linux
CPU-Target: x86_64

Re: Dynamisch erstellte GUI speichern

Beitrag von Warf »

Such dir einfach ein Format raus und speichere die Daten dann damit.
Für eine kleinere IDE für die Skriptsprache Autoit habe ich einen Formulareditor geschrieben, welcher die Controls in Autoit Script Abspeichert und lädt. Kannst dir das ja mal ansehen: Link

mse
Beiträge: 2013
Registriert: Do 16. Okt 2008, 10:22
OS, Lazarus, FPC: Linux,Windows,FreeBSD,(MSEide+MSEgui 4.6,git master FPC 3.0.4,fixes_3_0)
CPU-Target: x86,x64,ARM

Re: Dynamisch erstellte GUI speichern

Beitrag von mse »

Das "streamen" einer Form geschieht mittels TWriter.WriteRootComponent():

Code: Alles auswählen

 
  twriter = class(tfiler)
[...]
  public
    constructor Create(Stream: TStream; BufSize: Integer); overload;
    procedure WriteRootComponent(ARoot: tcomponent);
 

Zum Laden einer Form aus dem geschriebenen stream dient TReader.ReadRootComponent():

Code: Alles auswählen

 
  treader = class(tfiler)
[...]
  public
    constructor Create(Stream: TStream; BufSize: Integer);
    function ReadRootComponent(ARoot: tcomponent): tcomponent;
 

Die ganze Streamerei ist leider ziemlich kompliziert.

ArmFPC1
Beiträge: 33
Registriert: Do 19. Mär 2015, 18:18

Re: Dynamisch erstellte GUI speichern

Beitrag von ArmFPC1 »

Ok Vielen Danke ich werde das mal versuchen.

Dann ist eigentlich nur noch die Frage wie ich herausbekomme welche Componenten alle auf der "Form" sich befinden, dann kann ich die wichtigen Eigenschaften speichern und diese dann beim Start des Programmes diese wieder Laden lassen und erstellen.

Warf
Beiträge: 1908
Registriert: Di 23. Sep 2014, 17:46
OS, Lazarus, FPC: Win10 | Linux
CPU-Target: x86_64

Re: Dynamisch erstellte GUI speichern

Beitrag von Warf »

ArmFPC1 hat geschrieben:Ok Vielen Danke ich werde das mal versuchen.

Dann ist eigentlich nur noch die Frage wie ich herausbekomme welche Componenten alle auf der "Form" sich befinden, dann kann ich die wichtigen Eigenschaften speichern und diese dann beim Start des Programmes diese wieder Laden lassen und erstellen.


Es gibt die Eigenschaft ComponentCount und Components[Index] bzw ControlCount und Controls[Index], damit kannst du dich durch alle Komponenten und Controls iterieren

mse
Beiträge: 2013
Registriert: Do 16. Okt 2008, 10:22
OS, Lazarus, FPC: Linux,Windows,FreeBSD,(MSEide+MSEgui 4.6,git master FPC 3.0.4,fixes_3_0)
CPU-Target: x86,x64,ARM

Re: Dynamisch erstellte GUI speichern

Beitrag von mse »

ArmFPC1 hat geschrieben:Ok Vielen Danke ich werde das mal versuchen.

Falls du mit "das" die Methode mit TReader/TWriter meinst, damit wird die ganze Komponententenhierarchie gestreamt. Die Nachkommentschaft läuft dabei über die Prozedur TComponent.GetChildren(), welche für visuelle Komponenten die eingebetteten visuellen Komponenten liefert. Bei visuellen Komponenten wird also nicht die Beziehung Components/Owner verwendet.

ArmFPC1
Beiträge: 33
Registriert: Do 19. Mär 2015, 18:18

Re: Dynamisch erstellte GUI speichern

Beitrag von ArmFPC1 »

Ok Vielen Dank.

also ich habe es jetzt mal Testweise mit Form.Componets[index] durch iteriert. Nun kann ich die Namen und alle wichtigen Positionen ermitteln und auch in einer XML Datei abspeichern. Nun hänge ich an den Eventfunktionen die ich angehängt habe. Wie bekomme ich die hinterlegten "Funktionsnamen" gespeichert, dass ich diese dann auch wieder anhängen kann nach dem Neustart.

Prinzipiell könnte ich das jetzt statisch machen, da ich weiß wenn es z.B ein Bild ist das die 3 Funktionen hin müssen. Ich persönlich finde das aber nicht ganz so elegant würde das lieber "Dynamisch" machen.

Kann mir da jemand ein Tipp geben ?

Danke schon mal !!

mse
Beiträge: 2013
Registriert: Do 16. Okt 2008, 10:22
OS, Lazarus, FPC: Linux,Windows,FreeBSD,(MSEide+MSEgui 4.6,git master FPC 3.0.4,fixes_3_0)
CPU-Target: x86,x64,ARM

Re: Dynamisch erstellte GUI speichern

Beitrag von mse »

Schau halt wie es TReader/TWriter machen. Den Code hast du ja.

ArmFPC1
Beiträge: 33
Registriert: Do 19. Mär 2015, 18:18

Re: Dynamisch erstellte GUI speichern

Beitrag von ArmFPC1 »

mse hat geschrieben:Schau halt wie es TReader/TWriter machen. Den Code hast du ja.


ich habe mir das angeschaut. Hatte auch den Erfolg das das Speichern von den Components funktioniert. Nun habe ich das Problem bei Starten der Anwendung (lesen vom Stream)

procedure ReadComponentFromBinaryStream(AStream: TStream; var RootComponent: TComponent; OnFindComponentClass: TFindComponentClassEvent;
TheOwner: TComponent = nil; Parent: TComponent = nil; ReaderRoot: TComponent = nil);

Ich habe mir das Beispiel hier angeschaut. http://wiki.freepascal.org/Streaming_components/de
Irgendetwas mache ich bei Read falsch aber ich verstehe nicht ganz was. Konkret liegt es an der OnFindComponentClass Übergabe, hier muss ich doch eine "Funktion" übergeben mit der richtigen Anzahl von Parameter.

Oder verstehe ich da etwas Falsch?

mse
Beiträge: 2013
Registriert: Do 16. Okt 2008, 10:22
OS, Lazarus, FPC: Linux,Windows,FreeBSD,(MSEide+MSEgui 4.6,git master FPC 3.0.4,fixes_3_0)
CPU-Target: x86,x64,ARM

Re: Dynamisch erstellte GUI speichern

Beitrag von mse »

Registriere alle benötigten Klassen mit registerclass(), dann sollte es auch ohne OnFindComponentClass funktionieren (nil übergeben).

Antworten