2018年6月30日 星期六
iOS 在 screens 之間傳資料
所謂 screens 之間就是 ViewControllers 之間,這裡討論的是 A screen 叫出了 B screen,但 B screen 想要送資料回 A screen 時該怎麼做。
通常如果是 A controller contains B controller (A screen 叫出了 B screen),那麼不應該讓 B screen 知道關於 A controller 的細節,否則就是 circular dependency,意思就是不該這樣做:
```swift
class BViewController: UITableViewController, . . . {
// This variable refers to the other view controller
var aController: AViewController
@IBAction func done() {
// Create the new checklist item object
let item = ChecklistItem()
item.text = textField.text!
// Directly call a method from AViewController
aController.add(item)
}
}
```
有時候有些 screen 是要被很多 ViewController 呼叫的,所以如果這樣做也同時失去了可以被很多 controller 呼叫的彈性
比較好的作法應該是用 delegate
如此一來 B 就不知道 A 是誰,B 只知道有哪些 delegate 可以用。
那怎麼 delegate 呢?在 Swift 裡面就是寫一個 protocol,Protocol 的功用就是給有 implement 這個 protocol 的 class 一些規範,說白了就是定義有哪些 functions, 哪些是 required 哪些是 optional
example:
```swift
protocol AddItemViewControllerDelegate: class {
func addItemViewControllerDidCancel(
_ controller: AddItemViewController)
func addItemViewController(
_ controller: AddItemViewController,
didFinishAdding item: ChecklistItem)
}
```
從此之後 B controller 只需要
```swift
weak var delegate: AddItemViewControllerDelegate?
```
就可以操作 delegate 的 controller 了
通常 delegate 會是 weak variable 以及 optional
optional 的原因是 delegate 本來就 optional,要不要 implement 都沒關係。另外一個主要原因是當 StoryBoard load 這個 controller 時,並不知道 delegate 是誰,所以應該要是 optional。
通常會在 prepare 的 function 指派 delegate,此例就是在 A segue 到 B 時指派 A 成為 B 的 AddItemViewControllerDelegate 的 delegate,在 A controller 裡面加上:
```swift
override func prepare(for segue: UIStoryboardSegue,
sender: Any?) {
// 1
if segue.identifier == "B" {
// 2
let controller = segue.destination
as! BController
// 3
controller.delegate = self
}
}
```
Delegates in five easy steps:
These are the steps for setting up the delegate pattern between two objects, where object A is the delegate for object B, and object B will send messages back to A. The steps are:
1 - Define a delegate protocol for object B.
2 - Give object B a delegate optional variable. This variable should be weak.
3 - Update object B to send messages to its delegate when something interesting happens, such as the user pressing the Cancel or Done buttons, or when it needs a piece of information. You write delegate?.methodName(self, . . .)
4 - Make object A conform to the delegate protocol. It should put the name of the protocol in its class line and implement the methods from the protocol.
5 - Tell object B that object A is now its delegate.
訂閱:
張貼留言 (Atom)

沒有留言:
張貼留言