在iOS 13中,模态视图控制器在呈现时有一个新的行为。

现在它不是全屏默认情况下,当我向下滑动时,应用会自动解除视图控制器。

我怎么能防止这种行为,并回到旧的全屏模态vc?

谢谢


当前回答

提示:如果你调用present to一个嵌入在NavigationController内部的ViewController,你必须将NavigationController设置为。fullscreen,而不是VC。

你可以像@davidbates这样做,也可以通过编程方式(像@pascalbros)这样做。

同样适用于UITabViewController

一个NavigationController的示例场景:

    //BaseNavigationController: UINavigationController {}
    let baseNavigationController = storyboard!.instantiateViewController(withIdentifier: "BaseNavigationController")
    var navigationController = UINavigationController(rootViewController: baseNavigationController)
    navigationController.modalPresentationStyle = .fullScreen
    navigationController.topViewController as? LoginViewController
    self.present(navigationViewController, animated: true, completion: nil)

其他回答

提示:如果你调用present to一个嵌入在NavigationController内部的ViewController,你必须将NavigationController设置为。fullscreen,而不是VC。

你可以像@davidbates这样做,也可以通过编程方式(像@pascalbros)这样做。

同样适用于UITabViewController

一个NavigationController的示例场景:

    //BaseNavigationController: UINavigationController {}
    let baseNavigationController = storyboard!.instantiateViewController(withIdentifier: "BaseNavigationController")
    var navigationController = UINavigationController(rootViewController: baseNavigationController)
    navigationController.modalPresentationStyle = .fullScreen
    navigationController.topViewController as? LoginViewController
    self.present(navigationViewController, animated: true, completion: nil)

这对我很有效

let vc = self.storyboard?.instantiateViewController(withIdentifier: "storyboardID_cameraview1") as! CameraViewController
  
vc.modalPresentationStyle = .fullScreen
    
self.present(vc, animated: true, completion: nil)`
let Obj = MtViewController()
Obj.modalPresentationStyle = .overFullScreen
self.present(Obj, animated: true, completion: nil)

//如果你想禁用滑动来消除它,添加行

Obj.isModalInPresentation = true

查看苹果文档获取更多信息。

我在ios 13中使用了swizzling

import Foundation
import UIKit

private func _swizzling(forClass: AnyClass, originalSelector: Selector, swizzledSelector: Selector) {
    if let originalMethod = class_getInstanceMethod(forClass, originalSelector),
       let swizzledMethod = class_getInstanceMethod(forClass, swizzledSelector) {
        method_exchangeImplementations(originalMethod, swizzledMethod)
    }
}

extension UIViewController {

    static let preventPageSheetPresentation: Void = {
        if #available(iOS 13, *) {
            _swizzling(forClass: UIViewController.self,
                       originalSelector: #selector(present(_: animated: completion:)),
                       swizzledSelector: #selector(_swizzledPresent(_: animated: completion:)))
        }
    }()

    @available(iOS 13.0, *)
    @objc private func _swizzledPresent(_ viewControllerToPresent: UIViewController,
                                        animated flag: Bool,
                                        completion: (() -> Void)? = nil) {
        if viewControllerToPresent.modalPresentationStyle == .pageSheet
                   || viewControllerToPresent.modalPresentationStyle == .automatic {
            viewControllerToPresent.modalPresentationStyle = .fullScreen
        }
        _swizzledPresent(viewControllerToPresent, animated: flag, completion: completion)
    }
}

然后放这个

UIViewController.preventPageSheetPresentation

的某个地方

例如在AppDelegate中

func application(_ application: UIApplication,
                 didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey : Any]?) -> Bool {

    UIViewController.preventPageSheetPresentation
    // ...
    return true
}

以上的答案和建议是正确的,下面是另一个版本,和有效的方法使用编程。

创建一个UIView扩展

创建一个方法()

//#1
extension UIViewController {

//#2
func presentLocal(_ viewControllerToPresent: UIViewController, animated flag: 
Bool, completion: (() -> Void)? = nil) {

//Reusing below 2 lines :-)
viewControllerToPresent.modalPresentationStyle = .overCurrentContext
self.present(viewControllerToPresent, animated: flag, completion: completion)

  }
}

调用如下所示

let vc = MyViewController()
let nc = UINavigationController(rootViewController: vc)
sourceView.presentLocal(nc, animated: true, completion: nil)

OR

let vc = MyViewController()
sourceView.presentLocal(vc, animated: true, completion: nil)