I'm struggling a little with Protocols and Delegates in Swift 4. I'm going to do my best to describe / show you what I have.
Main View Controller: (MVC) 1. I have the Main Viewcontroller class (MVC). The VC has a property of options that I would like to access from another ViewController Class (AVC)
class ViewController: UIViewController {
var options: Options?
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if (segue.identifier == "To Statements") {
// pass data to next view
let vc = segue.destination
let statementVC = vc as! StatementsViewController
statementVC.coreDataStack = coreDataStack
statementVC.currentPerson = currentPerson
}
}
extension ViewController: FormateStatementDelegate {
// formatting protocol
func addStatementFormat() -> Int {
// here is where I would use the options var that is found in the (MVC)
}
}
Statement ViewController: (SVC) 2. I have a View Controller class Statement ViewController (SVC) that is called from the (MVC). I am using prepare for segue func to set this view controller up for (MVC).
class StatementsViewController: UIViewController{
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if (segue.identifier == "Add Statement") {
// pass data to next view
//print("segue to add statement")
let vc = segue.destination
let addStatementVC = vc as! AddStatementViewController
addStatementVC.coreDataStack = coreDataStack
addStatementVC.personName = currentPerson!.name!
}
}
AddStatement View Controller (AVC) 3. I have a third View Controller class AddStatement View Controller (AVC) which is called from (SVC). I am also using prepare for segue func to set this view controller up as well from (SVC)
This class has a protocol that I define in (MVC).
protocol FormateStatementDelegate {
func func addStatementFormat() -> Intmal
}
class AddStatementViewController: UIViewController{
var delegate FormateStatementDelegate! = nil
}
Where I am confused is where to set the delegate property. The examples I have seen seem to set the delegate property in the prepare for seguer func. But since the (MVC) is the one that is conforming to the FormateStatementDelegate protocol where and how would I set the delegate in the (AVC) since they do not have a parent / child relationship. I hope I've explained this in a meaningful way.
Your delegate is declared as an implicitly unwrapped optional:
class AddStatementViewController: UIViewController{
var delegate FormateStatementDelegate! = nil
}
Be careful with that. If you forget to set the delegate, the app will crash. There's also potential for a strong retention cycle causing memory leak. The general pattern I use is to declare it as a weak optional:
protocol FormateStatementDelegate: class {
...
}
class AddStatementViewController: UIViewController{
weak var delegate: FormateStatementDelegate?
func doSomething() {
delegate?.addStatementFormat() // This statement will do nothing if delegate is nil
}
}
Now on to your problem: If I understand your problem description correctly, the segue order is like this:
ViewContorller -> StatementViewController -> AddStatementViewController
And AddStatementViewController
has a delegate, which ViewController
conforms to. You simply need to hold a reference to the instance of MainViewController
in the second view controller:
class ViewController: UIViewController {
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if (segue.identifier == "To Statements") {
// pass data to next view
let vc = segue.destination
let statementVC = vc as! StatementsViewController
statementVC.coreDataStack = coreDataStack
statementVC.currentPerson = currentPerson
statementVC.formateStatementDelegate = self
}
}
}
class StatementViewController {
weak var formateStatementDelegate: FormateStatementDelegate?
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if (segue.identifier == "Add Statement") {
// pass data to next view
//print("segue to add statement")
let vc = segue.destination
let addStatementVC = vc as! AddStatementViewController
addStatementVC.coreDataStack = coreDataStack
addStatementVC.personName = currentPerson!.name!
addStatementVC.delegate = formateStatementDelegate
}
}
}
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.