nev*_*ing 38 iphone cocoa-touch core-data objective-c uitableview
我正在使用Core Data作为表格视图,我想使用每个结果的第一个字母作为节标题(所以我可以在侧面获得节索引).有没有办法用关键路径做到这一点?像下面的东西,我name.firstLetter用作sectionNameKeyPath(不幸的是,这不起作用).
我是否必须手动抓取每个结果的第一个字母并创建我的部分?是否更好地放入一个新属性来保存第一个字母并将其用作sectionNameKeyPath?
NSFetchedResultsController *aFetchedResultsController =
[[NSFetchedResultsController alloc] initWithFetchRequest:fetchRequest
managedObjectContext:managedObjectContext
sectionNameKeyPath:@"name.firstLetter"
cacheName:@"Root"];
Run Code Online (Sandbox Code Playgroud)
谢谢.
**编辑:**我不确定它是否有所作为,但我的结果是日语,按片假名排序.我想用这些片假名作为部分索引.
ger*_*ry3 79
您应该只将"name"作为sectionNameKeyPath传递.请参阅"Core Data支持带索引的UITableView"问题的答案.
更新
该解决方案仅在您只关心拥有快速索引标题滚动条时才有效.在这种情况下,您不会显示节标题.请参阅下面的示例代码.
否则,我同意refulgentis,即瞬态属性是最佳解决方案.此外,在创建NSFetchedResultsController时,sectionNameKeyPath具有此限制:
如果此密钥路径与fetchRequest中第一个排序描述符指定的密钥路径不同,则它们必须生成相同的相对排序.例如,fetchRequest中的第一个排序描述符可能指定持久属性的键; sectionNameKeyPath可以指定从persistent属性派生的transient属性的键.
使用NSFetchedResultsController的Boilerplate UITableViewDataSource实现:
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
return [[fetchedResultsController sections] count];
}
- (NSArray *)sectionIndexTitlesForTableView:(UITableView *)tableView {
return [fetchedResultsController sectionIndexTitles];
}
- (NSInteger)tableView:(UITableView *)tableView sectionForSectionIndexTitle:(NSString *)title atIndex:(NSInteger)index {
return [fetchedResultsController sectionForSectionIndexTitle:title atIndex:index];
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
id <NSFetchedResultsSectionInfo> sectionInfo = [[fetchedResultsController sections] objectAtIndex:section];
return [sectionInfo numberOfObjects];
}
// Don't implement this since each "name" is its own section:
//- (NSString *)tableView:(UITableView *)tableView titleForHeaderInSection:(NSInteger)section {
// id <NSFetchedResultsSectionInfo> sectionInfo = [[fetchedResultsController sections] objectAtIndex:section];
// return [sectionInfo name];
//}
Run Code Online (Sandbox Code Playgroud)
更新2
对于新的"uppercaseFirstLetterOfName"瞬态属性,将新的字符串属性添加到模型中的适用实体,并选中"瞬态"框.
有几种方法可以实现getter.如果要生成/创建子类,则可以将其添加到子类的实现(.m)文件中.
否则,您可以在NSManagedObject上创建一个类别(我把它放在我的视图控制器的实现文件的顶部,但您可以在它自己的正确的头和实现文件之间拆分):
@interface NSManagedObject (FirstLetter)
- (NSString *)uppercaseFirstLetterOfName;
@end
@implementation NSManagedObject (FirstLetter)
- (NSString *)uppercaseFirstLetterOfName {
[self willAccessValueForKey:@"uppercaseFirstLetterOfName"];
NSString *aString = [[self valueForKey:@"name"] uppercaseString];
// support UTF-16:
NSString *stringToReturn = [aString substringWithRange:[aString rangeOfComposedCharacterSequenceAtIndex:0]];
// OR no UTF-16 support:
//NSString *stringToReturn = [aString substringToIndex:1];
[self didAccessValueForKey:@"uppercaseFirstLetterOfName"];
return stringToReturn;
}
@end
Run Code Online (Sandbox Code Playgroud)
此外,在此版本中,不要忘记将'uppercaseFirstLetterOfName'作为sectionNameKeyPath传递:
NSFetchedResultsController *aFetchedResultsController = [[NSFetchedResultsController alloc] initWithFetchRequest:fetchRequest managedObjectContext:managedObjectContext
sectionNameKeyPath:@"uppercaseFirstLetterOfName" // this key defines the sections
cacheName:@"Root"];
Run Code Online (Sandbox Code Playgroud)
并且,要tableView:titleForHeaderInSection:在UITableViewDataSource实现中取消注释:
- (NSString *)tableView:(UITableView *)tableView titleForHeaderInSection:(NSInteger)section {
id <NSFetchedResultsSectionInfo> sectionInfo = [[fetchedResultsController sections] objectAtIndex:section];
return [sectionInfo name];
}
Run Code Online (Sandbox Code Playgroud)
ref*_*tis 11
可能有更优雅的方式来做到这一点,但我最近遇到了同样的问题,并提出了这个解决方案.
首先,我在我正在索引的对象上定义了一个名为firstLetterOfName的瞬态属性,并将getter写入该对象的.m文件中.前
- (NSString *)uppercaseFirstLetterOfName {
[self willAccessValueForKey:@"uppercaseFirstLetterOfName"];
NSString *stringToReturn = [[self.name uppercaseString] substringToIndex:1];
[self didAccessValueForKey:@"uppercaseFirstLetterOfName"];
return stringToReturn;
}
Run Code Online (Sandbox Code Playgroud)
接下来,我设置我的获取请求/实体以使用此属性.
NSFetchRequest *request = [[NSFetchRequest alloc] init];
NSEntityDescription *entity = [NSEntityDescription entityForName:@"Object" inManagedObjectContext:dataContext];
[request setEntity:entity];
[NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"name" ascending:YES selector:@selector(caseInsensitiveCompare:)];
NSArray *sortDescriptors = [NSArray arrayWithObject:sortDescriptor];
[request setSortDescriptors:sortDescriptors];
Run Code Online (Sandbox Code Playgroud)
注意事项,没有任何结果:小心NSFetchedResultsController - 它还没有完全被烘焙,但恕我直言,除了文档中列出的简单案例之外的任何情况,你可能会以"老式"的方式做得更好.
| 归档时间: |
|
| 查看次数: |
24580 次 |
| 最近记录: |