UICollectionView - 基于 Core Data 一对多关系的部分和行

Posted

技术标签:

【中文标题】UICollectionView - 基于 Core Data 一对多关系的部分和行【英文标题】:UICollectionView - sections and rows based on CoreData on-to-many relationship 【发布时间】:2013-10-20 09:03:09 【问题描述】:

我有一个如下所示的数据模型:

Location <------->> Item

每个位置可以有许多项目。我想在UICollectionView 中显示这些位置和项目。我希望每个位置都是包含项目的部分。像这样:

-----------------------
I   Location 1        I
-----------------------
I Item 1   I  Item 2  I
I--------- I-----------
I   Location 2        I
-----------------------
        [...]

我想知道哪种方式最适合实现这一目标?我以前从未使用过部分,所以我不确定这是否是正确的方法。如果这是要走的路,我如何将位置作为部分获取,然后在这些部分中显示项目?

我当前的非工作实现如下所示:

- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView

    return [[self.fetchedResultsController sections] count];


- (NSInteger)collectionView:(UICollectionView *)collectionView numberOfItemsInSection: (NSInteger)section

    id <NSFetchedResultsSectionInfo> sectionInfo = [self.fetchedResultsController sections][section];
    return [sectionInfo numberOfObjects];


- (NSFetchedResultsController *)fetchedResultsController

    if (_fetchedResultsController != nil) 
        return _fetchedResultsController;
    

    NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
    // Edit the entity name as appropriate.
    NSEntityDescription *entity = [NSEntityDescription entityForName:@"Location" inManagedObjectContext:self.managedObjectContext];
    [fetchRequest setEntity:entity];

    // Set the batch size to a suitable number.
    [fetchRequest setFetchBatchSize:20];

    // Edit the sort key as appropriate.
    NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"name" ascending:NO];
    NSArray *sortDescriptors = @[sortDescriptor];

    [fetchRequest setSortDescriptors:sortDescriptors];

    // Edit the section name key path and cache name if appropriate.
    // nil for section name key path means "no sections".
    NSFetchedResultsController *aFetchedResultsController = [[NSFetchedResultsController alloc] initWithFetchRequest:fetchRequest managedObjectContext:self.managedObjectContext  sectionNameKeyPath:nil cacheName:@"Master"];
    aFetchedResultsController.delegate = self;
    self.fetchedResultsController = aFetchedResultsController;

[...]

    return _fetchedResultsController;

有什么想法或建议吗?

【问题讨论】:

【参考方案1】:

您必须获取Item 对象,并使用sectionNameKeyPath: 参数进行分组 根据相关位置将项目分成几部分:

NSFetchRequest *fetchRequest = [[NSFetchRequest alloc] init];
NSEntityDescription *entity = [NSEntityDescription entityForName:@"Item" inManagedObjectContext:self.managedObjectContext];
[fetchRequest setEntity:entity];

// The first sort descriptor must use the sectionNameKeyPath key:
NSSortDescriptor *sort1 = [[NSSortDescriptor alloc] initWithKey:@"location.name" ascending:NO];
// The second sort descriptor sorts the items within each section:
NSSortDescriptor *sort2 = [[NSSortDescriptor alloc] initWithKey:@"name" ascending:NO];
NSArray *sortDescriptors = @[sort1, sort2];
[fetchRequest setSortDescriptors:sortDescriptors];

NSFetchedResultsController *aFetchedResultsController = [[NSFetchedResultsController alloc] initWithFetchRequest:fetchRequest
                      managedObjectContext:self.managedObjectContext
                        sectionNameKeyPath:@"location.name"
                                 cacheName:nil];

【讨论】:

谢谢马丁。你还知道我如何从viewForSupplementaryElementOfKind 获取Location 对象吗? @Anders:我得查一下,我不知道。 好的,将为它创建另一个问题。 @Anders:可能类似于id &lt;NSFetchedResultsSectionInfo&gt; sectionInfo = [self.fetchedResultsController sections][indexPath.section]; Item *item = sectionInfo.objects[0]; Location *location = item.location;,但未经测试。 嗯,我尝试过类似的方法。问题是每个位置都可能没有任何项目。所以我不断收到index 0 beyond bounds for empty array

以上是关于UICollectionView - 基于 Core Data 一对多关系的部分和行的主要内容,如果未能解决你的问题,请参考以下文章

UICollectionView - 基于水平滚动更新数组 indexPath

基于 iphone 5 与 iphone 6 的 UICollectionView 单元格宽度

UICollectionView - 基于 Core Data 一对多关系的部分和行

基于UILabel的动态UICollectionView标头大小

UICollectionView Cell Spacing 基于设备屏幕大小

基于UICollectionView的无限轮播器(封装)