AGB  ·  Datenschutz  ·  Impressum  







Anmelden
Nützliche Links
Registrieren
Zurück Delphi-PRAXiS Programmierung allgemein Programmieren allgemein Delphi RegisterClasses und RTTI - dynamisches Registrieren aller Klassen zur Laufzeit

RegisterClasses und RTTI - dynamisches Registrieren aller Klassen zur Laufzeit

Ein Thema von Tobitoba · begonnen am 15. Okt 2018 · letzter Beitrag vom 20. Jun 2019
Antwort Antwort
Tobitoba

Registriert seit: 6. Jan 2017
6 Beiträge
 
Delphi 11 Alexandria
 
#1

RegisterClasses und RTTI - dynamisches Registrieren aller Klassen zur Laufzeit

  Alt 15. Okt 2018, 15:46
Hallo zusammen,
in unserem Projekt, müssen wir dafür sorgen, dass alle verfügbare Klassen des Projektes in den RegisterClasses registriert werden.
Nun habe ich mich ein wenig mit RTTI und dessen Funktion GetTypes auseinander gesetzt.
Leider erzielen wir bisher nur Teilziele.
Im Projekt Quelltext, stehen rund 400 Klassen, welche beim Starten auch tatsächlich vor den Ausführen der nachfolgenden Funktion initialisiert werden, während die Funktion leider nur 146 relevante davon findet und registriert. Die Filterung nach "TFRM" liegt daran, dass wir explizit alle unsere Klassen die Relevant sind so vorab benennen.

Nun das bestehende Problem der aktuellen Funktion:
Klasse_A wird mittels der Funktion gefunden und wird in RegisterClasses registriert.
Klasse_B wird nicht gefunden.
Beide Klassen erben von Klasse_C, welche gefunden wird und verwenden die selben Uses.

Um zu schauen, ob die fehlende Klasse_B überhaupt irgendwo aufgelistet wird ggf. mit dem Unit-Namen o.ä., habe ich mit alle Typen "KlassenALL" und alle Klassen "klassen" als Liste ausgeben lassen. Leider findet man in keiner der beiden die entschiedene fehlende Klasse_B.

Habt Ihr eventuell Iden, Gedankenansätze, wieso das so sein könnte oder wo man nochmal nachschauen kann ?
Weiterer Hinweis:
wir wollen das manuelle Registrieren unter dem Block initialization vermeiden, da sonst ebenfalls die Implementierung der Units in den uses erfolgen muss. Durch die hohe Anzahl ist es serh mühselig und der Wartungsaufwand, sowie die Sicherstellung ist zu hoch. In dem Code-Beispiel, habe ich die Uses und initialization mal nur auf ein Beispiel herunter gebrochen.

Verwendete Delphi-Version XE10 Seattle Architect

Bei Fragen einfach melden, vielen Dank vorab
Lg Tobi


Delphi-Quellcode:
uses System.Classes, System.Rtti, System.SysUtils;

procedure FindeAlleKlassen();

implementation
uses fKlasseA

procedure FindeAlleKlassen;
var
  ctx: TRttiContext;
  typ: TRttiType;
  list: TArray<TRttiType>;
  i: Integer;
  KlassenAll: TStringList;
  Klassen: TstringList;
begin

  // sucht die Klasse und gibt diese für das Array der RegisterClasses zurück.
  ctx := TRttiContext.Create;
  list := ctx.GetTypes;
  Klassen := TStringList.Create;
  Klassen.Clear;
  KlassenAll := TStringList.Create;
  KlassenAll.Clear;
  i := 0;
  for typ in list do
  begin
    //Zum Testen aller typen ohne Instanziierung
    KlassenALL.Add(typ.Name);
    if typ.IsInstance and not(typ = nil) then
    begin
      if Pos('TFRM',UpperCase(typ.ToString),1)>0 then
      begin
        //Zum testen in StringList schrieben und Inhalte nachlesen
        Klassen.Add(typ.AsInstance.MetaclassType.ClassName);

        //Füge die Klasse den RegisterClasses hinzu.
        RegisterClasses([TPersistentClass(typ.AsInstance.MetaclassType)]);

        //Zähler i
        Inc(i);
      end;
    end;
  end;
  // Testzwecke
  Klassen.SaveToFile('X:\Klassen.txt');
  KlassenALL.SaveToFile('X:\KlassenALL.txt');
  ctx.Free;

end;

initialization
  RegisterClasses([TfrmKlasseA])
Tobi
  Mit Zitat antworten Zitat
Benutzerbild von Uwe Raabe
Uwe Raabe

Registriert seit: 20. Jan 2006
Ort: Lübbecke
10.934 Beiträge
 
Delphi 12 Athens
 
#2

AW: RegisterClasses und RTTI - dynamisches Registrieren aller Klassen zur Laufzeit

  Alt 15. Okt 2018, 16:50
In der Regel entfernt der Linker allen Methoden und Klassen, die nicht benutzt werden. Diese sind dann logischerweise auch über RTTI nicht zu finden. Der RegisterClass-Aufruf für TfrmKlasseA sorgt dafür, daß diese Klasse und ihre Vorfahren benutzt werden. Deswegen wird TfrmKlasseA und TfrmKlasseC auch gefunden. Es ist gut möglich, daß deine Anforderung gar nicht realisierbar ist, wenn das RegisterClass die einzige Verwendung einer Klasse wäre.
Uwe Raabe
Certified Delphi Master Developer
Embarcadero MVP
Blog: The Art of Delphi Programming
  Mit Zitat antworten Zitat
freimatz

Registriert seit: 20. Mai 2010
1.377 Beiträge
 
Delphi 11 Alexandria
 
#3

AW: RegisterClasses und RTTI - dynamisches Registrieren aller Klassen zur Laufzeit

  Alt 16. Okt 2018, 08:11
An das dachte ich auch.
Für den Zweck habe ich eine eigene unit, die nur dazu da ist alle solche units nach uses aufzuführen.
  Mit Zitat antworten Zitat
hoika

Registriert seit: 5. Jul 2006
Ort: Magdeburg
8.269 Beiträge
 
Delphi 10.4 Sydney
 
#4

AW: RegisterClasses und RTTI - dynamisches Registrieren aller Klassen zur Laufzeit

  Alt 16. Okt 2018, 08:18
Hallo,
das uses nützt Dir aber nichts,
weil der Linker erkennt, dass das Formular nicht benutzt wird.
Heiko
  Mit Zitat antworten Zitat
Tobitoba

Registriert seit: 6. Jan 2017
6 Beiträge
 
Delphi 11 Alexandria
 
#5

AW: RegisterClasses und RTTI - dynamisches Registrieren aller Klassen zur Laufzeit

  Alt 16. Okt 2018, 09:01
Hey Uwe,
vielen lieben Dank für die erste rasche Antwort.
Das Linken haben wir in dem Projekt eingeschaltet, sowie das Bereitstellen von der detaillierten map-Datei und drc-Datei. Leider sind hier auch Unterschiede wahrzunehmen. KlasseA steht dort mit der unit..Klasse drin und hat nachfolgend alle Inhalte aufgelistet unit.Funtkion, bei der KlasseB leider nur mit der .pas und .dfm ...

Der letzte von dir beschriebene Fall , ist hier eigentlich nicht gegeben.

Weiterer Unterschied ist, in den Projekt-Optionen > Formulare, dort werden nur die 3 wichtigen automatisch erzeugt und der Rest wird unter verfügbare Formulare kategorisiert. Verschiebe ich die fehlende Klasse auf die automatische Seite, ist diese über RTTI zu finden. Eine generelle Aussage dessen ist es aber nicht, da von den 147 gefunden nicht eine einzige auf dieser Seite steht.
Von den Formularen die automatisch erzeugt werden, erbt auch keine einzige, diese sind völlig autark.
Unabhängig der Seite, werden trotzdem vor der RTTI-Funktion alle Klassen initialisiert, ebenfalls die fehlende.

Nochmals zum Zweck der Verwendung:
Wir wissen anhand in einer DB stehenden Info, welches Formular geladen werden soll. Die Speicherung und Auslesung erfolgt als String.
Im Anschluss wird der String an eine Funktion übergeben, die entsprechend die zu ladenden Formulare in einem Detaildialog des Hauptfensters einbettet und ggf. schon weitere Funktionen ausführt.
Dafür verwenden wir die unten aufgelistete Funktion.


Gruß Tobi


Delphi-Quellcode:
var
  c: TFormClass;
begin
  c := TFormClass(GetClass(Klasse:string));
  DoShowListForm(c);
end;
Tobi
  Mit Zitat antworten Zitat
mcinternet

Registriert seit: 22. Apr 2010
Ort: Odenwald
193 Beiträge
 
Delphi 10.3 Rio
 
#6

AW: RegisterClasses und RTTI - dynamisches Registrieren aller Klassen zur Laufzeit

  Alt 19. Jun 2019, 16:16
Hallo,

ich möchte es ähnlich machen. Dieses "FindeAlleKlassen" findet die Klassen allerdings erst, nachdem sie mit registerclass registriert sind. Vorher sind diese unsichtbar. Sie werden alle eincompiliert und ich hab ne Liste mit über 30 Klassen, welche ich ganz gern dynamisch registrieren möchte (dynamisch erzeugt werden sie ohnehin).
Beispiel:


unit registerforms

uses Classes,...bla bla, uDummy;

registerclass(TFrmDummy);


----------------

Unit HauptMenue

wenn User = Recht auf TFrmDummy then xForm := TFrmDummy.create(self);


------------------

Wenn ich das FindeAlleKlassen aufrufe, um z.B. TFrmDummy und alle anderen zu registrieren, dann findet es nur TFrmMain.
Rufe ich es NACH (an der Stelle mal "RegisterClasses([TPersistentClass(typ.AsInstance.MetaclassType)]);" auskommentiert)
meinem "registerclass(TFrmDummy);" auf - dann wird TFrmDummy gefunden.

Also beißt sich die Katze da in den Schwanz

Also - gibt es eine bessere Idee?

Beste Grüße

mcinternet
Jörg

Geändert von mcinternet (19. Jun 2019 um 16:18 Uhr)
  Mit Zitat antworten Zitat
Benutzerbild von Ralf Kaiser
Ralf Kaiser

Registriert seit: 21. Mär 2005
Ort: Wuppertal
932 Beiträge
 
Delphi 10.3 Rio
 
#7

AW: RegisterClasses und RTTI - dynamisches Registrieren aller Klassen zur Laufzeit

  Alt 19. Jun 2019, 18:39

Also beißt sich die Katze da in den Schwanz

Also - gibt es eine bessere Idee?
Registriere die Klassen in ihren eigenen Units im initialzation Abschnitt.
Ralf Kaiser
  Mit Zitat antworten Zitat
BerndS

Registriert seit: 8. Mär 2006
Ort: Jüterbog
477 Beiträge
 
Delphi 11 Alexandria
 
#8

AW: RegisterClasses und RTTI - dynamisches Registrieren aller Klassen zur Laufzeit

  Alt 20. Jun 2019, 08:25
So was ähnliches wurde hier schon mal besprochen. Schau mal hier.
Ich verwende das etwas abgewandelt immer vor einem Release um zu prüfen, ob sich alle Formulare und Reports laden lassen.
Bernd
  Mit Zitat antworten Zitat
Themen-Optionen Thema durchsuchen
Thema durchsuchen:

Erweiterte Suche
Ansicht

Forumregeln

Es ist dir nicht erlaubt, neue Themen zu verfassen.
Es ist dir nicht erlaubt, auf Beiträge zu antworten.
Es ist dir nicht erlaubt, Anhänge hochzuladen.
Es ist dir nicht erlaubt, deine Beiträge zu bearbeiten.

BB-Code ist an.
Smileys sind an.
[IMG] Code ist an.
HTML-Code ist aus.
Trackbacks are an
Pingbacks are an
Refbacks are aus

Gehe zu:

Impressum · AGB · Datenschutz · Nach oben
Alle Zeitangaben in WEZ +1. Es ist jetzt 20:10 Uhr.
Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz