Search code examples
ioscore-datansfetchedresultscontrollernssortdescriptor

Custom sort in iOS, want to show default(All Group) title on top from Coredata


I am using core data with NSFetchedResultController. In this case, I have an n number of user groups and a user can select a particular group or select all group. So manually I added All group title, static ID and relevant content to the database.

NSFetchRequest <IRSUserAssetGroup *> *fetchRequest = [NSFetchRequest fetchRequestWithEntityName: [IRSUserAssetGroup entityName]];

NSSortDescriptor *nameSortDescriptor = [NSSortDescriptor sortDescriptorWithKey: NSStringFromSelector(@selector(assetGroupName))
                                                                     ascending: YES
                                                                      selector: @selector(localizedCaseInsensitiveCompare:)];

[fetchRequest setSortDescriptors: @[nameSortDescriptor]];

[fetchRequest setFetchBatchSize: 4];

NSManagedObjectContext *mainContext = [[IRSCoreDataManager sharedManager] managedObjectContext];

NSFetchedResultsController <IRSUserAssetGroup *> *fetchedResultsController = [[NSFetchedResultsController alloc] initWithFetchRequest: fetchRequest
                                                                                                                 managedObjectContext: mainContext
                                                                                                                   sectionNameKeyPath: nil
                                                                                                                            cacheName: nil];

NSError *fetchError = nil;

if (![fetchedResultsController performFetch: &fetchError])
    FCALog(@"fetch error: %@", fetchError);

[self setUserAssetGroupFetchedResultsController: fetchedResultsController];

This is my FRC code. I am using sort by name. Some group name has start with the number. Because of this All group not place in first place.

Is that possible All group place always top on sort?

Extra: I am using table view with search option

Example: @[@1, @5, @"text", @"aaaaaaa", @"All group"]. Here All group show always on top of the list. How can I sort like that.

Output: @[@"All group", @1, @5, @"aaaaaaa", @"text"]


Solution

  • You and I know that 'All group' is special because we read and understand the word, but core data has no way of knowing that the 'All group' is special; all it sees it that it starts with an "A". You could add another property to your Entity isAllGroup and first sort by that, and then by assetGroupName.

    Or you can have a property 'groupOrder' which is 0 for the "all Group" and 100 for every other groups. This allows you to have more room to have other special group ordering without creating a new property.

    An even more general approach would be to add a property assetGroupNameForSort and sort by that instead of assetGroupName which is used for display only. For most group the values are identical but for the "All Group" it is "__All Group" or something like that. This can also be used fix issue that can happen with names that are in difference languages that are sorted in ways you don't expect.

    I would recommend the first approach, just add an 'isAllGroup' property. It is the simplest and the data is readily understandable.

    Also: minor issue - a fetchedResultsController does not respect FetchBatchSize so you can remove it.