Bedeutung der Transformationsreihenfolge

Ein einzelnes Matrixobjekt kann eine einzelne Transformation oder eine Sequenz von Transformationen speichern. Letzteres wird als zusammengesetzte Transformation bezeichnet. Die Matrix einer zusammengesetzten Transformation wird durch Multiplikation der Matrizen der einzelnen Transformationen abgerufen.

In einer zusammengesetzten Transformation ist die Reihenfolge der einzelnen Transformationen wichtig. Wenn Sie z. B. zuerst rotieren, dann skalieren und übersetzen, erhalten Sie ein anderes Ergebnis als beim ersten Übersetzen, drehen und dann skalieren. In Windows GDI+ werden zusammengesetzte Transformationen von links nach rechts erstellt. Wenn S, R und T Skalierungs-, Drehungs- und Übersetzungsmatrizen sind, ist das Produkt-SRT (in dieser Reihenfolge) die Matrix der zusammengesetzten Transformation, die zuerst skaliert, dann gedreht und dann übersetzt wird. Die vom Produkt-SRT erzeugte Matrix unterscheidet sich von der Matrix, die vom Produkt TRS erzeugt wird.

Eine wichtige Reihenfolge ist, dass Transformationen wie Drehung und Skalierung im Hinblick auf den Ursprung des Koordinatensystems durchgeführt werden. Das Skalieren eines Objekts, das am Ursprung zentriert ist, führt zu einem anderen Ergebnis als das Skalieren eines Objekts, das vom Ursprung entfernt wurde. Ebenso führt das Drehen eines Objekts, das am Ursprung zentriert ist, zu einem anderen Ergebnis als das Drehen eines Objekts, das vom Ursprung entfernt wurde.

Im folgenden Beispiel werden Skalierung, Drehung und Übersetzung (in dieser Reihenfolge) kombiniert, um eine zusammengesetzte Transformation zu bilden. Das Argument "MatrixOrderAppend", das an die Graphics::RotateTransform-Methode übergeben wird, gibt an, dass die Drehung der Skalierung folgt. Ebenso gibt das Argument "MatrixOrderAppend", das an die Graphics::TranslateTransform-Methode übergeben wird, an, dass die Übersetzung der Drehung folgt.

Rect rect(0, 0, 50, 50);
Pen pen(Color(255, 255, 0, 0), 0);
graphics.ScaleTransform(1.75f, 0.5f);
graphics.RotateTransform(28.0f, MatrixOrderAppend);
graphics.TranslateTransform(150.0f, 150.0f, MatrixOrderAppend);
graphics.DrawRectangle(&pen, rect);

Im folgenden Beispiel werden die gleichen Methodenaufrufe wie im vorherigen Beispiel verwendet, aber die Reihenfolge der Aufrufe wird umgekehrt. Die resultierende Reihenfolge von Vorgängen wird zuerst übersetzt, dann gedreht und dann skaliert. Dies führt zu einem sehr anderen Ergebnis als bei der ersten Skala, rotiert dann und übersetzt:

Rect rect(0, 0, 50, 50);
Pen pen(Color(255, 255, 0, 0), 0);
graphics.TranslateTransform(150.0f, 150.0f);
graphics.RotateTransform(28.0f, MatrixOrderAppend);
graphics.ScaleTransform(1.75f, 0.5f, MatrixOrderAppend);
graphics.DrawRectangle(&pen, rect);

Eine Möglichkeit, die Reihenfolge der einzelnen Transformationen in einer zusammengesetzten Transformation umzukehren, besteht darin, die Reihenfolge einer Sequenz von Methodenaufrufen umzukehren. Eine zweite Möglichkeit, die Reihenfolge der Vorgänge zu steuern, besteht darin, das Matrixreihenfolgeargument zu ändern. Das folgende Beispiel entspricht dem vorherigen Beispiel, mit der Ausnahme, dass "MatrixOrderAppend" in "MatrixOrderPrepend"geändert wurde. Die Matrixmultiplikation erfolgt in der Reihenfolge SRT, wobei S, R und T die Matrizen für Skalierung, Drehung und Übersetzung sind. Die Reihenfolge der zusammengesetzten Transformation wird zuerst skaliert, dann gedreht und dann übersetzt.

Rect rect(0, 0, 50, 50);
Pen pen(Color(255, 255, 0, 0), 0);
graphics.TranslateTransform(150.0f, 150.0f,MatrixOrderPrepend);
graphics.RotateTransform(28.0f, MatrixOrderPrepend);
graphics.ScaleTransform(1.75f, 0.5f, MatrixOrderPrepend);
graphics.DrawRectangle(&pen, rect);

Das Ergebnis des vorherigen Beispiels ist das gleiche Ergebnis wie im ersten Beispiel dieses Abschnitts. Dies liegt daran, dass wir sowohl die Reihenfolge der Methodenaufrufe als auch die Reihenfolge der Matrixmultiplikation umgekehrt haben.