Czy jest możliwe uzyskanie tylko kąta obrotu z CGAffineTransform, który ma również wartości translacji i skalowania? Jeśli tak, w jaki sposób?Uzyskaj tylko obrót z CGAffineTransform
Z góry dziękuję!
Czy jest możliwe uzyskanie tylko kąta obrotu z CGAffineTransform, który ma również wartości translacji i skalowania? Jeśli tak, w jaki sposób?Uzyskaj tylko obrót z CGAffineTransform
Z góry dziękuję!
Weź asin() lub acos() afinicznego członka b lub c.
struct CGAffineTransform {
CGFloat a;
CGFloat b;
CGFloat c;
CGFloat d;
CGFloat tx;
CGFloat ty;
};
Możesz spróbować użyć funkcji acos() i asin(), aby odwrócić to, co robi CGAffineTransformMakeRotation. Jednakże, ponieważ macie pomnożoną macierz przekształcenia skali, może to być nieco trudne.
że w przeszłości stosowane klasy XAffineTransform z zestawu narzędzi GeoTools wyodrębnić obrót z matrycy afinicznej. Działa nawet wtedy, gdy zastosowano skalowanie i ścinanie.
Jest to biblioteka Java, ale powinieneś być w stanie z łatwością przekonwertować ją na (Objective-) C. Możesz spojrzeć na the source for XAffineTransform here. (Metoda nazywa się getRotation.) Możesz też read the API here.
To jest serce metody:
final double scaleX = getScaleX0(tr);
final double scaleY = getScaleY0(tr) * flip;
return Math.atan2(tr.getShearY()/scaleY - tr.getShearX()/scaleX,
tr.getScaleY()/scaleY + tr.getScaleX()/scaleX);
trzeba by też realizować getScale/getShear metod. Wcale nie twardy. (W większości przypadków można po prostu skopiować kod Java jak jest.)
atan2(rotationTransform.b, rotationTransform.d)
acos (b) rozwiązanie sugerowane przez kogoś jest ważny tylko w zakresie +/- 0.5pi. To rozwiązanie wydaje się być niezawodne w kombinacji rotacji, translacji i skalowania, chociaż prawie na pewno nie jest ścinaniem. Moja wcześniejsza odpowiedź (atan2(rotationTransform.b, rotationTransform.a
) nie była odporna na skalowanie.
Myślę, że powinno to być 'atan2 (rotationTransform.b, rotationTransform.d)' –
Luiz - Są one takie same i poprawne pod kombinacjami translacji i obrotu, ale wydaje się, że twoje zachowanie pozostaje poprawne po dodaniu skalowania, więc idę zaktualizować. Dziękuję Ci. –
using transform.b, transform.d zapisany dzień! Dzięki! – srik
asin i acos nie są poprawne, gdy występuje skala.
poprawna formuła brzmi:
CGFloat radians = atan2f(self.view.transform.b, self.view.transform.a);
CGFloat degrees = radians * (180/M_PI);
czyli
CGFloat angle = [(NSNumber *)[view valueForKeyPath:@"layer.transform.rotation.z"] floatValue];
Matematyka za to wyjaśniono w "Math Za matryc" podsekcji Programming Guide Quartz 2D: http: // developer.apple.com/mac/library/DOCUMENTATION/GraphicsImaging/Conceptual/drawingwithquartz2d/dq_affine/dq_affine.html#//apple_ref/doc/uid/TP30001066-CH204-CJBECIAD –
asin i acos nie są poprawne, gdy występuje skala. poprawna formuła to: CGFloat radians = atan2f (self.view.transform.b, self.view.transform.a); Stopnie CGFloat = radian * (180/M_PI); – lbsweek