我有一个基本的,但正在工作的应用程序,我正在努力。前提是:
在导航控制器中有一个带有加号按钮的表格视图控制器,用户按下加号按钮,它会显示模态视图;要求用户在4个文本字段中输入信息以获取以下信息:名称,金额,标题和日期。
我有以下型号:
具有wasCompleted属性的交易实体 具有name属性的Person实体 具有title属性的Action实体 具有金额属性的项目实体
事务实体与Person,Action和Item有关系。
当用户按下save时,我有以下代码将所有这些信息保存到Core Data Database:
- (IBAction)save:(id)sender
{
NSManagedObjectContext *context = [self managedObjectContext];
NSManagedObject *transaction = [NSEntityDescription insertNewObjectForEntityForName:@"Transaction" inManagedObjectContext:context];
NSManagedObject *person = [NSEntityDescription insertNewObjectForEntityForName:@"Person" inManagedObjectContext:context];
NSManagedObject *actionEvent = [NSEntityDescription insertNewObjectForEntityForName:@"Occasion" inManagedObjectContext:context];
NSManagedObject *amountType = [NSEntityDescription insertNewObjectForEntityForName:@"Item" inManagedObjectContext:context];
[person setValue:self.nameTextField.text forKey:@"name"];
[occasionEvent setValue:self.actionTextField.text forKey:@"title"];
[occasionEvent setValue:self.dateTextField.text forKey:@"dateOfEvent"];
[amountType setValue:self.itemTextField.text forKey:@"amount"];
[transaction setValue:person forKey:@"whoBy"];
[transaction setValue:actionEvent forKey:@"occasion"];
[transaction setValue:amountType forKey:@"item"];
}
这非常有效,但当然,它不是面向对象的编程,它是最好的,并且它不是使用setValues等的优秀代码。
我想要实现的是“保存”按钮:
调用事务NSManagedObject子类来创建一个新事务,我将检查该事务是否存在,如果不存在,我将使用wasCompleted属性创建Transaction对象,然后调用Person NSManagedObject类来创建该属性。事务NSManagedObject子类当然也调用Action和Item类来执行此操作。
我想我会使用类别(基于观看CS193p iTunes U课程)这样做,我花了好几个小时试图找出我实际传递的内容。从Save Button,我得到了NSManagedObjectContext,它是我想传递的一部分(尽管我正在使用来自AppDelegate的NSManagedObjectContext),但老实说我不知道我将什么传递给事务NSManagedObject子类。
我的问题是: 1)我应该创建一个Dictionary / Array来保存用户在Modal View类中添加的所有细节,并将其传递给Transaction NSManagedObject子类吗?或者,
2)是否有更好的方法将用户添加的信息传递给Transaction NSManagedObject子类?或者,
3)我应该从添加条目模态视图还是从事务NSManagedObject子类调用Person,Action和Item实体?
4)创建类别是正确的方法吗?
5)您是否能够提供一个简单的单行示例代码,说明我将传递给交易实体的内容?
对此的任何帮助都将受到大力赞赏。我已经被困了几个小时,我觉得它不会那么难,但我只是输了!我是iOS开发的新手!
编辑:
我想提供更多信息。我为每个实体(Person,Transaction等)提供了NSManagedObject子类,但除了将属性保存为属性之外,它们目前还没有做任何事情。在TableView和cellForRowAtIndexPath方法中,我正在调用transaction.whoBy.name等,这一切都正常。根据Mundi的最新回应,我觉得非常有帮助,但只需要一点点信息。模态视图绝对会用于添加新条目,但也可以用于编辑现有条目,因此,我必须检查它是否是新条目,或者是现有条目,然后传递该数据。
我将如何做这样的事情:
1)如果对象不存在,请使用每个属性创建一个新对象。 2)如果确实存在,则调用该属性。我从你的代码中看到它与:
有关NSManagedObjectContext *context = transaction.managedObjectContext;
所以在这种情况下,在Add Entry中,我只需要添加一些验证检查(因为如果我有两个相同名称的条目,我不希望NAME选项卡显示该信息两次,它应该是一个输入,等等,我会坚持我现在用于从save方法创建Transactions,Persons,Actions的代码,但是添加那些额外的验证检查?对不起,有点迷路了!
我完全理解传递现有数据的提及,但在代码中,我只是不确定如何实现这一点。
答案 0 :(得分:0)
我不认为在实体类本身或甚至在类别中创建实体是一个很好的模式。原则上,您通过创建和链接控制器中的实体(即控制器所用的实体)来做正确的事情。
您应该做的是创建NSManagedObject
子类(通过Core Data模型编辑器中的Xcode命令)。这提供了对象图的真实反映,并产生非常好的可读代码。
如果您的模态视图控制器在那里创建或编辑一个Transaction实例,我会将现有或新的事务对象传递给它。您可以从实例本身获取托管对象上下文。
NSManagedObjectContext *context = transaction.managedObjectContext;
如果传递的事务对象包含数据,则可以使用现有数据填充文本字段。如果在编辑“取消”后按下而不是“保存”,则只需删除新事务或保持现有事务不变。
NSManagedObject
子类允许您以更易读的形式设置属性和关系。例如:
person.name = self.nameTextField.text;
transaction.whoBy = person;
// etc.
顺便说一句,我想你在代码中写actionEvent
时可能意味着occasionEvent
。
还有一件事:Occasion实体的dateOfEvent
属性肯定是NSDate
类型,而不是字符串。因此,您可以将日期从文本(在文本字段中)转换为正确的NSDate
类型。虽然可以这样做,但更好的解决方案是使用UIDatePicker
来选择日期。从iOS 7开始,选择器应该与文本字段一起集成到控制器的视图中,而不是作为单独的模态视图控制器。