在不调用每个 viewDidAppear 的情况下解雇 rootViewController
Posted
技术标签:
【中文标题】在不调用每个 viewDidAppear 的情况下解雇 rootViewController【英文标题】:Dismissing to rootViewController without calling each viewDidAppear 【发布时间】:2019-11-20 18:16:34 【问题描述】:我的视图控制器就像 MainView -> NavigationController A -> ViewController A -> ViewController B -> ViewController C,我想关闭 ViewControllers(A、B 和 C)并再次显示 MainView...我使用了这条线
self.view.window?.rootViewController?.dismiss(animated: false, completion: nil)
它工作得很好..问题是在解除 viewControllers(A、B 和 C)时,它会调用每个 viewDidAppear,这会运行我不想运行的代码.. 解除并执行的最佳做法是什么返回MainView而不调用每个viewController
【问题讨论】:
@Sammy 1- 我不使用情节提要 2- 我将每个视图呈现为全屏视图 这是我转到 ViewController A 的代码 let vc = ViewControllerA() let navigationController = UINavigationController(rootViewController: vc) navigationController.modalPresentationStyle = .fullScreen senderVC.present(navigationController, animated: true, completion: nil) 【参考方案1】:您必须有其他导致问题的代码。
这是一个完整的例子......
PresDisViewController
是起始视图控制器
它的按钮创建一个以ViewControllerA
为根的导航控制器
ViewControllerA
有一个按下 ViewControllerB
的按钮
ViewControllerB
有一个按钮可以按下 ViewControllerC
ViewControllerC
有一个按钮可以执行你的 self.view.window?.rootViewController?.dismiss(animated: false, completion: nil)
每个 VC 都实现 viewDidAppear()
并将自己打印到调试控制台。
运行时的输出:
viewDidAppear scratchy.PresDisViewController
viewDidAppear scratchy.ViewControllerA
viewDidAppear scratchy.ViewControllerB
viewDidAppear scratchy.ViewControllerC
viewDidAppear scratchy.PresDisViewController
如您所见,当导航控制器被解除时,viewDidAppear
不会在 VC 中调用。
import UIKit
class ViewControllerA: UIViewController
let btn: UIButton =
let v = UIButton()
v.translatesAutoresizingMaskIntoConstraints = false
v.setTitle("Do Push", for: .normal)
v.backgroundColor = .red
return v
()
override func viewDidLoad()
super.viewDidLoad()
view.backgroundColor = .white
view.addSubview(btn)
NSLayoutConstraint.activate([
btn.centerYAnchor.constraint(equalTo: view.centerYAnchor, constant: -40.0),
btn.centerXAnchor.constraint(equalTo: view.centerXAnchor, constant: 0.0),
])
btn.addTarget(self, action: #selector(didTap(_:)), for: .touchUpInside)
@objc func didTap(_ sender: Any?) -> Void
let vc = ViewControllerB()
self.navigationController?.pushViewController(vc, animated: true)
override func viewDidAppear(_ animated: Bool)
super.viewDidAppear(animated)
print("viewDidAppear", NSStringFromClass(self.classForCoder))
class ViewControllerB: UIViewController
let btn: UIButton =
let v = UIButton()
v.translatesAutoresizingMaskIntoConstraints = false
v.setTitle("Do Push", for: .normal)
v.backgroundColor = .systemYellow
return v
()
override func viewDidLoad()
super.viewDidLoad()
view.backgroundColor = .white
view.addSubview(btn)
NSLayoutConstraint.activate([
btn.centerYAnchor.constraint(equalTo: view.centerYAnchor, constant: 0.0),
btn.centerXAnchor.constraint(equalTo: view.centerXAnchor, constant: 0.0),
])
btn.addTarget(self, action: #selector(didTap(_:)), for: .touchUpInside)
@objc func didTap(_ sender: Any?) -> Void
let vc = ViewControllerC()
self.navigationController?.pushViewController(vc, animated: true)
override func viewDidAppear(_ animated: Bool)
super.viewDidAppear(animated)
print("viewDidAppear", NSStringFromClass(self.classForCoder))
class ViewControllerC: UIViewController
let btn: UIButton =
let v = UIButton()
v.translatesAutoresizingMaskIntoConstraints = false
v.setTitle("Do Dismiss", for: .normal)
v.backgroundColor = .blue
return v
()
override func viewDidLoad()
super.viewDidLoad()
view.backgroundColor = .white
view.addSubview(btn)
NSLayoutConstraint.activate([
btn.centerYAnchor.constraint(equalTo: view.centerYAnchor, constant: 40.0),
btn.centerXAnchor.constraint(equalTo: view.centerXAnchor, constant: 0.0),
])
btn.addTarget(self, action: #selector(didTap(_:)), for: .touchUpInside)
@objc func didTap(_ sender: Any?) -> Void
self.view.window?.rootViewController?.dismiss(animated: false, completion: nil)
override func viewDidAppear(_ animated: Bool)
super.viewDidAppear(animated)
print("viewDidAppear", NSStringFromClass(self.classForCoder))
class PresDisViewController: UIViewController
let btn: UIButton =
let v = UIButton()
v.translatesAutoresizingMaskIntoConstraints = false
v.setTitle("Do Present", for: .normal)
v.backgroundColor = .orange
return v
()
override func viewDidLoad()
super.viewDidLoad()
view.backgroundColor = .white
view.addSubview(btn)
NSLayoutConstraint.activate([
btn.topAnchor.constraint(equalTo: view.topAnchor, constant: 60.0),
btn.centerXAnchor.constraint(equalTo: view.centerXAnchor, constant: 0.0),
])
btn.addTarget(self, action: #selector(didTap(_:)), for: .touchUpInside)
@objc func didTap(_ sender: Any?) -> Void
let vcA = ViewControllerA()
let navVC = UINavigationController(rootViewController: vcA)
navVC.modalPresentationStyle = .fullScreen
present(navVC, animated: true, completion: nil)
override func viewDidAppear(_ animated: Bool)
super.viewDidAppear(animated)
print("viewDidAppear", NSStringFromClass(self.classForCoder))
【讨论】:
【参考方案2】:这是通过 Storyboard 完成的。我不知道如何通过代码来做到这一点。我希望它有帮助 在你的 MainViewController 添加这个:
@IBAction func unwindToMainView(segue:UIStoryboardSegue)
在所有其他ViewController(viewController A,ViewController B,ViewController C)中, 像这样单击并拖动
然后选择你在mainVC中添加的segue
现在选择那个segue并给它一个标识符
从这里你可以在任何你想要的地方使用该标识符执行 segue。我使用按钮来执行那个segue
【讨论】:
以上是关于在不调用每个 viewDidAppear 的情况下解雇 rootViewController的主要内容,如果未能解决你的问题,请参考以下文章
如何在不为每个帖子调用评论对象的情况下从墙上的帖子中获取评论计数?