【问题标题】:error performing segue in Swift iOS在 Swift iOS 中执行 segue 时出错
【发布时间】:2015-08-02 18:06:25
【问题描述】:

我最近一直在玩 swift segues,我很想在我最新的应用程序中加入一个,问题是我似乎无法让它们工作。到目前为止,我已经创建了另一个视图控制器 SecondViewController 并在我的 ViewControllerSecondViewController 文件中这样引用:

ViewController.swift

import UIKit

class ViewController: UIViewController {

var secondViewController: SecondViewController!
var viewController: ViewController!

override func viewDidLoad() {
//lots more code here

SecondViewController.swift

import UIKit

class SecondViewController: UIViewController {

var secondViewController: SecondViewController!
var viewController: ViewController!

override func viewDidLoad() {

他们在故事板视图中我已经 crtl+将一个 segue 从 viewController 拖到 secondViewController 并且一旦使用右侧面板创建了 segue 标识符,segue 标识符是 GameOver 和 segue 类型是show

现在我想在没有用户交互的情况下自动调用 segue,在最终的应用程序中,一旦用户通过 func 击中游戏,它将触发 segue 并显示一个新的 UIView,其中高分可以与其他一些显示项目。

我用来调用 segue 的代码是:

self.viewController.performSegueWithIdentifier("GameOver", sender: self)

我收到以下错误...

Thread 1:EXC_BAD_INSTRUCTION (code=EXC_1386_INVOP, subcode=0x0

我在输出字段中也有这个错误...

fatal error: unexpectedly found nil while unwrapping an Optional value (lldb)

我已经使用了 segues 的名称和文件名,但仍然遇到同样的错误,我确定我缺少一些基本的东西,所以希望有人可以帮助我解决这个问题。

我创建了一个新项目并将其上传到 GitHub,如果有人能告诉我我缺少什么,那就太好了,这是我的 GitHub 存储库的链接https://github.com/rich84ts/TestSingleView

谢谢。

【问题讨论】:

  • 好吧,一方面,你的 segue 是 Show segue。但这没有任何意义 - 你不在导航控制器中。
  • @matt,我同意他不应该在这里进行 Show segue,但是如果 viewController 没有嵌入 NavigationController 中,iOS 会以模态方式呈现。
  • @vacawama 你知道,我也知道,但如果他知道自己在做什么而不是意外工作会更好。 :)

标签: ios iphone swift uiviewcontroller segue


【解决方案1】:

您不能只输入一些实例属性并期望它们神奇地做某事:

class ViewController: UIViewController {

    var secondViewController: SecondViewController!
    var viewController: ViewController!

}

这些属性是nil,向它们发送消息会使您的应用崩溃。你必须给他们价值

在你的情况下,segue 来自这个视图控制器,所以你真正想说的是

self.performSegueWithIdentifier("GameOver", sender: self)

您犯的另一个大错误是您在viewDidLoad 中说了所有这些。那太早了!你还不能做任何segue-ing;您的视图甚至不在界面中!将您的代码移动到viewDidAppear:,它就会真正起作用:

override func viewDidAppear(animated: Bool) {
    super.viewDidAppear(animated)
    self.performSegueWithIdentifier("GameOver", sender: self)
}

你的代码仍然很傻而且没用,但至少你会看到一些事情发生并且你可以从那里继续开发。

我实际上建议你删除你的 viewDidLoad 实现并将这个:

override func viewDidAppear(animated: Bool) {
    super.viewDidAppear(animated)
    func delay(delay:Double, closure:()->()) {
        dispatch_after(
            dispatch_time(
                DISPATCH_TIME_NOW,
                Int64(delay * Double(NSEC_PER_SEC))
            ),
            dispatch_get_main_queue(), closure)
    }
    delay(1) {
        self.performSegueWithIdentifier("GameOver", sender: self)
    }
}

这将允许第一个视图控制器出现,等待一秒钟,然后召唤第二个视图控制器。因此,您将了解到一切都已正确连接,并且可以继续做一些更实际的事情。

【讨论】:

  • matt 是对的 除了你的类已经是当前的 ViewController,所以如果你想执行一个 segue 你只需要调用 self.performSegueWithIdentifier("GameOver", sender: nil)
【解决方案2】:

您可以通过控制单击 ViewController 对象并从手动转场拖动到目标视图控制器来从情节提要创建手动转场。然后,您可以使用源控制器中的指定标识符调用此 segue。你不需要引用目标视图控制器来实现这一点。

要在视图控制器中引用情节提要中的任何内容,您需要像这样声明属性:

@IBOutlet var someProperty : UIView?

@IBOutlet 位使属性在情节提要上可见,您可以从它控制拖动到视图中的相应对象。但是你不能用视图控制器来做到这一点。要在 segue 之前访问源视图控制器中的目标视图控制器,您需要覆盖 func prepareForSegue(_ segue: UIStoryboardSegue, sender sender: AnyObject?)。这允许您在实际 segue 之前从 segue-instance 访问目标视图控制器(例如,如果您需要传递数据)。

【讨论】:

    【解决方案3】:

    首先你的 self.viewController 是一个 nil 对象,因为你只创建了变量而没有初始化它。您不能使用 nil 对象调用方法。其次,您已经从情节提要创建了一个推送转场,但情节提要中没有导航控制器,因此 self.performSegueWithIdentifier("GameOver", sender: self) 也将不起作用。要使用 push segue,您应该在 UINavigationController 的堆栈中拥有当前视图控制器,因此首先在情节提要中添加一个 UINavigationController 并制作该初始视图控制器并将 ViewController 设置为导航控制器的 rootViewController 然后调用 self.performSegueWithIdentifier("GameOver", sender: self )

    然后代码将起作用。希望对您有所帮助。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2016-02-29
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2016-11-23
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多