AliSoftware / OHAttributedLabel

UILabel that supports NSAttributedString
https://github.com/AliSoftware/OHAttributedLabel/wiki
1.51k stars 344 forks source link

Unexpected border on multiline labels #153

Closed jberlana closed 10 years ago

jberlana commented 11 years ago

I am experiencing an unexpected behavior, on multiline label OHAttributedLabel draws an estrange 1 pixel border.

OH attributed label is initialized on the xib, but basically has this properties:

OHAttributedLabel *a = [[OHAttributedLabel alloc] init];
a.font = [UIFont systemFontOfSize:13];
a.lineBreakMode = NSLineBreakByWordWrapping;
a.numberOfLines = 0;

This sceenshot shows the behaviour: https://dl.dropboxusercontent.com/u/538459/Screenshot%202013.08.09%2013.59.23.png

Any idea?

AliSoftware commented 11 years ago

Never seen this behavior before.

Did you try to change the font and/or background color and check if the unwanted line was affected by it? And used tools like DCInspector or such to check that this line is really due to OHAttributedLabel and not some other view behind that would have the unwanted line color ?

A was thinking maybe if you called sizeToFit the OHAttributedLabel (instead of controlling its frame yourself and using sizeThatFits or, even better, methods I provide in my NSAttributedString+Attributes category to compute the string size), and it the returned size lies in a subpixel (CGRect that has floating point positions like 10.5 that lies between two pixels), and you didn't use CGRectIntegral or any other function to round its values to fit on a pixel, maybe you could experience such a shift in your label vertical positioning, leading to shift it by one pixel and to reveal just a one-pixel-high line of some other view behind it…?

jberlana commented 11 years ago

It is just happening on iOS 7 beta 5 and there is no other views behind the label... is really strange behavior. I fix the problem with a really bad but working solution:

_commentLbl.layer.borderColor = [UIColor whiteColor].CGColor;
_commentLbl.layer.borderWidth = 1;

I am calculating the frame of the OHattributed label as you can show in the next fragment of code:

CTFramesetterRef framesetter = CTFramesetterCreateWithAttributedString((__bridge CFMutableAttributedStringRef)_commentLbl.attributedText);
CGSize suggestedSize = CTFramesetterSuggestFrameSizeWithConstraints(framesetter, CFRangeMake(0, 0), NULL, CGSizeMake(COMMENT_WIDTH, CGFLOAT_MAX), NULL);
CFRelease(framesetter);

//adjust the label the the new height.
CGRect newFrame = _commentLbl.frame;
newFrame.size.height  = suggestedSize.height +2;
self.commentLbl.frame = newFrame;
self.commentLbl.extendBottomToFit = YES;

I do that because the label can have emojii and calculating in other way was no returning the correct height. Maybe there have been a change in the NSAttributedString API's on iOS7.

Hope this can help.

AliSoftware commented 10 years ago

Just a question aside, why not using my NSAttributedString+Attributes category and its sizeConstrainedToSize: method for your fix, (and thus avoid the use of CoreText C code in your own code)?

CGSize suggestedSize = [_commentLbl.attributedText sizeConstainedToSize:CGSizeMake(COMMENT_WIDTH, CGFLOAT_MAX)];

I bet the line border you have is because of your +2 and maybe the use of extendBottomToFit = YES which adds some extra pixels to the label rendering rect to fix the emojis? What if you play around with those values (does changing the +2 to something bigger makes the unwanted border thicker? does removing extendBottomToFit removes the issue?)

jberlana commented 10 years ago

That work like a charm! Thanks a lot for your help, and for this great library!