2010-04-22 6 views
14

Ich war überrascht, keine Antwort auf diese Frage zu finden, vielleicht etwas sehr einfach irgendwie übersehen I:Holen Größe von UIView nach CGAffineTransform Anwendung

Wie die reale Größe eines UIView erhalten, nachdem ich eine CGAffineTransform anwenden es?

z.

meine UIView hat eine Größe von 300 x 200, verwende ich eine Skalierungstransformation sagen wir Faktor 2 sowohl horizontal als auch vertikal, so dass die UIView jetzt 600 x 400 auf dem Bildschirm, aber es ist Grenzen und seine Grenzen sind immer noch eine Größe 300 x 200 ... wo finde ich die wahre Größe der UIView?

ps. vergessen zu erwähnen, dass ich auch die uiview rotieren möchte. Wenn ich nur die Skalierung anwenden CGSizeApplyAffineTransform funktioniert gut, aber wenn es auch Rotation gibt, dann funktioniert es nicht richtig.

Edit: drawnonward mich in die richtige Richtung, ich raffiniert nur ein bisschen den Code zu kompilieren und hier ist es:

UIView* view = (your view being transformed); 
CGAffineTransform trans = (view.transform or create a new transformation); 

CGRect rect = [view bounds]; 
CGMutablePathRef path = CGPathCreateMutable(); 
rect.origin = CGPointZero; 
CGPathAddRect(path , &trans , rect); 
rect = CGPathGetBoundingBox(path); 
CGPathRelease(path); 

Jetzt rect.size enthält die Dimensionen der Ansicht mit der Transformation angewendet Danke nochmal an drawnonward

Antwort

11

[myView frame] gibt den Rahmen der Ansicht aus der Sicht des übergeordneten Elements für Layout und relative Größen zurück. [myView bounds] gibt die Grenzen der Ansicht für das Zeichnen zurück. Wenn Transformationen auf mehrere Ansichten angewendet werden, können Sie convertRect: in oder aus einer Ansicht verwenden.

Edit:

Vielleicht so etwas wie dieses.

CGRect rect = [view bounds]; 
CGPathRef path = CGPathCreateMutable(); 
rect.origin = CGPointZero; 
CGPathAddRect(rect , [view transform]); 
rect = CGPathGetBoundingBox(path); 
CGPathRelease(path); 

Die Verwendung [view center] die Position in der Superview zu finden.

+1

Hier ist die Dokumentation über "Frame" aus dem Apple Doc: Warnung: Wenn die Transformationseigenschaft nicht die Identitätstransformation ist, ist der Wert dieser Eigenschaft undefiniert und sollte daher ignoriert werden. Frame kommt also nicht in Frage, wenn eine Transformation angewendet wird. Und "Grenzen" gibt immer die Originalgröße zurück –

+0

In der Tat! Argh, diese Funktion Bibliotheken, die ich immer vergessen - CGPathGetBoundingBox war der Trick. Ich habe die Frage mit dem Arbeitscode bearbeitet, danke viel Mann –

+0

Beachten Sie auch, dass die Center-Eigenschaft funktionieren soll, auch mit Nicht-Identität-Transformationen. – Olie

2

Verwenden Sie CGSizeApplyAffineTransform(size, transform) und es wird eine transformierte Größe zurückgegeben. Es gibt ähnliche Funktionen wie CGPoint und CGRect.

+0

Das funktioniert nicht richtig, wenn CGSizeApplyAffineTransform auch Rotation enthält, aber ansonsten sind Sie in den Fällen richtig, in denen nur Skalierung angewendet wird. (Mein Fehler, ich habe auch Rotation in meine Frage nicht eingeschlossen) –

2

Einfachere: Eine Ansicht mit (Grenzen) Größe s, auf die TR-Transformation angewendet resultierende Größe:

CGSizeMake(s.width*hypotf(tr.a, tr.b), s.height*hypotf(tr.c, tr.d)) 

Wenn jedoch Ansicht des Super oder jede Vorfahr hat noch keine nicht-Einheit Transformation angewendet, diese Größe macht in absoluten Zahlen wenig Sinn.

Wenn Sie die absolute Größe einer Ansicht in Fensterkoordinaten wünschen, nachdem eine beliebige Transformation auf diese Ansicht oder ihre Übersichten angewendet wurde, sollten Sie zunächst die absolute Transformationsmatrix berechnen, indem Sie die gesamte Ansicht in das Stammfenster transformieren. und wenden Sie dann die obige Formel auf das Ergebnis an.

33

Ich benutze:

CGRect transformedBounds = CGRectApplyAffineTransform(view.bounds, view.transform); 
+0

Ich glaube, nur "view.bounds" wäre eine bessere Antwort. Warum transformierst du hier die Grenzen, anstatt nur die Größe des Rahmens zu nehmen? –

0

Aber Sie gelten eine rotierende verwandeln, es nicht bekommen richtige Größe von CGPathGetBoundingBox.

2

Alte Frage, stieß aber hier, nach der Suche nach einer Lösung und Tonnen von Versuchen.Es war einfach;

view.layer.frame hat alle Transformationen angewendet und Sie erhalten die Größe von view.layer.frame.size leicht.

- hier unten ist keine Antwort auf diese Frage - -

Und für mein Problem, ich neuen center Wert zu berechnen versuche nach layer.anchorPoint meiner gedrehten Ansicht zu ändern, so dass er sich nicht bewegt . Und schließlich war es so;

CGPoint topLeft = [self.superview convertPoint:CGPointMake(0, 0) fromView:self]; 
self.layer.anchorPoint = CGPointMake(0, 0); 
self.center = topLeft; 

für reverse

CGPoint center = [self.superview convertPoint:CGPointMake(self.bounds.size.width/2, self.bounds.size.height/2) fromView:self]; 
self.layer.anchorPoint = CGPointMake(.5, .5); 
self.center = center; 

schließlich.

Verwandte Themen