Dieses Tutorial beschreibt, wie einzelne Objekte automatisiert mit dem Graph::Aligner
Knoten ausgerichtet werden können.
ContainerAlignment
Ganz generell und unabhängig vom Aligner
Graphenknoten kann bei einigen Objekten (wie etwa PlaneGeometry
oder TextGeometry
) der Ankerpunkte für die Positionierung mit den Attributen containerAlignmentX
und containerAlignmentY
angepasst werden. Standardmäßig liegt der Ankerpunkt immer im Zentrum.
Die gültigen Werte sind im Enum IEnums::AlignmentX
bzw. IEnums::AlignmentY
aufgelistet:
UNDEFINED
LEFT
(oderBOTTOM
für Y)CENTER
(default)RIGHT
(oderTOP
für Y)NEGATIVE
POSITIVE
Zur Veranschaulichung positionieren wir drei Planes an derselben Position 0/0/0 und ändern lediglich die Parameter containerAlignmentX
und containerAlignmentY
(sowie den Farbparameter).
29 30 31 32 33 34 35 36 37 38 39 40 41 42 | <!-- blue plane --> < PlaneGeometry id = "box_plane_01" posX = "0" posY = "0" scaleFactor = "100" parametersSlot = "0" materialSlot = "2" /> <!-- red plane --> < PlaneGeometry id = "box_plane_02" posX = "0" posY = "0" scaleFactor = "100" parametersSlot = "1" materialSlot = "2" containerAlignmentX = "LEFT" containerAlignmentY = "TOP" /> <!-- green plane --> < PlaneGeometry id = "box_plane_03" posX = "0" posY = "0" scaleFactor = "100" parametersSlot = "2" materialSlot = "2" containerAlignmentX = "RIGHT" containerAlignmentY = "BOTTOM" /> |
Als Ergebnis erhalten wir drei Planes die entsprechend ihren Alignment-Vorgaben unterschiedlich positioniert werden. Alle drei Planes haben die gleiche Ankerposition in der virtuellen Welt (0/0/0), allerdings liegt der Ankerpunkt bei der blauen Plane im Zentrum, bei der roten links oben und bei der grünen rechts unten.

Aligner Graphenknoten
Der Aligner
Graphenknoten kann verwendet werden um Objekte entlang einer vorgegebenen Achse automatisch anordnen zu lassen. Dabei berechnet der Aligner
Knoten für alle seine direkten Kindknoten (bzw. Sub-Graphen) die entsprechende Container-Größe und ordnet sie nacheinander an. Als erstes Beispiel ordnen wir drei PlaneGeometry
-Objekte entlang der Y-Achse an.
44 45 46 47 48 49 50 51 52 53 54 | < Aligner id = "aligner01" axis = "Y" posX = "-200" > <!-- blue plane --> < PlaneGeometry scaleFactor = "100" parametersSlot = "0" materialSlot = "2" /> <!-- red plane --> < PlaneGeometry scaleFactor = "100" parametersSlot = "1" materialSlot = "2" containerAlignmentX = "LEFT" containerAlignmentY = "TOP" /> <!-- green plane --> < PlaneGeometry scaleFactor = "100" parametersSlot = "2" materialSlot = "2" containerAlignmentX = "RIGHT" containerAlignmentY = "BOTTOM" /> </ Aligner > |
Das Zentrum des Aligner
Knoten legen wir nach links an die Position -200/0/0. Die PlaneGeometry
Objekte werden entlang der Y-Achse des Aligners angeordnet. Die anderen Koordinatenwerte (X/Z) bleiben unverändert.

Mit dem Attribut objectAlignment
können auch die Koordinatenwerte der verbleibenden Achsen (in unserem Fall X/Z) angepasst werden. Beispielsweise bewirkt die Angabe objectAlignmentX="LEFT"
, dass alle Objekte entlang des linken Rands des Aligners ausgerichtet werden.
Zur Veranschaulichung erstellen wir einen neuen Aligner
Knoten, bei dem das Attribut objectAlignmentX
gesetzt ist. Durch die Angabe von posY="150"
und containerAlignmentY="TOP"
wird der obere Rand des Aligner
an die Position 150
gelegt. Die Angabe von order="DESCENDING"
bewirkt eine absteigende Anordnung.
56 57 58 59 60 61 62 63 64 65 66 67 68 | < Aligner id = "aligner02" axis = "Y" posX = "-350" posY = "150" containerAlignmentY = "TOP" objectAlignmentX = "LEFT" order = "DESCENDING" > <!-- blue plane --> < PlaneGeometry scaleFactor = "100" parametersSlot = "0" materialSlot = "2" /> <!-- red plane --> < PlaneGeometry scaleFactor = "100" parametersSlot = "1" materialSlot = "2" containerAlignmentX = "LEFT" containerAlignmentY = "TOP" /> <!-- green plane --> < PlaneGeometry scaleFactor = "100" parametersSlot = "2" materialSlot = "2" containerAlignmentX = "RIGHT" containerAlignmentY = "BOTTOM" /> </ Aligner > |

Mit dem Attribut spacing
kann ein Abstand zwischen den angeordneten Objekten definiert werden und mit dem Attribut padding
kann ein äußerer Rand für den Aligner
festgelegt werden.
070 071 072 073 074 075 076 077 078 079 080 081 082 083 084 085 086 087 088 089 090 091 092 093 094 095 096 097 098 099 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 | < Aligner id = "aligner03" axis = "Y" posX = "250" posY = "250" containerAlignmentY = "TOP" containerSizeX = "200" order = "DESCENDING" spacing = "20" > < TextGeometry materialSlot = "4" systemFontName = "SansBold" fontSize = "20" textColor = "255i, 255i, 255i, 255i" backgroundColor = "0i, 0i, 0i, 0i" text = "Line 1 centered" enableWordWrapping = "yes" containerSizeX = "200" textAlignmentX = "CENTER" /> < TextGeometry materialSlot = "4" systemFontName = "SansBold" fontSize = "20" textColor = "255i, 255i, 255i, 255i" backgroundColor = "0i, 0i, 0i, 0i" text = "A auto wrapped text line" enableWordWrapping = "yes" containerSizeX = "200" textAlignmentX = "CENTER" /> < TextGeometry materialSlot = "4" systemFontName = "SansBold" fontSize = "20" textColor = "255i, 255i, 255i, 255i" backgroundColor = "0i, 0i, 0i, 0i" text = "A manually wrapped line" enableWordWrapping = "yes" containerSizeX = "200" textAlignmentX = "CENTER" /> < TextGeometry materialSlot = "4" systemFontName = "SansBold" fontSize = "20" textColor = "255i, 255i, 255i, 255i" backgroundColor = "0i, 0i, 0i, 0i" text = "Left aligned text" enableWordWrapping = "yes" containerSizeX = "200" textAlignmentX = "LEFT" /> < TextGeometry materialSlot = "4" systemFontName = "SansBold" fontSize = "20" textColor = "255i, 255i, 255i, 255i" backgroundColor = "0i, 0i, 0i, 0i" text = "Right aligned text" enableWordWrapping = "yes" containerSizeX = "200" textAlignmentX = "RIGHT" /> < Node > < PlaneGeometry scaleFactor = "100" parametersSlot = "0" materialSlot = "2" containerAlignmentY = "TOP" /> < PlaneGeometry scaleFactor = "100" parametersSlot = "1" materialSlot = "2" containerAlignmentX = "LEFT" /> < PlaneGeometry posX = "25" posY = "-25" scaleFactor = "100" parametersSlot = "2" materialSlot = "2" containerAlignmentX = "RIGHT" containerAlignmentY = "BOTTOM" /> </ Node > </ Aligner > |

Die resultierende Größe des Aligner
nach dem Anordnen kann mit der Methode GetBoundingVolume()
abgefragt werden. Allerdings muss die Abfrage in der Methode OnFinishTick()
und nicht in der Methode OnProcessTick()
erfolgen, da das Ausrichten der Objekte im Aligner
erst nach erfolgter Abarbeitung von OnProcessTick()
durchgeführt wird. Eine Abfrage in OnProcessTick()
liefert daher immer die Werte des vorherigen Frames.
70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 | void App::AlignerLogic::OnFinishTick( const Logic::IState* state) { // Size if (mPrintBoundingValues) { const Graph::IBoundingVolume* boundingVolume = mAligner->GetBoundingVolume(); const Graph::Box& box = boundingVolume->GetInnerLocalBox(); const Graph::Vector& min = box.GetMinimum(); const Graph::Vector& max = box.GetMaximum(); Debug::Trace( "From OnFinishTick:" ); Debug::Trace( " Bounding X %f / %f" , min.x, max.x); Debug::Trace( " Bounding Y %f / %f" , min.y, max.y); Debug::Trace( " Bounding Z %f / %f" , min.z, max.z); mPrintBoundingValues = false ; } } |
Als Ergebnis erhalten wir für den Aligner
aligner03
und das erste Frame:
Für alle weiteren Frames liefert OnProcessTick()
und OnFinishTick()
dasselbe Ergebnis, da sich in unserem Beispiel die Inhalte des Aligner
nicht mehr ändern und damit das IBoundingVolume
gleich bleibt. Durch Drücken der Taste P kann das IBoundingVolume
für ein weiteres Frame ausgegeben werden:
Wir können das berechnete IBoundingVolume
noch optisch mit einem PlaneGeometry
Knoten verifizieren:
132 133 134 | < PlaneGeometry posX = "250" posY = "250" containerAlignmentY = "TOP" scaleFactorX = "200" scaleFactorY = "450" parametersSlot = "3" materialSlot = "2" depthOrder = "-1" /> |
