====== Bilder Rotieren ====== Dieser Abschnitt zeigt wie sich Bilder um einen beliebigen Winkel φ (sprich PHI) rotieren lassen. Rotation (lat. rotatio: Drehung) Dieser Abschnitt ist noch nicht komplett fertiggestellt. ===== Grad- und Bogenmaß ===== Wenn Bilder um einen Winkel $\varphi$ gedreht (rotiert) werden sollen, muss beachtet werden, dass das rotierte Bild eventuell größer als das originale Bild werden kann. | {{ :inf:java:smiley00.png?150 |}} |{{ :inf:java:smiley45.png? |}}| |Das originale Bild ist hier Quadratisch mit ''222x222'' Pixeln.|Das Bild wurde um 45° Grad im Uhrzeigersinn gedreht. Damit das komplette Bild sichtbar ist muss es jetzt ''314x314'' Pixel groß sein. | * Wenn Bilder gedreht werden, ist das Drehzentrum in der Regel der Mittelpunkt des Bildes * Der wichtigste Parameter bei der Rotation ist der Drehwinkel $\varphi$. Die Drehung erfolgt gegen den Uhrzeigersinn * In Java (i.a. in allen Programmiersprachen) werden die Drehwinkel nicht in **Grad**, sondern in **Rad** angegeben. Es gilt 360° = 2 $\pi$ rad. Winkel werden also nicht im **Gradmaß**, sondern im **Bogenmaß** verwendet. Für die Umrechnung vom Gradmaß in das Bogenmaß gilt die Beziehung: \begin{equation} \frac{360° }{\text{Winkel im Gradmaß}} == \frac{2 \pi}{\text{Winkel im Bogenmaß}} \end{equation} ===== Die Transformationsgleichung für die Rotation ===== Bei der Rotation wird jeder Bildpunkt P(x|y) des Originalbildes in einen neuen Bildpunkt P´(x|y) überführt. * mit altem Bildpunkt P( $p_x$ | $p_y$ ) bezeichnen wir die Bildpunkte des originalen Bildes. * mit neuem Bildpunkt P' ( $p\prime_x$ | $p\prime_y$ ) werden die transformierten Bildpunkte bezeichnet //(P´ lies P Strich)//. Gesucht ist eine Transformation, die ausgehend von dem alten Bildpunkt, sowie dem gewünschen Drehwinkel, einen neuen Bildpunkt berechnet. \begin{equation} \left(\begin{array}{}p\prime_x\\p\prime_y\end{array}\right) = R(\varphi)\cdot \left(\begin{array}{}p_x\\p_y\end{array}\right) \end{equation} * "//in Worten//" **neuer Bildpunkt = Transformation $R(\varphi)$ · alter Bildpunkt** * $R(\varphi)$ ist die sogenannte **Transformationsmatrix** um den Winkel $\varphi$ ==== Transformationsgleichungen ==== Wir werden an dieser Stelle die Transformation gleich angeben und anschließend an einem Beispiel zeigen, wie man mit ihr arbeitet. Eine Herleitung dieser Gleichungen ist weiter unten angegeben. Die gesuchten Transformationsgleichungen sind: \begin{equation} \color{blue}{p\prime_x} = cos(\varphi)\cdot \color{red}{p_x} - sin(\varphi) \cdot \color{red}{p_y} \\ \color{blue}{p\prime_y} = sin(\varphi)\cdot \color{red}{p_x} + cos(\varphi) \cdot \color{red}{p_y} \end{equation} {{:inf:sample.gif?|}} {{:inf:aufgabe.gif?|}} Wie lauten die Koordinaten des neuen Bildpunktes bei einer Drehung um **40°**, wenn der alte Bildpunkt **P(10,30)** ist?\\ {{:inf:solution.gif?|}} Für den Sinus und Cosinus ergibt sich: * sin(40°)=0,643 * cos(40°)=0.766 Eingesetzt in die Transformationsformeln ergibt sich: * px´ = 0.766·10 - 0,643·30 = -11,63 * py´ = 0,643·10 + 0,766·30 = 29,41 Die neuen Koordinaten sind damit** P´( -11,63 | 29,41 )**. ==== Java Methode zum Rotieren ==== Die folgende Java Methode benutzt die Java Klasse Point, um die Transformation zu berechnen. public Point rotation(Point point, double angle){ Point result = new Point(); double c = Math.cos(angle); double s = Math.sin(angle); result.x = c*point.x - s*point.y; result.y = s*point.x + c*point.y; return result; } | FIXME|FIXME | |Orginal.|Das um FIXME Grad gedrehte Bild. | ===== Grundprinzip zum Rotieren von Bildern ===== ==== fromScreen ↔ toScreen ==== Um Bilder zu rotieren, müssen grundsätzlich folgende Schritte abgearbeitet werden. Wir gehen hier davon aus, dass das Bild um seine Bildmitte rotiert werden soll. - Vom zu rotierenden Bild $\text{Bild}_{\text{ALT}}$ wird die Größe (Breite und Höhe) ermittelt. - Ein leeres Bild $\text{Bild}_{\text{NEU}}$ wird erzeugt. * Die neue Größe kann aus der alten Größe ermittelt werden! - für jeden Bildpunkt des zu rotierenden Bildes $\text{Bild}_{\text{ALT}}$ gilt nun: * **fromScreen** Die Bildkoordinaten werden in kartesische Koordinaten umgerechnet. * Die kartesischen Koordinaten werden mithilfe der Transformationsformel um einen gegebenen Winkel rotiert. * **toScreen** Die rotierten kartesischen Koordinaten werden wieder in Bildkoordinaten umgerechnet. * Die so berechneten Bildkoordinaten werden im $\text{Bild}_{\text{NEU}}$ gespeichert. Hierbei ist zu beachten, dass Bildkoordinaten **integer** Werte sind und die Transformation in der Regel **double** Werte ergibt. Grundsätzlich sollte man immer mit **double** rechnen. Nur beim Lesen der Bildkoordinaten und beim Schreiben in Bildkoordinaten müssen integer Werte verwendet werden. === fromScreen === |Bildkoordinaten|//fromScreen// → |kartesische Koordinaten| Mit **fromScreen** bezeichnen wir eine Java-Methode, die Bildkoordinaten in (mathematisch) kartesische Koordinaten transformiert. * Kartesische Koordinaten, sind in der Regel** vorzeichenbehaftete double Werte**. * häufig ist der Koordinatenursprung in der Mitte des Bildes überaus zweckmäßig. === toScreen === |kartesische Koordinaten| //toScreen// ** →** |Bildkoordinaten| Mit **toScreen** bezeichnen wir eine Java-Methode, die (mathematisch) kartesische Koordinaten in Bildkoordinaten transformiert. * Bildkoordinaten haben ihren Ursprung (0|0) oben links und besitzen nur positive integer Werte ===== Herleitung der Transformationsgleichung: ===== Wir leiten jetzt die im vorherigen Abschnitt angegeben Transformationsgleichungen her. ==== Voraussetzungen ==== Damit die Herleitung nachvollzogen werden kann, werden lediglich die Additionstheoreme für Sinus und Kosinus benötigt. * cos(φ + α ) = cos(φ)·cos(α) - sin(φ)·sin(α) * sin(φ + α ) = sin(φ)·cos(α) + cos(φ)·sin(α) Eine einfache Herleitung dieser Formel kann mit Hilfe der komplexen Zahlen (Eulerformel) erfolgen. Für unsere Zwecke ist es aber ausreichend, sie in das Gedächtnis gerufen zu haben. ==== Herleitung ==== |{{:inf:java:rot2d.png?320|}} | {{:inf:java:cossin.png?170|}}| |Der rote Punkt wird bei einer Drehung um den Winkel φ in den blauen Punkt überführt (transformiert). |Die oben stehenden Formeln lassen sich direkt aus dem Bild ablesen. \\ **Schauen Sie sich beides solange an, bis ihnen das gelingt!** | |Ausgehend von den Addtionstheoremen für Cosinus und Sinus, werden zuerst cos(α) bzw. sin(α) durch ihre rechten Seiten ersetzt.\\ \\ Jetzt ersetzen wir sin(φ+α) bzw. cos(φ+α) durch ihre rechten Seiten. \\ \\ \\ \\ Der Radius r kürzt sich heraus. | {{:inf:java:herleitung.png?330|}}| | Damit sind die oben angegebenen Transformationsgleichungen gefunden. :-) ||