Silver Challenge Solution


#1

In last chapter’s challenge I handled this via using a footer, but I see that isn’t really what they wanted. Here is how I re-solved the issue.

The next two methods are for the addition of the last line. The first adds a row to the table beyond what the data source will provide (since “no more items” is not a value in the array). The second then checks to see if we have hit that final row and if so it provides the “no more items!” label.

-(NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
    return ([[[BNRItemStore sharedStore]allItems]count])+1;
}
-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"UITableViewCell" forIndexPath:indexPath];
    
    if (indexPath.row == [[[BNRItemStore sharedStore]allItems]count])
    {
        cell.textLabel.text = @"No more items!";
    }
    else
    {
        NSArray *items = [[BNRItemStore sharedStore]allItems];
        BNRItem *item = items[indexPath.row];
    
        cell.textLabel.text = [item description];
    }
    
    return cell;
}

This last method checks to see if the row is the final row and if so it doesn’t allow for any editing to be done. The challenge mentioned only the move, but the same should be done for delete. I don’t think you’d want the ability to delete the no more items message and certainly there is no way to delete it from the data source since it doesn’t exist there.

-(BOOL)tableView:(UITableView *)tableView canEditRowAtIndexPath:(NSIndexPath *)indexPath
{
    if (indexPath.row == [[[BNRItemStore sharedStore]allItems]count])
    {
        return FALSE;
    }
    else return TRUE;
}

#2

[quote=“C6silver”]
This last method checks to see if the row is the final row and if so it doesn’t allow for any editing to be done. The challenge mentioned only the move, but the same should be done for delete. I don’t think you’d want the ability to delete the no more items message and certainly there is no way to delete it from the data source since it doesn’t exist there.

-(BOOL)tableView:(UITableView *)tableView canEditRowAtIndexPath:(NSIndexPath *)indexPath { if (indexPath.row == [[[BNRItemStore sharedStore]allItems]count]) { return FALSE; } else return TRUE; } [/quote]

Hi C6silver,
It should be -(BOOL)tableView:(UITableView *)tableView canEditRowAtIndexPath:(NSIndexPath *)indexPath { if (indexPath.row == [[[BNRItemStore sharedStore]allItems]count] - 1) { return FALSE; } else return TRUE; } for it to work, because [[[BNRItemStore sharedStore]allItems]count] returns the number that starts from 1 and indexPath.row has numbers that start from zero.

Cheers,
Yarik


#3

[quote=“soberman”][quote=“C6silver”]
This last method checks to see if the row is the final row and if so it doesn’t allow for any editing to be done. The challenge mentioned only the move, but the same should be done for delete. I don’t think you’d want the ability to delete the no more items message and certainly there is no way to delete it from the data source since it doesn’t exist there.

-(BOOL)tableView:(UITableView *)tableView canEditRowAtIndexPath:(NSIndexPath *)indexPath { if (indexPath.row == [[[BNRItemStore sharedStore]allItems]count]) { return FALSE; } else return TRUE; } [/quote]

Hi C6silver,
It should be -(BOOL)tableView:(UITableView *)tableView canEditRowAtIndexPath:(NSIndexPath *)indexPath { if (indexPath.row == [[[BNRItemStore sharedStore]allItems]count] - 1) { return FALSE; } else return TRUE; } for it to work, because [[[BNRItemStore sharedStore]allItems]count] returns the number that starts from 1 and indexPath.row has numbers that start from zero.

Cheers,
Yarik[/quote]

Hi, while you are correct about the index values for the array and the table row, you are not correct about the solution. Remember, the last row containing the message about no more data is not in the array. Therefore if you subtract one as you are proposing you will not be allowed to edit the final row of the array data which is something you do want to be able to do. For this solution to work properly you do not want to subtract one.


#4

Did you actually try it? You need to subtract one, otherwise it does not work?


#5

You do not need to include the - 1 for this method to behave appropriately. The reason for this is that you’re checking for the row AFTER all of the items in the array have been accounted for, meaning that the row index will actually align with the count of the array items. You can start at the lowest level to verify this by launching the app with ZERO BNRItems. The “No More Items!” row should be at indexPath.row 0 - and there are 0 items. If there were 25 items, the “No more items!” row should be at indexPath.row 25.