在哪里设置CGAffineTransformMakeScale(2,2);

时间:2013-03-18 17:59:16

标签: ios objective-c calayer

我正在使用最新的SDK开发iOS应用程序。

我以这种方式创建AVCaptureVideoPreviewLayer

// Create the preview layer
_videoPreviewLayer = [[AVCaptureVideoPreviewLayer alloc] initWithSession:_captureSession];
[_videoPreviewLayer setFrame:self.view.bounds];
_videoPreviewLayer.videoGravity = AVLayerVideoGravityResizeAspectFill;
[self.view.layer insertSublayer:_videoPreviewLayer atIndex:0];

现在我想这样做:

_videoPreviewLayer.affineTransform = CGAffineTransformMakeScale(2, 2);

但如果我把它放在[_videoPreviewLayer setFrame:self.view.bounds];之前,我会得到与之后不同的结果。

我在哪里申请比例?

而且,如果我想设置CGAffineTransformMakeRotation(-M_PI_2); // -90 degrees,我该在哪里做?

1 个答案:

答案 0 :(得分:1)

您不应在变换不是标识的视图上使用setFrame。根据Apple关于UIView框架属性的文档:

  

如果transform属性不是identity变换,则此属性[frame]的值是未定义的,因此应该被忽略。

在UIView.h中,在frame属性

之上
  

如果转换视图,请不要使用框架,因为它无法正确反映视图的实际位置。使用bounds + center。

因此,如果您在此代码中切换到使用setBounds和setCenter而不是setFrame,那么您可能会获得所需的一致结果。

直接回答问题:如果您还使用setFrame,则没有正确的位置来放置这些变换(比例或旋转)。如果使用setBounds和setCenter,那么无论是在setBounds / setCenter之前还是在setBounds / setCenter之后应用转换,都会得到相同的结果。

编辑:VansFannel指出这是一个CALayer,而不是UIView,因此上述评论并不真正适用。我要离开他们,以免剥夺VansFannel对上下文的评论,也因为它对UIViews来说仍然是个好警告

现在,对于CALayers,如果设置框架(如[_videoPreviewLayer setFrame:self.view.bounds]),即使_videoPreviewLayer具有非标识转换,也会导致_videoPreviewLayer的实际渲染帧为self.view.bounds。重要的是要记住CALayer的框架实际上是派生属性。它来自图层的边界,位置,anchorPoint和变换。当你使用setFrame时,QuartzCore将计算出一个边界和位置,它产生你在现有的anchorPoint和transform下传递给setFrame的帧。

因此,如果您希望这些转换产生任何效果,则应在调用setFrame之后将其设置为。如果先设置变换,那么setFrame将有效地否定它们。如果您绝对需要先设置变换,则必须避免使用setFrame并直接使用图层的边界和位置。