如何在Swift中关闭ViewController?


213

我试图通过调用驳回迅速一个视图控制器dismissViewControllerIBAction

  @IBAction func cancel(sender: AnyObject) {
    self.dismissViewControllerAnimated(false, completion: nil)
    println("cancel")
}

@IBAction func done(sender: AnyObject) {
    self.dismissViewControllerAnimated(false, completion: nil)
    println("done")
}

segue的随机图像

我可以在控制台输出中看到println消息,但是ViewController永远不会消失。可能是什么问题呢?


2
您是如何呈现视图控制器的?
dasdom

我通过设置segue来完成映射-“显示”,请参阅随附的屏幕截图。
rshankar

4
尝试使用模式。如果使用推,则应使用导航控制器的pop方法将其关闭。
dasdom 2014年

Answers:


414

从您的图像来看,好像您使用push呈现了ViewController

dismissViewControllerAnimated用于使用模式所呈现接近ViewControllers

迅捷2

navigationController.popViewControllerAnimated(true)

斯威夫特4

navigationController?.popViewController(animated: true)

dismiss(animated: true, completion: nil)

6
对于“显示详细信息”序列,您将如何处理?
MoralCode 2014年

2
对于Swift 2.2 navigationController!.popViewControllerAnimated(true)
swiftBoy,2016年

7
对于Swift 3 navigationController!.popViewController(动画:true)
Alex Trott

173

我有解决您问题的方法。如果您使用模式显示视图,请尝试使用以下代码关闭视图控制器:

斯威夫特3:

self.dismiss(animated: true, completion: nil)

要么

如果使用“ push” segue显示视图

self.navigationController?.popViewController(animated: true)

1
谢谢,但仍然是相同的结果,它不会关闭ViewController
rshankar

4
这与OP使用的方法有何不同?
dasdom 2014年

30
如果您不回答我的问题,谈话将毫无用处。
dasdom 2014年

_ = self.navigationController?.popViewController(animated:true)
valexa

19

如果您这样做,我想您可能不会在控制台中收到println消息,

@IBAction func cancel(sender: AnyObject) {
  if(self.presentingViewController){
    self.dismissViewControllerAnimated(false, completion: nil)
    println("cancel")
   }
}

@IBAction func done(sender: AnyObject) {
  if(self.presentingViewController){
    self.dismissViewControllerAnimated(false, completion: nil)
    println("done")
  }    
}

1
stackoverflow.com/questions/30840235/…。请问您有帮助吗?我坚持了这么久,仍然找不到解决办法
Thiha Aung 2015年

14

在Swift 3.0到4.0中,就像在函数中键入以下内容一样简单:

self.dismiss(animated: true, completion: nil)

或者,如果您在导航控制器中,则可以“弹出”它:

self.navigationController?.popViewController(animated: true)

解散无法正常工作,因为我正在使用pushViewController。只有self.navigationController?.popViewController(animated:true)工作。
iOS

13
  1. 将要关闭的View嵌入到NavigationController中
  2. 添加带有“完成”作为标识符的BarButton
  3. 选择完成按钮,调用助手编辑器
  4. 为此按钮创建一个IBAction
  5. 将此行添加到括号中:

    self.dismissViewControllerAnimated(true, completion: nil)

12

用:

self.dismiss(animated: true, completion: nil)

代替:

self.navigationController.dismissViewControllerAnimated(true, completion: nil)

1
加一个!到navigationController,它对我
Jason G

1
@naturalc:请注意,如果navigationController为nil且您输入了!,应用程序将崩溃
jobima 2015年

8

如果呈现的控制器不带导航控制器,则可以从呈现的控制器的方法中调用以下代码。

self.presentingViewController?.dismiss(animated: true, completion: nil)

如果以模态方式显示ViewController,则可选的presentingViewController不会为nil,并且将执行代码。


你救了我的一天。
Shanu Singh

6

根据我的经验,我添加了一种方法来将我作为UIViewController的扩展名:

extension UIViewController {
    func dismissMe(animated: Bool, completion: (()->())?) {
        var count = 0
        if let c = self.navigationController?.viewControllers.count {
            count = c
        }
        if count > 1 {
            self.navigationController?.popViewController(animated: animated)
            if let handler = completion {
                handler()
            }
        } else {
            dismiss(animated: animated, completion: completion)
        }
    }
}

然后,我调用此方法以消除任何子UIViewController类中的视图控制器。例如,在取消动作中:

class MyViewController: UIViewController {
   ...
   @IBAction func cancel(sender: AnyObject) {
     dismissMe(animated: true, completion: nil)
   }
   ...
}

6

从Apple 文档中

呈现视图控制器负责解散其呈现的视图控制器

因此,仅从自身调用dismiss方法是一种不好的做法。

如果要呈现模式,应该做的是:

presentingViewController?.dismiss(animated: true, completion: nil)

4

不要从“取消”或“完成”到其他VC创建任何序列,只需将此代码编写为按钮@IBAction

@IBAction func cancel(sender: AnyObject) {
    dismiss(animated: false, completion: nil)
}

3

这是解散当前视图控制器并返回到先前视图控制器的一种方法。您只能通过情节提要进行此操作。

  1. 打开情节提要
  2. 右键单击“取消”按钮并将其拖动到上一个视图控制器,然后在该控制器上移回上一个控制器
  3. 现在释放右键单击,您可以看到一些在“取消”按钮上执行的操作
  4. 现在从列表中选择“存在弹出窗口”选项
  5. 现在,您可以通过单击取消按钮关闭当前视图

请尝试这个,它正在和我一起工作。

第二种方式-使用- navigationController.popViewControllerAnimated(true)

好运..


stackoverflow.com/questions/30840235/…。请问您有帮助吗?我坚持了这么久,仍然找不到解决办法
Thiha Aung 2015年

3
错了 您永远不会关闭视图,而要在当前视图之上显示一个新的视图控制器,从而导致内存泄漏。这很可能会导致您的应用被应用商店拒绝。
3366784 '17

2

作为参考,请注意您可能会解雇错误的视图控制器。例如,如果在另一个模式上方显示一个警告框或模式。(例如,您可以在当前模式警报的顶部显示一个Twitter帖子警报)。在这种情况下,您需要调用两次dismiss或使用取消同步功能。


1

如果要以模态形式显示ViewController,并想返回到根ViewController,请在返回根ViewController之前,先消除以模态形式显示的ViewController,否则该ViewController不会从内存中删除并导致内存泄漏。


1

在Swift 3.0中

如果您要关闭显示的视图控制器

self.dismiss(animated: true, completion: nil)

1

在Swift 4.1和Xcode 9.4.1中

如果您使用pushViewController呈现新的视图控制器,请使用此

self.navigationController?.popViewController(animated: false)

另一个复制粘贴答案
J. Doe

1

试试这个:

@IBAction func close() {
  dismiss(animated: true, completion: nil)
}

名为“ dismissViewController”的方法仅需要一个参数,我想这看起来像是将动画关闭到以前的视图,这是最简单的解决方案。
cassiodiego

0

将此代码编写为按钮操作以消除

  @IBAction func cancel(sender: AnyObject) {
   dismiss(animated: true, completion: nil)
  }

1
尽管此代码段可以解决问题,但提供说明确实有助于提高您的帖子质量。请记住,您将来会为读者回答这个问题,而这些人可能不知道您提出代码建议的原因。
DimaSan


0

如果您在父VC中使用present方法,则应调用此函数,以关闭子VC,请使用此方法

self.dismiss(animated: true, completion: nil)

如果您使用push方法调用子VC,则要关闭子VC,请使用此方法

self.navigationController?.popViewController(animated: true)
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.