Search code examples
iosobjective-cnsstringnsattributedstringstrikethrough

Objective C - Strikethrough on Table Cell Label when complete


Here is some working code that I have which adds a checkmark to a to-do item when it is complete:

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    static NSString *cellIdentifier = @"ListPrototypeCell";
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:cellIdentifier forIndexPath:indexPath];
    XYZToDoItem *toDoItem = [self.toDoItems objectAtIndex:indexPath.row];
    cell.textLabel.text = toDoItem.itemName;
    if (toDoItem.completed) {
        cell.accessoryType = UITableViewCellAccessoryCheckmark;

    } else {
         cell.accessoryType = UITableViewCellAccessoryNone;
    }    return cell;
}

What I want to do is remove the checkmark code and some something like (basic logic of it):

    if (toDoItem.completed) {
        cellIdentifier.textLabel (NSAttributedString Strikethrough = YES)

    } else {
         cellIdentifier.textLabel (NSAttributedString Strikethrough = NO)
    }    return cell;

I've also tried to change NSString to NSAttributedString and NSMutableAttributedString based on some other questions and answers I've seen such as this one like this:

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    NSDictionary* attributes = @{
                             NSStrikethroughStyleAttributeName: [NSNumber numberWithInt:NSUnderlineStyleSingle]
                             };
    static NSAttributedString* cellIdentifier = [[NSAttributedString alloc] initWithString:@"ListPrototypeCell" attributes:attributes];
    cell.textLabel.attributedText = cellIdentifier;
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:cellIdentifier forIndexPath:indexPath];
    XYZToDoItem *toDoItem = [self.toDoItems objectAtIndex:indexPath.row];
    cell.textLabel.text = toDoItem.itemName;
    if (toDoItem.completed) {
        cell.accessoryType = UITableViewCellAccessoryCheckmark;


    } else {
        cell.accessoryType = UITableViewCellAccessoryNone;
    }    return cell;
}

But I'm not sure of the exact implementation, for example how to call this on the if (toDoItem.completed) method. This will only need to be supported by iOS7.

How can I get the strikethrough effect on my Table Cell Label when the item is complete?


Solution

  • There are several things wrong with the code you're using. The crash is the result of setting an attributed string as the cell's identifier. From there, you should be dequeuing the cell before you try to assign values to its properties. You should also be initializing the attributed string from the object in your toDoItems array. Overall, I think this is what you meant to do:

    - (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
    {
        static NSString *cellID = @"ListPrototypeCell";
        UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:cellID forIndexPath:indexPath];
    
    
        XYZToDoItem *toDoItem = [self.toDoItems objectAtIndex:indexPath.row];
    
        if (toDoItem.completed) {
            cell.accessoryType = UITableViewCellAccessoryCheckmark;
    
            NSDictionary* attributes = @{NSStrikethroughStyleAttributeName: [NSNumber numberWithInt:NSUnderlineStyleSingle]};
            NSAttributedString* attributedString = [[NSAttributedString alloc] initWithString:toDoItem.itemName attributes:attributes];
    
            cell.textLabel.attributedText = attributedString;
    
        } else {
            cell.textLabel.text = toDoItem.itemName;
            cell.accessoryType = UITableViewCellAccessoryNone;
        } 
    
        return cell;
    }