禁用UIView的自动旋转

时间:2010-07-21 16:05:14

标签: iphone uiview uiinterfaceorientation

我的应用程序由后台UIView中的工具栏和AVCaptureVideoPreviewLayer组成。 我希望看到工具栏按设备方向旋转,所以在我的主ViewController中,我实现了这个功能:

- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
    return (interfaceOrientation == UIInterfaceOrientationPortrait
            || interfaceOrientation == UIInterfaceOrientationLandscapeLeft
            || interfaceOrientation == UIInterfaceOrientationLandscapeRight);
}

这样可以正常工作,但是当界面方向改变时,我看到背景UIView(带有视频图层)也在旋转,所以我的视频视图现在向左或向右旋转90度...这不是真的很酷!
所以我的问题是:有没有办法在特定的UIView上禁用自动旋转动画?

我已经看到了一个类似的问题:Disabling autorotate for a single UIView,但答案不符合我的问题,我真的需要背景视图不要移动,不要用一种解决问题“反击动画”。所以我决定提出这个话题。

有什么想法吗?

谢谢!

5 个答案:

答案 0 :(得分:11)

这篇文章指出了正确的方向。为了让AVCaptureVideoPreviewLayer不与设备一起旋转,我将其包裹在UIView中并以相反的方向为该视图设置动画:

- (void) willAnimateRotationToInterfaceOrientation:(UIInterfaceOrientation)toInterfaceOrientation duration:(NSTimeInterval)duration {

    float rotation;

    if (toInterfaceOrientation==UIInterfaceOrientationPortrait) {
        rotation = 0;
    } else
    if (toInterfaceOrientation==UIInterfaceOrientationLandscapeLeft) {
        rotation = M_PI/2;
    } else
    if (toInterfaceOrientation==UIInterfaceOrientationLandscapeRight) {
        rotation = -M_PI/2;
    }

    [UIView animateWithDuration:duration animations:^{
        cameraPreview.transform = CGAffineTransformMakeRotation(rotation);
        cameraPreview.frame = self.view.frame;
    }];
}

似乎有点迂回,但它动画很顺利。预览图层顶部的其他视图会自动旋转。

答案 1 :(得分:2)

- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation {
  return NO;
}

或者您是说只有在显示某个视图时才禁用它?如果是这样,您可以使用UIView的isDescendantOfView方法检查这一点。

答案 2 :(得分:2)

我终于找到了一个明智的答案。不再乱用“反旋转动画”等等!

关键是使用UIViewController作为预览图层(非旋转视图),使用另一个作为实际界面。使用shouldAutorotateToInterfaceOrientation配置两者的旋转选项:(代码在上面的答案中):

  • 预览视图控制器应设置为不旋转
  • 应将界面视图控制器设置为旋转到您需要的方向

重要的一点是通过将视图直接添加到窗口来保持视图分离。我在AppDelegate中执行此操作:

[self.window addSubview:previewViewController.view];
[self.window addSubview:interfaceViewController.view];
self.window.rootViewController = interfaceViewController;
[self.window makeKeyAndVisible];

将视频预览置于后台,然后在其上添加界面视图。界面可以自由旋转,而不会影响预览。

需要注意的一件重要事项:界面视图的背景应该是透明的,否则会阻止预览。

答案 3 :(得分:1)

我遇到了同样的问题,但只是在AVCaptureVideoPreviewLayer上设置orientation属性是不够的。另外一个问题是CALayer不支持iPhone上的布局管理器,因此旋转设备时视频图层的框架可能不正确。

我通过使用自定义UIView来修复此问题以包含AVCaptureVideoPreviewLayer,然后我覆盖此视图的layoutSubviews方法,以确保始终正确设置视频图层的帧。这也是设置orientation属性的好地方。也就是说,我的UIView看起来像:

@implementation VideoPreview

@synthesize previewLayer;

- (void) layoutSubviews {
    if (previewLayer) {
        // set the correct orientation for the video layer
        previewLayer.orientation = [[UIDevice currentDevice] orientation];

        // and set its frame to that of its parent UIView
        previewLayer.frame = self.bounds;
    }
}

- (void) addPreviewLayer: (AVCaptureVideoPreviewLayer *) videoLayer {
    previewLayer = videoLayer;
    [self.layer addSublayer:videoLayer];
}

@end

答案 4 :(得分:-2)

试试这个:

myVideoCaptureLayer.orientationSupported = NO;