如何锁定一个视图控制器的方向?

时间:2015-04-29 17:21:46

标签: ios swift orientation portrait

我可以在一个控制器中设置纵向和锁定方向吗?

我确实尝试过:

override func supportedInterfaceOrientations() -> Int {
    return Int(UIInterfaceOrientationMask.Portrait.rawValue)
}

override func shouldAutorotate() -> Bool{
    return false
}

但它对我没有帮助。我必须添加其他内容吗?

6 个答案:

答案 0 :(得分:7)

此代码应该有效:

    override func supportedInterfaceOrientations() -> Int {
        return Int(UIInterfaceOrientationMask.Portrait.rawValue)
    }

    override func shouldAutorotate() -> Bool{
        return false
    }

    override func preferredInterfaceOrientationForPresentation() -> UIInterfaceOrientation {
        return UIInterfaceOrientation.Portrait
    }

如果它现在适合你,那么我想你的控制器在另一个控制器中(UINavigationControllerUITabBarControllerUISplitViewController)。在这种情况下,您需要在该父控制器中使用此代码。

如果您的导航控制器包含多个视图控制器,并且您只需要为其中某些视图控制器禁用方向,那么您需要继承UINavigationController类并写下类似的内容:

class NavigationController: UINavigationController {

    var shouldRotate: Bool = true

    override func supportedInterfaceOrientations() -> Int {
        return shouldRotate ? Int(UIInterfaceOrientationMask.Portrait.rawValue) : Int(UIInterfaceOrientationMask.All.rawValue)
    }

    override func shouldAutorotate() -> Bool{
        return shouldRotate
    }
}

然后在控制器中,您需要禁用方向,您可以为导航控制器禁用它:

class ViewController: UIViewController {

    var lastControllerRotationStatus: Bool?

    override func viewWillAppear(animated: Bool) {
        super.viewWillAppear(animated)

        if let navigationController = self.navigationController as? NavigationController {
            lastControllerRotationStatus = navigationController.shouldRotate
            navigationController.shouldRotate = false
        }
    }

    override func viewDidDisappear(animated: Bool) {
        super.viewDidDisappear(animated)

        if let navigationController = self.navigationController as? NavigationController {
            navigationController.shouldRotate = lastControllerRotationStatus ?? true
        }
    }
}

但请记住,您需要在控制器被推出导航控制器后恢复旧的旋转状态。在这个例子中,我在更改之前保存旋转状态,并在控制器消失后恢复它。您也可以使用其他方法。例如,您可以重载UINavigationController方法popViewController,并将shouldRotate设置为false。

使用控制器进行变量设置的相同方法可用于控制来自AppDelegate方法application(application: UIApplication, supportedInterfaceOrientationsForWindow window: UIWindow) -> Int的旋转

然后您不需要继承导航控制器。

您的AppDelegate班级代码如下:

class AppDelegate: UIResponder, UIApplicationDelegate {

    var window: UIWindow?

    var shouldRotate = true
    func application(application: UIApplication, supportedInterfaceOrientationsForWindow window: UIWindow?) -> Int {

        return shouldRotate ? Int(UIInterfaceOrientationMask.All.rawValue) : Int(UIInterfaceOrientationMask.Portrait.rawValue)

    }

}

您的控制器代码如下所示:

class ViewController: UIViewController {

    var lastControllerRotationStatus: Bool?

    override func viewWillAppear(animated: Bool) {
        super.viewWillAppear(animated)

        if let appDelegate = UIApplication.sharedApplication().delegate as? AppDelegate {
            lastControllerRotationStatus = appDelegate.shouldRotate
            appDelegate.shouldRotate = false
        }
    }

    override func viewDidDisappear(animated: Bool) {
        super.viewDidDisappear(animated)

        if let appDelegate = UIApplication.sharedApplication().delegate as? AppDelegate {
            appDelegate.shouldRotate = lastControllerRotationStatus ?? true
        }
    }
}

答案 1 :(得分:4)

如果你想要纵向方向,但你只想锁定一个viewController(例如在横向上),你可以这样做:

这对我使用Swift 2.0

<强>的AppDelegate

var shouldRotate = true

//MARK: - Func to rotate only one view controller
func application(application: UIApplication, supportedInterfaceOrientationsForWindow window: UIWindow?) -> UIInterfaceOrientationMask {

    if (shouldRotate == true){
        return UIInterfaceOrientationMask.All
    }

    return UIInterfaceOrientationMask.Landscape

}

<强>的ViewController

    override func viewDidLoad() {
        super.viewDidLoad()

        // 1. lock the rotation
        let appdelegate = UIApplication.sharedApplication().delegate as! AppDelegate
        appdelegate.shouldRotate = false

        // 2. Force the device in landscape mode when the view controller gets loaded
        UIDevice.currentDevice().setValue(UIInterfaceOrientation.LandscapeRight.rawValue, forKey: "orientation")
    }

    override func shouldAutorotate() -> Bool {
        // 3. Lock autorotate
        return false
    }

    override func supportedInterfaceOrientations() -> UIInterfaceOrientationMask {
        return [UIInterfaceOrientationMask.LandscapeRight, UIInterfaceOrientationMask.LandscapeLeft]
    }


    override func preferredInterfaceOrientationForPresentation() -> UIInterfaceOrientation {

        // 4. Only allow Landscape
        return UIInterfaceOrientation.LandscapeRight
    }

    // 5. Restoring the locked-rotation before controller disappeared
    override func viewWillDisappear(animated: Bool) {
        let appdelegate = UIApplication.sharedApplication().delegate as! AppDelegate
        appdelegate.shouldRotate = true
    }

答案 2 :(得分:1)

我在类似的问题上发现了这一点。 Link

&#34;首先,我真的非常感谢zellb给我这个答案让我明白。为了将一个视图控制器的设备方向设置为纵向,将其他视图控制器设置为两者,你可以在AppDelegate设置它.swift使用了这个函数,它有supportedInterfaceOrientationsForWindow

func application(application: UIApplication, supportedInterfaceOrientationsForWindow window: UIWindow) -> Int {

return checkOrientation(self.window?.rootViewController?)// This is the custom function that u need to set your custom view to each orientation which u want to lock

}

以下是根据您的需要检查每个视图控制器设置纵向或全方位的功能。

func checkOrientation(viewController:UIViewController?)-> Int{

if(viewController == nil){

    return Int(UIInterfaceOrientationMask.All.rawValue)//All means all orientation

}else if (viewController is SignInViewController){

    return Int(UIInterfaceOrientationMask.Portrait.rawValue)//This is sign in view controller that i only want to set this to portrait mode only

}else{

    return checkOrientation(viewController!.presentedViewController?)
}
}

并且不要忘记设置您想要在属性检查器中锁定的视图控制器,其中包括方向&#34;纵向&#34;和其他人推测&#34;&#34;

希望有所帮助。

答案 3 :(得分:0)

将它放在viewDidAppear:

let value = UIInterfaceOrientation.Portrait.rawValue
UIDevice.currentDevice().setValue(value, forKey: "orientation")

答案 4 :(得分:0)

Swift 3答案:

在视图控制器中,您想要锁定

的方向
override var shouldAutorotate: Bool {
    return false
}

override var supportedInterfaceOrientations: UIInterfaceOrientationMask {
    return .portrait
}

override var preferredInterfaceOrientationForPresentation: UIInterfaceOrientation {
    return .portrait
}

改编自how to lock portrait orientation for only main view using swift

答案 5 :(得分:0)

**添加到AppDelegate文件:*

var orientationLock = UIInterfaceOrientationMask.all
  func application(_ application: UIApplication, supportedInterfaceOrientationsFor window: UIWindow?) -> UIInterfaceOrientationMask {
    return self.orientationLock
  }

  struct AppUtility {
    static func lockOrientation(_ orientation: UIInterfaceOrientationMask) {
      if let delegate = UIApplication.shared.delegate as? AppDelegate {
        delegate.orientationLock = orientation
      }
    }

    static func lockOrientation(_ orientation: UIInterfaceOrientationMask, andRotateTo rotateOrientation:UIInterfaceOrientation) {
      self.lockOrientation(orientation)
      UIDevice.current.setValue(rotateOrientation.rawValue, forKey: "orientation")
    }
  }

添加到要强制定位的viewcontroller:

override func viewDidAppear(_ animated: Bool) {
    super.viewDidAppear(animated)
    AppDelegate.AppUtility.lockOrientation(.portrait)
  }

  override func viewWillDisappear(_ animated: Bool) {
    super.viewWillDisappear(animated)
    AppDelegate.AppUtility.lockOrientation(.all)
  }