初学者,这是我第一次使用委托,我很困惑 - 我正试图在两个控制器之间传递数据,第一个是显示某些产品的tableview,另一个是模态允许用户输入要在该tableview上显示的新产品的视图。当用户在模态视图中点击“保存”时,我想将新产品保存到核心数据中并将其显示在tableview上。
用户在AddProductController
(模态视图)的三个文本字段中输入信息,然后点击保存调用handleSave
:
func handleSave() {
guard let newProductUrl = self.urlTextField.text else {
print("error getting text from product url field")
return
}
guard let newProductName = self.nameTextField.text else {
print("error getting text from product name field")
return
}
guard let newProductImage = self.logoTextField.text else {
print("error getting text from product logo field")
return
}
DispatchQueue.main.async {
self.productSaveDelegate?.save(name: newProductName, url: newProductUrl, image: newProductImage)
let companyController = CompanyController()
self.navigationController?.pushViewController(companyController, animated: true)
}
}
反过来调用save
中的ProductController
(表格视图):
func save(name: String, url: String, image: String) {
guard let appDelegate =
UIApplication.shared.delegate as? AppDelegate else {
return
}
let managedContext =
appDelegate.persistentContainer.viewContext
let entity =
NSEntityDescription.entity(forEntityName: "Product",
in: managedContext)!
let product = NSManagedObject(entity: entity,
insertInto: managedContext)
product.setValue(name, forKey: "name")
product.setValue(url, forKey: "url")
product.setValue(image, forKey: "image")
do {
try managedContext.save()
products.append(product)
} catch let error as NSError {
print("Could not save. \(error), \(error.userInfo)")
}
tableView.reloadData()
}
如果我理解正确,我使用委托作为两者之间的一种链接,以便我可以将用户输入的值直接传递到我的save
函数中?如果我错了,请纠正我,我很新。但是我在ProductController
(tableview控制器)的顶部创建了类范围之外的委托,如下所示:
protocol ProductSaveDelegate {
func save(name: String, url: String, image: String)
}
然后在AddProductController
(用户输入新产品信息的模态视图)中,我初始化了类顶部附近的委托:
var productSaveDelegate: ProductSaveDelegate?
然后使用它来调用save
中的handleSave()
函数,如上所示。
当我尝试将ProductSaveDelegate
添加到AddProductController
的类定义时,我收到错误消息,指出AddProductController
不符合协议。
我可以在此处更改以使用户输入的产品正确保存到核心数据?在此先感谢您的帮助!
答案 0 :(得分:0)
代表们真的很酷很强大,但有时,是的,他们可能会让人感到困惑。您需要在ProductController
内初始化委托,而不是AddProductController
。
这是一张很棒的图片,展示了委托和协议设置的工作原理:
图片来自Andrew Bancroft的website
在这种情况下,您的代表是您的ProductController
,而您的代表是AddProductController
答案 1 :(得分:0)
请确认您已签署代理
不要忘记 -
classObject.delegate = self
我想你已经熟悉代表了,
您收到此错误的原因是,您not implemented the delegate method
中有AddProductController
(在您的情况下是假的,因为我可以看到它已实现),或者您忘记订阅该代表,这样做你需要确保 -
- 订阅代理,即在转换到下一个控制器之前,将代表设置为自我 -
醇>
// addProductController is the AddProductController Class's Object
addProductController.productSaveDelegate = self
self.navigationController?.present(addProductController, animated: true, completion: nil)
同样在同一个类中你需要实现协议中定义的方法,例如你的func save(name: String, url: String, image: String)
(已经实现)
您还可以查看small demo,我已在此处实施协议。