web-dev-qa-db-fra.com

Forcer le mode paysage dans un ViewController à l’aide de Swift

J'essaie de forcer une seule vue dans mon application en mode paysage, J'appelle 

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

override func supportedInterfaceOrientations() -> Int {
    print("supportedInterfaceOrientations")
    return Int(UIInterfaceOrientationMask.LandscapeLeft.rawValue)
}

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

La vue est lancée en mode portrait et continue à tourner lorsque je modifie l'orientation du périphérique. 
Le shouldAutorotate n'est jamais appelé.
Toute aide serait appréciée.

47
sazz

Cela peut être utile pour les autres, j'ai trouvé un moyen de forcer la vue à se lancer en mode paysage:

Mettez ceci dans le viewDidLoad ():

let value = UIInterfaceOrientation.landscapeLeft.rawValue
            UIDevice.current.setValue(value, forKey: "orientation")

et,

override var shouldAutorotate: Bool {
    return true
}
58
sazz

Swift 4

override func viewDidLoad() {
    super.viewDidLoad()
    let value = UIInterfaceOrientation.landscapeLeft.rawValue
    UIDevice.current.setValue(value, forKey: "orientation")
}

override var supportedInterfaceOrientations: UIInterfaceOrientationMask {
    return .landscapeLeft
}

override var shouldAutorotate: Bool {
    return true
}

// Si votre vue est intégrée à un contrôleur de navigation, ce qui précède ne fonctionnera pas. vous devez monter en cascade// Donc ajoutez l'extension suivante après la définition de la classe

extension UINavigationController {

override open var shouldAutorotate: Bool {
    get {
        if let visibleVC = visibleViewController {
            return visibleVC.shouldAutorotate
        }
        return super.shouldAutorotate
    }
}

override open var preferredInterfaceOrientationForPresentation: UIInterfaceOrientation{
    get {
        if let visibleVC = visibleViewController {
            return visibleVC.preferredInterfaceOrientationForPresentation
        }
        return super.preferredInterfaceOrientationForPresentation
    }
}

override open var supportedInterfaceOrientations: UIInterfaceOrientationMask{
    get {
        if let visibleVC = visibleViewController {
            return visibleVC.supportedInterfaceOrientations
        }
        return super.supportedInterfaceOrientations
    }
}}

Swift 3

override func viewDidLoad() {
    super.viewDidLoad()
    let value = UIInterfaceOrientation.landscapeLeft.rawValue
    UIDevice.current.setValue(value, forKey: "orientation")
}

private func supportedInterfaceOrientations() -> UIInterfaceOrientationMask {
    return UIInterfaceOrientationMask.landscapeLeft
}

private func shouldAutorotate() -> Bool {
    return true
}
39
Manee ios

Swift 4 , Testé sur iOS 11

Vous pouvez spécifier l'orientation dans projectTarget -> Général -> DeploymentInfo (orientation du périphérique) -> Portrait (Landscapeleft et Landscaperight sont facultatifs)

AppDelegate

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

LandScpaeViewController

override func viewDidLoad() {
        super.viewDidLoad()
        let appDelegate = UIApplication.shared.delegate as! AppDelegate
        appDelegate.myOrientation = .landscape
}

OnDismissButtonTap

let appDelegate = UIApplication.shared.delegate as! AppDelegate
 appDelegate.myOrientation = .portrait

C'est tout. :)

17
Zeesha

Utiliser Swift 2.2

Essayer:

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

Suivi par:

UIViewController.attemptRotationToDeviceOrientation()

De la référence de classe UIViewController d'Apple:

Certains contrôleurs de vue peuvent souhaiter utiliser des conditions spécifiques à une application pour déterminer les orientations d'interface prises en charge. Si votre contrôleur de vue le fait, lorsque ces conditions changent, votre application doit appeler cette méthode de classe. Le système tente immédiatement de pivoter vers la nouvelle orientation.

Ensuite, comme d'autres l'ont suggéré, remplacez les méthodes suivantes, le cas échéant:

override func supportedInterfaceOrientations() -> UIInterfaceOrientationMask {
    return UIInterfaceOrientationMask.LandscapeLeft
}

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

J'avais un problème similaire avec une vue de signature et cela l'a résolu pour moi.

16
Aidan Malone

Pour moi, les meilleurs résultats ont été obtenus en combinant la réponse de Zeesha à celle de sazz.

Ajoutez les lignes suivantes à AppDelegate.Swift:

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

Ajoutez la ligne suivante à votre classe de contrôleur de vue:

let appDel = UIApplication.shared.delegate as! AppDelegate

Ajoutez les lignes suivantes à la fonction viewDidLoad() de votre contrôleur de vue:

appDel.myOrientation = .landscape
UIDevice.current.setValue(UIInterfaceOrientation.landscapeLeft.rawValue, forKey: "orientation")

(facultatif) Ajoutez cette ligne à votre fonction de renvoi:

appDel.myOrientation = .portrait
UIDevice.current.setValue(UIInterfaceOrientation.portrait.rawValue, forKey: "orientation")

Ces lignes de code définissent l'orientation par défaut sur portrait, font pivoter ce dernier lorsque le contrôleur de vue est chargé, puis le réinitialisent à nouveau lorsque cette dernière se ferme.

8
Microbob

Je devais forcer un contrôleur en orientation portrait. Ajouter cela a fonctionné pour moi.

Swift 4 avec iOS 11

override var   supportedInterfaceOrientations : UIInterfaceOrientationMask{

    return  .portrait

}
6
Rob Schlackman

Fonctionne dans Swift 2.2

 func application(application: UIApplication, supportedInterfaceOrientationsForWindow window: UIWindow?) -> UIInterfaceOrientationMask {
    if self.window?.rootViewController?.presentedViewController is SignatureViewController {

        let secondController = self.window!.rootViewController!.presentedViewController as! SignatureViewController

        if secondController.isPresented {

            return UIInterfaceOrientationMask.LandscapeLeft;

        } else {

            return UIInterfaceOrientationMask.Portrait;
        }

    } else {

        return UIInterfaceOrientationMask.Portrait;
    }
}
2
idris yıldız

Dans ViewController dans la méthode viewDidLoad, appelez la fonction ci-dessous.

func rotateDevice(){
    UIDevice.current.setValue(UIInterfaceOrientation.landscapeLeft.rawValue, forKey: "orientation")
    UIView.setAnimationsEnabled(true) // while rotating device it will perform the rotation animation
}`

Fichier délégué de l'application Ajouter au-dessous de la fonction et des variables

//Orientation Variables
var orientationLock = UIInterfaceOrientationMask.portrait
var myOrientation: UIInterfaceOrientationMask = .portrait

func application(_ application: UIApplication, supportedInterfaceOrientationsFor window: UIWindow?) -> UIInterfaceOrientationMask { return .landscape }
1
Mayur Rathod

Swift 4

En essayant de garder l'orientation, rien ne fonctionnait pour moi:

...        
override func viewDidLoad() {
       super.viewDidLoad()
       forcelandscapeRight()
       let notificationCenter = NotificationCenter.default
       notificationCenter.addObserver(self, selector: #selector(forcelandscapeRight), name: Notification.Name.UIDeviceOrientationDidChange, object: nil)
    }

    @objc func forcelandscapeRight() {
        let value = UIInterfaceOrientation.landscapeRight.rawValue
        UIDevice.current.setValue(value, forKey: "orientation")
    }
....
1
Daxito

Swift 3. Ceci verrouille l'orientation à chaque fois que l'utilisateur rouvre l'application.

class MyViewController: UIViewController {
    ...
    override func viewDidLoad() {
        super.viewDidLoad()

        // Receive notification when app is brought to foreground
        NotificationCenter.default.addObserver(self, selector: #selector(self.onDidBecomeActive), name: NSNotification.Name.UIApplicationDidBecomeActive, object: nil)
    }

    // Handle notification
    func onDidBecomeActive() {
        setOrientationLandscape()
    }

    // Change orientation to landscape
    private func setOrientationLandscape() {
        if !UIDevice.current.orientation.isLandscape {
            let value = UIInterfaceOrientation.landscapeLeft.rawValue
            UIDevice.current.setValue(value, forKey:"orientation")
            UIViewController.attemptRotationToDeviceOrientation()
        }
    }

    // Only allow landscape left
    override var supportedInterfaceOrientations: UIInterfaceOrientationMask {
        return UIInterfaceOrientationMask.landscapeLeft
    }

    /*
    // Allow rotation - this seems unnecessary
    private func shouldAutoRotate() -> Bool {
        return true
    }
    */
    ...
}
1
Greg T

Ma solution est

vient d'ajouter les codes ci-dessous dans AppDelegate 

enum PossibleOrientations {
  case portrait
    case landscape

    func o() -> UIInterfaceOrientationMask {
      switch self {
      case .portrait:
        return .portrait
      case .landscape:
        return .landscapeRight
      }
    }
}
var orientation: UIInterfaceOrientationMask = .portrait

func switchOrientation(to: PossibleOrientations) {
    let keyOrientation = "orientation"

    if to == .portrait && UIDevice.current.orientation.isPortrait {
        return
    } else if to == .landscape && UIDevice.current.orientation.isLandscape {
        return
    }

    switch to {
    case .portrait:
        orientation = .portrait
        UIDevice.current.setValue(UIInterfaceOrientation.portrait.rawValue, forKey: keyOrientation)
    case .landscape:
        orientation = .landscapeRight
        UIDevice.current.setValue(UIInterfaceOrientation.landscapeRight.rawValue, forKey: keyOrientation)
    }
}

Et appelez les codes ci-dessous pour changer 

override func viewDidLoad() {
    super.viewDidLoad()

    if let appDelegate = UIApplication.shared.delegate as? AppDelegate {
        appDelegate.switchOrientation(to: .landscape)
    }
}

ou comme ci-dessous

@IBAction func actBack() {
    if let appDelegate = UIApplication.shared.delegate as? AppDelegate {
        appDelegate.switchOrientation(to: .portrait)
    }
    self.navigationController?.popViewController(animated: true)
}
0
Utku

Selon la documentation de supportedInterfaceOrientations , la méthode shouldAutorotate doit renvoyer true ou YES en Objective-C afin que les supportedInterfaceOrientations soient considérés.

0
Sebastian Wramba

Dans AppDelegate ajouter ceci

//Orientation Variables
    var myOrientation: UIInterfaceOrientationMask = .portrait

    func application(_ application: UIApplication, supportedInterfaceOrientationsFor window: UIWindow?) -> UIInterfaceOrientationMask
    {
        return myOrientation

    }

Ajoutez ceci dans viewController, qui veut changer d'orientation

override func viewDidLoad() {
        super.viewDidLoad()
        self.rotateToLandsScapeDevice()
    }

    override func viewWillDisappear(_ animated: Bool) {
        super.viewWillDisappear(animated)
        self.rotateToPotraitScapeDevice()
    }

    func rotateToLandsScapeDevice(){
        let appDelegate = UIApplication.shared.delegate as! AppDelegate
        appDelegate.myOrientation = .landscapeLeft
        UIDevice.current.setValue(UIInterfaceOrientation.landscapeLeft.rawValue, forKey: "orientation")
        UIView.setAnimationsEnabled(true)
    }

    func rotateToPotraitScapeDevice(){
        let appDelegate = UIApplication.shared.delegate as! AppDelegate
        appDelegate.myOrientation = .portrait
        UIDevice.current.setValue(UIInterfaceOrientation.portrait.rawValue, forKey: "orientation")
        UIView.setAnimationsEnabled(true)
    }
0
Elangovan

// au-dessous du code placé dans le contrôleur de vue// vous pouvez changer landscapeLeft ou portrait

remplace func viewWillAppear (_ animé: Bool) { UIDevice.current.setValue (UIInterfaceOrientation.landscapeRight.rawValue, forKey: "orientation") }

écrasez var shouldAutorotate: Bool { retourne vrai } redéfinissez var supportedInterfaceOrientations: UIInterfaceOrientationMask { retourne .landscapeRight } écrasez var preferredInterfaceOrientationForPresentation: UIInterfaceOrientation { retourne .landscapeRight }

0
Muthuraj M