Search code examples
uitextviewnsattributedstringtextkit

UITextView scroll performance for large attributed strings


How can scroll performance of a UITextView be improved when using attributed strings? The following sample code results in completely unacceptable performance on an iPad 3.

NSMutableParagraphStyle *pStyle = [[NSMutableParagraphStyle alloc] init];
pStyle.lineSpacing = 14.0;
pStyle.lineHeightMultiple = 20;
pStyle.maximumLineHeight = 20.0;
pStyle.minimumLineHeight = 20.0;
UIFont *font = [UIFont systemFontOfSize:20.0];
NSDictionary *attributes = @{ NSFontAttributeName : font, NSParagraphStyleAttributeName : pStyle};

NSMutableAttributedString *newline = [[NSMutableAttributedString alloc] initWithString:@"\n\n"];
NSMutableAttributedString *string  = [[NSMutableAttributedString alloc] initWithString:@"" attributes:@{}];

for (int paragraph=0; paragraph<300; paragraph++){
    for (int word=0; word<100; word++){
        [string appendAttributedString:[[NSAttributedString alloc] initWithString:@"text!"]];
    }
    [string appendAttributedString:newline];
}

[string setAttributes:attributes range:NSMakeRange(0, string.length)];

self.textView.attributedText = string;

I should mention that I am open to using Text Kit, but I wouldn't know where to start to ensure that performance is ultimately ok. Also, here's what's going on in the profiler while scrolling.

Profiler


Solution

  • Two things help here.

    1. First, I only needed the lineSpacing style set. Setting any of the other paragraph parameters results in slow scrolling.

    2. The second was to call [self.textView.layoutManager ensureLayoutForCharacterRange:NSMakeRange(0, self.textView.attributedText.length)]; in viewDidAppear:. Otherwise the first time you scroll through the document it is jerky.