【问题标题】:Swift 4: Presenting ViewControllers with a UIView as the frameSwift 4:以 UIView 作为框架呈现 ViewControllers
【发布时间】:2018-05-30 14:12:39
【问题描述】:

我会尽力解释我的问题,所以提前谢谢。

我通常通过让每个 ViewController 代表不同的视图来构建具有多个视图控制器的应用程序。现在,我正在创建一个具有许多不同视图的大型应用程序。我不想在我的应用程序中有 15 个以上的视图控制器。我宁愿让一个 ViewController 继承不同的 UIView。

例如,如果我在菜单栏上选择“设置”选项。然后我会被带到 selectionController 并让 selectionController 继承名为 Settings View 的 UIView

目前我可以导航到我的 settingsController 并让导航栏代表所选的选项。但是我将如何继承 View 呢?

当一个选项被选中时,这个函数被调用..

//Whatever option selected will affect which view is inherited

    let option = self.menuOptions[indexPath.row]
        if option.name != "Home" {
            self.homeController?.displayController(menuOption: menuOption, view: self.settingsView)
        }

家庭控制器

class HomeController: UIViewController {
lazy var menu: Menu = {
    let menuLauncher = Menu()
    menuLauncher.homeController = self
    return menuLauncher
}()

override func viewDidLoad() {
    super.viewDidLoad()
    navigationItem.title = "Home"
        view.backgroundColor = Color.blue
        navigationItem.leftBarButtonItem = UIBarButtonItem(image: UIImage(named: "menu"), style: .plain, target: self, action: #selector(displayMenu))
}

func displayController(menuOption: MenuOption, view: UIView) {
    let selectionController = UIViewController()
    selectionController.navigationItem.title = menuOption.name
    selectionController.view.backgroundColor = Color.blue

//Why dosen't this present the view I have assigned to it??
    selectionController.view.addSubview(HomeView(frame: view.frame))
    navigationController?.navigationBar.tintColor = UIColor.white
    navigationController?.pushViewController(selectionController, animated: true)
}

@objc func displayMenu() {
    menu.displayMenu()
}

}

【问题讨论】:

  • 您正确地展示了视图。我怀疑SelectionController的frame太小或者没有设置。
  • 你会如何设置它?我认为框架是它自己的东西,永远不需要设置。
  • 首先,您应该在调用selectionController.view.addSubview(HomeView(frame: view.frame)) 的位置设置一个断点,并检查view.frameselectionController.view.frame 的大小。看看它们是否有宽度和高度。视图的框架可配置为您喜欢的任何内容。如果UIViewController 是从故事板创建的,则它与设备的屏幕大小相同。如果您在代码中创建它,您需要自己设置它。要将其设置为屏幕大小,您可以执行selectionController.view.frame = UIScreen.main.bounds
  • 谢谢!我现在就尝试实现它。
  • 感谢您的回答。 UIScreen.main.bounds 正是我所需要的。

标签: ios swift uiview viewcontroller


【解决方案1】:

您似乎在此处的“设置”视图中发送:

self.homeController?.displayController(menuOption: menuOption, view: self.settingsView)

但我没有看到您实际将该视图分配给视图控制器的位置:

func displayController(menuOption: MenuOption, view: UIView) {
    //[...]
    //What is HomeView?  
    selectionController.view.addSubview(HomeView(frame: view.frame))
    //[...]
    navigationController?.pushViewController(selectionController, animated: true)
}

您将 HomeView 传递给 ViewController,而不是传入的视图,并将 HomeView 的大小设置为传入视图的框架(在本例中为设置)。

我希望是这样的:

func displayController(menuOption: MenuOption, view: UIView) {
   let selectionController = UIViewController()
   selectionController.navigationItem.title = menuOption.name
   selectionController.view.backgroundColor = Color.blue

   selectionController.view.addSubview(view)

   navigationController?.navigationBar.tintColor = UIColor.white
   navigationController?.pushViewController(selectionController, animated: true)
}

不知道 HomeView 做了什么,但假设它有一些你想要的其他东西,也许传入的视图会成为 HomeView 的子视图,然后 HomeView 会返回你想要的。在这种情况下:

 selectionController.view.addSubview(HomeView(selectedView: view))

在这种情况下,HomeView 应该在内部从传入的视图中推断出它的帧大小,因此帧参数变得不必要。

【讨论】:

  • 回答得很漂亮!我应用了您的答案并像这样实现了 UIScreen.main.bounds: selectionController.view.addSubview(HomeView(selectedView: UIScreen.main.bounds )) 它就像一个魅力:)
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多