在swift中从另一个访问Viewcontroller的实例

McL*_*nce 29 uiviewcontroller ios swift

我试图将数据从一个View Controller的文本字段传输到另一个View标签.

如何从其他View Controller的代码中调用View Controller实例?我正在使用故事板,因此我从未在代码中创建View Controller的实例?是否自动创建实例?他们有什么名字?

谢谢你的帮助!

Ima*_*tit 20

1.如果包含文本字段的视图控制器可以调用(带有segue)包含标签的视图控制器...

在项目中添加一个新的Cocoa Touch类文件,为其命名FirstViewController并在其中设置以下代码:

import UIKit

class FirstViewController: UIViewController {

    @IBOutlet weak var textField: UITextField! // FIXME: link this to the UITextField in the Storyboard!!!

    override func prepareForSegue(segue: UIStoryboardSegue, sender: AnyObject?) {
        let controller = segue.destinationViewController as! SecondViewController
        controller.text = textField.text
    }

}
Run Code Online (Sandbox Code Playgroud)

在项目中添加一个新的Cocoa Touch类文件,为其命名SecondViewController并在其中设置以下代码:

import UIKit

class SecondViewController: UIViewController {

    var text: String?
    @IBOutlet weak var label: UILabel! // FIXME: link this to the UILabel in the Storyboard!!!

    override func viewDidLoad() {
        super.viewDidLoad()

        label.text = text
    }

}
Run Code Online (Sandbox Code Playgroud)

在Storyboard中,将第一个视图控制器嵌入到UINavigationController.使用a UIButton或a 将第一个视图控制器链接到第二个视图控制器UIBarButtonItem.将第一个视图控制器FirstViewController的名称设置为,将第二个视图控制器的名称设置为SecondViewController.UITextField在第一个视图控制器中创建一个.UILabel在第二个视图控制器中创建一个.链接文本框,并在标签各自的声明FirstViewControllerSecondViewController.


2.如果包含标签的视图控制器可以调用(带有segue)包含文本字段的视图控制器...

在这里,这是一个完美的协议/委托案例.您可能会在StackOverflow上找到很多处理此问题的东西.但是,这是一个粗略的例子.

在项目中添加一个新的Cocoa Touch类文件,为其命名FirstViewController并在其中设置以下代码:

import UIKit

class FirstViewController: UIViewController, DetailsDelegate {

    @IBOutlet weak var label: UILabel! // FIXME: link this to the UILabel in the Storyboard

    func updateLabel(withString string: String?) {
        label.text = string
    }

    override func prepareForSegue(segue: UIStoryboardSegue, sender: AnyObject?) {
        let controller = segue.destinationViewController as! SecondViewController
        controller.delegate = self
    }

}
Run Code Online (Sandbox Code Playgroud)

在项目中添加一个新的Cocoa/Cocoa Touch类文件,为其命名SecondViewController并在其中设置以下代码:

import UIKit

protocol DetailsDelegate: class {
    func updateLabel(withString string: String?)
}

class SecondViewController: UIViewController {

    weak var delegate: DetailsDelegate?
    @IBOutlet weak var textField: UITextField! // FIXME: link this to the UITextField in the Storyboard

    override func viewWillDisappear(animated: Bool) {
        super.viewWillDisappear(animated)

        delegate?.updateLabel(withString: textField.text)
    }

}
Run Code Online (Sandbox Code Playgroud)

在Storyboard中,将第一个视图控制器嵌入到UINavigationController.使用a UIButton或a 将第一个视图控制器链接到第二个视图控制器UIBarButtonItem.将第一个视图控制器FirstViewController的名称设置为,将第二个视图控制器的名称设置为SecondViewController.UILabel在第一个视图控制器中创建一个.UITextField在第二个视图控制器中创建一个.链接文本框,并在标签各自的声明FirstViewControllerSecondViewController.

  • 有没有办法在没有segue的情况下实现这样的目标? (3认同)

Joã*_*ves 15

Imanou Petit和Oscar Swanros已经正确回答.然而,有一种替代方案是相当"hacky",我不得不使用它来在两个视图控制器之间传输数据而没有连接它们的segue.

要获取应用程序的根视图控制器,您可以执行以下操作:

UIApplication.sharedApplication().windows[0].rootViewController
Run Code Online (Sandbox Code Playgroud)

从那里你可以得到你想要的任何视图控制器.例如,如果您想要根视图控制器的第二个子视图控制器,那么您将执行以下操作:

let viewController = UIApplication.sharedApplication().windows[0].rootViewController?.childViewControllers[1] as? YourViewController
viewController?.yourProperty = newValue
Run Code Online (Sandbox Code Playgroud)

请记住,这种方法相当"hacky",可能违反了最佳编码实践.


Osc*_*ros 5

您需要在视图控制器之间创建一个Segue:

  1. 在故事板上,选择ViewController A.
  2. 按住Control,单击ViewController A,拖放蓝线到ViewController B.如果ViewController A嵌入了a NavigationController,请从放开时出现的菜单中选择"显示".否则,请选择"以模态方式呈现".
  3. 在故事板上选择Segue,在Utilities面板上,转到Attributes Inspector并为您的segue分配一个标识符(例如:"DetailSegue").

现在,当你想要触发segue时ViewController A,你只需要打电话(也许只需按一下按钮):

@IBAction func buttonTapped() {
    self.performSegueWithIdentifier("DetailSegue", sender: self)
}
Run Code Online (Sandbox Code Playgroud)

要传递值ViewController B,请覆盖以下prepareForSegue:sender方法ViewController A:

override func prepareForSegue(segue: UIStoryboardSegue!, sender: AnyObject!) {
    if segue.identifier == "DetailSegue" {
        var viewControllerB = segue.destinationViewController as ViewControllerB
        viewControllerB.text = self.textField.text
    }
}
Run Code Online (Sandbox Code Playgroud)

非常直截了当.

请注意,要使其正常工作,您的ViewController B类应如下所示:

class ViewControllerB: UIViewController {
    ver label = UILabel(...)
    var text: String? 

    override func viewDidLoad() {
        super.viewDidLoad()

        label.text = text!
    }
}
Run Code Online (Sandbox Code Playgroud)

希望这可以帮助.