I am using TTTAttributedLabel to apply formatting to text, however it seems to crash because I am trying to apply formatting to a range which includes emoji. Example:
NSString *text = @"@user1234 🍺🍺 #hashtag"; // text.length reported as 22 by NSLog as each emoji is 2 chars in length
cell.textLabel.text = text;
int length = 8;
int start = 13;
NSRange *range = NSMakeRange(start, length);
if (!NSEqualRanges(range, NSMakeRange(NSNotFound, 0))) {
// apply formatting to TTTAttributedLabel
[cell.textLabel addLinkToURL:[NSURL URLWithString:[NSString stringWithFormat:@"someaction://hashtag/%@", [cell.textLabel.text substringWithRange:range]]] withRange:range];
}
Note: I am passed the NSRange values from an API, as well as the text string.
In the above I am attempting to apply formatting to #hashtag. Normally this works fine, but because I have emoji involved in the string, I believe the range identified is attempting to format the emoji, as they are actually UTF values, which in TTTAttributedLabel causes a crash (it actually hangs with no crash, but...)
Strangely, it works fine if there is 1 emoji, but breaks if there are 2.
Can anyone help me figure out what to do here?
I assume this is from the Twitter API, and you are trying to use the entities dictionary they return. I have just been writing code to support handling those ranges along with NSString
's version of the range of a string.
My approach was to "fix" the entities dictionary that Twitter return to cope with the extra characters. I can't share code, for various reasons, but this is what I did:
unichar
by unichar
, doing this:
unichar
is in the surrogate pair range (0xd800
-> 0xdfff
).unichar
s). Then increment the loop counter by 1 to skip the partner of this surrogate pair as it's been handled now.I hope that helps! I also hope that one day I can open source this code as I think it would be incredibly useful!
The problem is that any Unicode character in your string with a Unicode value of \U10000 or higher will appears as two characters in NSString
.
Since you want to format the hashtag, you should use more dynamic ways to obtain the start and length values. Use NSString rangeOfString
to find the location of the #
character. Use that results and the string's length to get the needed length.
NSString *text = @"@user1234 🍺🍺 #hashtag"; // text.length reported as 22 by NSLog as each emoji is 2 chars in length
cell.textLabel.text = text;
NSUInteger start = [text rangeOfString:@"#"];
if (start != NSNotFound) {
NSUInteger length = text.length - start;
NSRange *range = NSMakeRange(start, length);
// apply formatting to TTTAttributedLabel
[cell.textLabel addLinkToURL:[NSURL URLWithString:[NSString stringWithFormat:@"someaction://hashtag/%@", [cell.textLabel.text substringWithRange:range]]] withRange:range];
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With