iOS关于在boundingRectWithSize和CoreText方法之间计算文本大小的不同结果

时间:2017-06-08 06:19:34

标签: ios

相同的单行文本在boundingRectWithSize and CoreText`方法之间获得不同的宽度。

这是我的代码和结果:

- (IBAction)buttonSeletor:(id)sender {
    [self getSeparatedLinesWithText:self.contentField.text fontSize:self.fontField.text.floatValue labelWidth:10000];
}

- (void)getSeparatedLinesWithText:(NSString *)text fontSize:(CGFloat)fontSize labelWidth:(CGFloat)labelWidth
{
    UIFont *font = [UIFont systemFontOfSize:fontSize];
    CTFontRef myFont = CTFontCreateWithName((__bridge CFStringRef)([font fontName]), [font pointSize], NULL);
    NSMutableAttributedString *attStr = [[NSMutableAttributedString alloc] initWithString:text];
    CTParagraphStyleSetting set[kCTParagraphStyleSpecifierCount] = { 0 };
    int count = 0;
    CTLineBreakMode paraLineBreak = (CTLineBreakMode)NSLineBreakByCharWrapping;
    set[count].spec = kCTParagraphStyleSpecifierLineBreakMode;
    set[count].valueSize = sizeof(CTLineBreakMode);
    set[count].value = &paraLineBreak;
    count++;
    CTParagraphStyleRef style = CTParagraphStyleCreate(set, count);

    [attStr addAttribute:(NSString *)kCTFontAttributeName value:(__bridge id)myFont range:NSMakeRange(0, attStr.length)];
    [attStr addAttribute:(NSString *)kCTParagraphStyleAttributeName value:(__bridge id)style range:NSMakeRange(0, attStr.length)];
    CTFramesetterRef frameSetter = CTFramesetterCreateWithAttributedString((__bridge CFAttributedStringRef)attStr);
    CGMutablePathRef path = CGPathCreateMutable();
    CGPathAddRect(path, NULL, CGRectMake(0,0,labelWidth,100000));
    CTFrameRef frame = CTFramesetterCreateFrame(frameSetter, CFRangeMake(0, 0), path, NULL);
    NSArray *lines = (__bridge NSArray *)CTFrameGetLines(frame);

    CGFloat width = [text boundingRectWithSize:CGSizeMake(CGFLOAT_MAX, CGFLOAT_MAX) options:NSStringDrawingUsesLineFragmentOrigin | NSStringDrawingUsesFontLeading attributes:@{NSFontAttributeName :font} context:nil].size.width;
    CTLineRef obj = (__bridge CTLineRef)(lines[0]);
    CGRect r = CTLineGetBoundsWithOptions(obj, kCTLineBoundsExcludeTypographicLeading);
    NSLog(@"\ntext %@\nboundingRectWithSize %f\nCoreText %f\nboundingRectWithSize/CoreText %f",text,width,r.size.width,width/r.size.width);
}

结果:

Result

设计草图:

Design sketch

1 个答案:

答案 0 :(得分:0)

如果要在标签中显示最多三行,则无需计算宽度等。您可以通过autolayout从界面(storyboard或xib)进行管理。

给你的标签有三个约束:leading,trailing,top和设置行数到3!如果您有固定宽度标签,则设置约束:top,leading, fixed width,行数应为3!

它将根据内容调整大小,并且不会显示超过三行!