3

有一个我真正喜欢的图书馆,你可以在这里找到(https://github.com/pixyzehn/MediumMenu)。有没有办法查看另一个UIViewController后面的UIViewController而不会搞乱AppDelegate窗口?

本质上,它具有以下功能:

MediumMenu Demo

在后面的菜单实际上是一个UIViewController。如果我们深入到源代码,我们会发现下面的非常重要的代码:

public init(items: [MediumMenuItem], forViewController: UIViewController) { 
    self.init() 
    self.items = items 
    height = screenHeight - 80 // auto-calculate initial height based on screen size 
    frame = CGRect(x: 0, y: 0, width: screenWidth, height: height) 
    contentController = forViewController 
    menuContentTableView = UITableView(frame: frame) 
    menuContentTableView?.delegate = self 
    menuContentTableView?.dataSource = self 
    menuContentTableView?.showsVerticalScrollIndicator = false 
    menuContentTableView?.separatorColor = UIColor.clearColor() 
    menuContentTableView?.backgroundColor = menuBackgroundColor 
    addSubview(menuContentTableView!) 

    if panGestureEnable { 
     let pan = UIPanGestureRecognizer(target: self, action: #selector(MediumMenu.didPan(_:))) 
     contentController?.view.addGestureRecognizer(pan) 
    } 

    let menuController = UIViewController() 
    menuController.view = self 

    UIApplication.sharedApplication().delegate?.window??.rootViewController = contentController 
    UIApplication.sharedApplication().delegate?.window??.insertSubview(menuController.view, atIndex: 0) 
} 

前几行是不是真的很重要,但最后行(那​​些对付UIApplication.sharedApplication().delegate?.window??是关键到这个库工作,但他们也限制了库。

根据这些行,我们使UIViewController,我们希望菜单为rootViewController,然后我们将菜单视图添加到0指数(我猜这是什么把它放在后面,在contentController之后)

库存问题:

只有当您需要初始视图控制器上的菜单时,该库才有效。从某种意义上说,只有contentController已经是rootViewController。它实际上会在我的应用程序中为我运行,但是我不能继续回到我的原始UIViewController,因为它不再处于层次结构中。

我有一个场景,我有一个登录视图控制器,并且当您成功登录时,我会将您添加到我想要的菜单的UINavigationController中。问题的第一个明确标志是我收到投诉“警告:尝试在其视图不在窗口层次结构中的LoginViewController上呈现UINavigationController!”显然,它不在窗口层次结构中,因为我正在重新分配rootViewController。

我不知道如何解决这个问题。有没有办法让这个功能工作时,UIViewController我想菜单上不是初始视图控制器?

+0

你最初的'UIViewController'是'UINavigationController'吗? –

回答

3

简短的回答是:是的

这可以用通过分配UIViewControllerTransitioningDelegateViewController含有list-menu和实施interactionControllerForPresentation()interactionControllerForDismissal()方法来实现。您不必触碰UIWindow,直接)。

你可以改变这部分关于现有的library,但从它的外观来看,它只是一个TableView的幻想过渡。你可以很容易地实现这一点。

查看Apple的API Reference交互式转场和this tutorial Ray Wenderlich举例说明。

2

所以很清楚你的情况是:

  1. rootViewController =一个UINavigationController
  2. UINavigationControllerrootViewController是的LoginController
  3. 当有人登录成功,navigationController推(或SEGUE)到menuController

or

  1. rootViewController是的LoginController
  2. 当有人登录成功,它会出现menuController

所以关键点是获得menuController,而不是将其设置为应用程序的rootViewController

这里是我做了一些改变以适应您的要求的代码。 https://github.com/Moonsownner/MediumMenu-master

我做了什么:

  1. MediumMenu实际上是一个UIView,我们要创建一个控制器来遏制它,以便使过渡。所以我做了一个名为MediumMenuController的新班级。你可以看到我将showMenu功能移到MediumMenuController。所以如果有人想手动显示菜单,目标必须是一个MediumMenuController而不是之前的NavigationController。而MediumMenuController将包含您发送到MediumMenuController的init函数中的业务控制器。
class MediumMenuController: UIViewController { 

    let menuView: MediumMenu 
    let child: UIViewController 

    init(items: [MediumMenuItem], childController: UIViewController){ 
     self.menuView = MediumMenu(items: items, forViewController: childController) 
     self.child = childController 
     super.init(nibName: nil, bundle: nil) 
    } 

    required init?(coder aDecoder: NSCoder) { 
     fatalError("init(coder:) has not been implemented") 
    } 

    override func viewDidLoad() { 
     super.viewDidLoad() 

     view.addSubview(menuView) 
     addChildViewController(child) 
     self.view.addSubview(child.view) 
     child.view.frame = UIScreen.mainScreen().bounds 
     child.didMoveToParentViewController(self) 

    } 

    func showMenu() { 
     menuView.show() 
    } 

} 
  • 我在MediumMenu删除的代码。
  • let menuController = UIViewController(); 。menuController.view =自 UIApplication.sharedApplication()委派.window ?? RootViewController的 = contentController UIApplication.sharedApplication()委派.window ?? insertSubview?。?。(menuController.view, atIndex:0)

    并创建一个名为MediumMenuController的新控制器,以便将MediumMenu和其他控制器视图添加到该控制器。

    也许通过上述说法并不清楚。代码可以显示细节。祝你好运。

    +0

    你的答案应该显示关键代码的增加,而不是单独删除,因为最终yhat链接将会中断,这个答案将毫无意义 – Wain

    +0

    你是对的。我的错。 –

    2

    您可以通过以下步骤实现它。

    (i)将LoginViewController设为rootViewController。(ii)当用户登录成功时,将用户重定向到主屏幕。这是您成功登录后想要显示的第一个屏幕。

    (iii)您可以在其中显示菜单的父级UIViewControllers。 (iv)然后,初始化任何UIViewController时,父类将调用public init(items: [MediumMenuItem], forViewController: UIViewController)方法,并且可以用下面的代码替换最后两行。 self.view.insertSubview(menuController.view, atIndex: 0)

    (v)点击退出按钮,您可以简单地关闭显示的视图控制器,所以LoginViewController将永远在那里。

    希望这会有所帮助!

    相关问题