Hallo lieber Community,
ich möchte dieses Thema erneut aufgreifen, da ich keinen Schritt weitergekommen bin. Wie gesagt, ich bin Hobby-Entwickler und kann daher oft nicht jeden Gedanken problemlos nachvollziehen. Ich sage das nur, damit die Antworten gern „normalofreundlich“ ausfallen, ohne Fachbegriffe bzw. diese erklärt.
Ich würde TTreeItem (oder besser TPerson) so definieren:
Delphi-Quellcode:
TPerson = class
Mother: TPerson;
Father: TPerson;
Name: String;
end;
Und mehr brauchst du gar nicht. Die Kinder musst du gar nicht speichern, weil sie sich implizit ergeben: Das sind die Personen, wo entweder Father oder Mother das jeweilige Subjekt sind.
Ist die Argumentation richtig? Weil es wären doch dann immer Mutter und Vater das Subjekt, oder sind mit dem oder Halbgeschwister gemeint?
Dann noch TFamilyTree in etwa so:
Delphi-Quellcode:
TFamilyTree = class
Family: TList<TPerson>;
function TreeToLayers(Subject: TPerson; Depth: Integer): TList<TLayer>;
end;
Ist TFamilyTree jetzt jeweils ein TLayer oder der vollständige Baum nachher? Was wird jetzt alles in der Family Liste dargestellt? Nur immer ein TLayer, also Ausgangsperson und deren Eltern, sowie die Geschwister der Ausgangsperson? Die Kinder der Ausgangsperson und deren Geschwister müssten ja dann wieder in einen neuen TLayer, oder? Vielleicht kann jemand dazu bitte eine kleine Zeichnung machen, um zu veranschaulichen, was in welcher Klasse jeweils ausgegeben wird. Das sollte dem Verständnis meinerseits helfen
Was ist in dem Fall, dass eine Ausgangsperson bzw. deren Geschwister mehrere Partner hatte? Die müssen ja dann auch in dem Layer dargestellt werden und die Kinder der einzelnen Beziehungen darunter.
Um den Baum (eigentlich ein Graph) zu zeichnen, musst du über den Graphen iterieren und ihn in „Schichten“ (= Generationen) anordnen.
Delphi-Quellcode:
type
TLayer = TList<TPerson>;
function TFamilyTree.TreeToLayers(Subject: TPerson; Depth: Integer): TList<TLayer>;
procedure AssignPerson(Person: TPerson; Layers: TList<TLayer>; LayerIndex: Integer);
begin
if LayerIndex >= Layers.Count then exit;
Layers[CurrentLayerIndex].Add(Person);
AssignPerson(Person.Mother, Layers, LayerIndex+1);
AssignPerson(Person.Father, Layers, LayerIndex+1);
end;
var
i: Integer;
begin
Result := TList<TLayer>.Create;
for i := 0 to Depth-1 do
Result.Add(TLayer.Create);
AssignPerson(Subject, 0);
end;
In dem Beispielcode werden nur die Ahnen berücksichtigt, aber es ist nicht schwer es so zu erweitern, dass auch Kinder, Geschwichter, Cousins etc. in die jeweiligen Schichten eingefügt werden. Man muss dann nur aufpassen, dass man einen Knoten nicht mehrfach hinzufügt.
Die Schichten kannst du dann problemlos in einer Richtung zeichnen.
Jetzt wird es kompliziert. Der eigentliche Baum ist ist also dann eine Liste von TLayer? Wie kann ich das integrieren, damit die richtigen Kinder jeweils unter dem richtigen Elternpaar abgebildet werden?
Wenn ich mir das Bild so anschaue, dann kann man die Daten zu dieser Anzeige hiermit abbilden (die Bilder habe ich jetzt mal weggelassen):
Vermutlich ist der Vorschlag von Namensloser, den ich wie gesagt noch nicht ganz durchblicke günstiger, weil er nicht nur auf vier Generationen begrenzt ist. Oder kann man Ihre Struktur dynamisch erweitern?
Ich würde mich sehr freuen, wenn wir das Step-by-Step behandeln könnten, damit ich es verstehe und dann auch zu dem, juhu, wie ich Mathematik geliebt habe
, Berechnungen der Koordinaten kommen.
Ich danke sehr im Voraus.